1. xact.c: update comments about changing MyProc->xid and MyProc->xmin.
2. varsup.c:ReadNewTransactionId(): don't read nextXid from disk - this func doesn't allocate next xid, so ShmemVariableCache->nextXid may be used (but GetNewTransactionId() must be called first). 3. vacuum.c: change elog(ERROR, "Child item....") to elog(NOTICE) - this is not ERROR, proper handling is just not implemented, yet. 4. s_lock.c: increase S_MAX_BUSY by 2 times. 5. shmem.c:GetSnapshotData(): have to call ReadNewTransactionId() _after_ SpinAcquire(ShmemIndexLock).
This commit is contained in:
parent
48c1887964
commit
1b812d9358
|
@ -7,7 +7,7 @@
|
||||||
*
|
*
|
||||||
*
|
*
|
||||||
* IDENTIFICATION
|
* IDENTIFICATION
|
||||||
* $Header: /cvsroot/pgsql/src/backend/access/transam/varsup.c,v 1.21 1999/06/03 04:41:40 vadim Exp $
|
* $Header: /cvsroot/pgsql/src/backend/access/transam/varsup.c,v 1.22 1999/06/06 20:19:33 vadim Exp $
|
||||||
*
|
*
|
||||||
*-------------------------------------------------------------------------
|
*-------------------------------------------------------------------------
|
||||||
*/
|
*/
|
||||||
|
@ -335,16 +335,13 @@ ReadNewTransactionId(TransactionId *xid)
|
||||||
|
|
||||||
SpinAcquire(OidGenLockId); /* not good for concurrency... */
|
SpinAcquire(OidGenLockId); /* not good for concurrency... */
|
||||||
|
|
||||||
if (ShmemVariableCache->xid_count == 0)
|
/*
|
||||||
{
|
* Note that we don't check is ShmemVariableCache->xid_count equal
|
||||||
TransactionId nextid;
|
* to 0 or not. This will work as long as we don't call
|
||||||
|
* ReadNewTransactionId() before GetNewTransactionId().
|
||||||
VariableRelationGetNextXid(&nextid);
|
*/
|
||||||
TransactionIdStore(nextid, &(ShmemVariableCache->nextXid));
|
if (ShmemVariableCache->nextXid == 0)
|
||||||
ShmemVariableCache->xid_count = VAR_XID_PREFETCH;
|
elog(ERROR, "ReadNewTransactionId: ShmemVariableCache->nextXid is not initialized");
|
||||||
TransactionIdAdd(&nextid, VAR_XID_PREFETCH);
|
|
||||||
VariableRelationPutNextXid(nextid);
|
|
||||||
}
|
|
||||||
|
|
||||||
TransactionIdStore(ShmemVariableCache->nextXid, xid);
|
TransactionIdStore(ShmemVariableCache->nextXid, xid);
|
||||||
|
|
||||||
|
|
|
@ -7,7 +7,7 @@
|
||||||
*
|
*
|
||||||
*
|
*
|
||||||
* IDENTIFICATION
|
* IDENTIFICATION
|
||||||
* $Header: /cvsroot/pgsql/src/backend/access/transam/xact.c,v 1.39 1999/06/03 13:33:12 vadim Exp $
|
* $Header: /cvsroot/pgsql/src/backend/access/transam/xact.c,v 1.40 1999/06/06 20:19:34 vadim Exp $
|
||||||
*
|
*
|
||||||
* NOTES
|
* NOTES
|
||||||
* Transaction aborts can now occur two ways:
|
* Transaction aborts can now occur two ways:
|
||||||
|
@ -942,15 +942,11 @@ CommitTransaction()
|
||||||
/*
|
/*
|
||||||
* Let others know about no transaction in progress by me.
|
* Let others know about no transaction in progress by me.
|
||||||
* Note that this must be done _before_ releasing locks we hold
|
* Note that this must be done _before_ releasing locks we hold
|
||||||
* and SpinAcquire(ShmemIndexLock) is required - or bad (too high)
|
* and SpinAcquire(ShmemIndexLock) is required: UPDATE with xid 0 is
|
||||||
* XmaxRecent value might be used by vacuum: UPDATE with xid 0 is
|
|
||||||
* blocked by xid 1' UPDATE, xid 1 is doing commit while xid 2
|
* blocked by xid 1' UPDATE, xid 1 is doing commit while xid 2
|
||||||
* gets snapshot - if xid 2' GetSnapshotData sees xid 1 as running
|
* gets snapshot - if xid 2' GetSnapshotData sees xid 1 as running
|
||||||
* then it must see xid 0 as running as well or XmaxRecent = 1
|
* then it must see xid 0 as running as well or it will see two
|
||||||
* might be used by concurrent vacuum causing
|
* tuple versions - one deleted by xid 1 and one inserted by xid 0.
|
||||||
* ERROR: Child itemid marked as unused
|
|
||||||
* This bug was reported by Hiroshi Inoue and I was able to reproduce
|
|
||||||
* it with 3 sessions and gdb. - vadim 06/03/99
|
|
||||||
*/
|
*/
|
||||||
if (MyProc != (PROC *) NULL)
|
if (MyProc != (PROC *) NULL)
|
||||||
{
|
{
|
||||||
|
|
|
@ -7,7 +7,7 @@
|
||||||
*
|
*
|
||||||
*
|
*
|
||||||
* IDENTIFICATION
|
* IDENTIFICATION
|
||||||
* $Header: /cvsroot/pgsql/src/backend/commands/vacuum.c,v 1.106 1999/06/03 13:25:54 vadim Exp $
|
* $Header: /cvsroot/pgsql/src/backend/commands/vacuum.c,v 1.107 1999/06/06 20:19:34 vadim Exp $
|
||||||
*
|
*
|
||||||
*-------------------------------------------------------------------------
|
*-------------------------------------------------------------------------
|
||||||
*/
|
*/
|
||||||
|
@ -1238,11 +1238,28 @@ vc_rpfheap(VRelStats *vacrelstats, Relation onerel,
|
||||||
Citemid = PageGetItemId(Cpage,
|
Citemid = PageGetItemId(Cpage,
|
||||||
ItemPointerGetOffsetNumber(&Ctid));
|
ItemPointerGetOffsetNumber(&Ctid));
|
||||||
if (!ItemIdIsUsed(Citemid))
|
if (!ItemIdIsUsed(Citemid))
|
||||||
elog(ERROR, "Child itemid marked as unused");
|
{
|
||||||
|
/*
|
||||||
|
* This means that in the middle of chain there was
|
||||||
|
* tuple updated by older (than XmaxRecent) xaction
|
||||||
|
* and this tuple is already deleted by me. Actually,
|
||||||
|
* upper part of chain should be removed and seems
|
||||||
|
* that this should be handled in vc_scanheap(), but
|
||||||
|
* it's not implemented at the moment and so we
|
||||||
|
* just stop shrinking here.
|
||||||
|
*/
|
||||||
|
ReleaseBuffer(Cbuf);
|
||||||
|
pfree(vtmove);
|
||||||
|
vtmove = NULL;
|
||||||
|
elog(NOTICE, "Child itemid in update-chain marked as unused - can't continue vc_rpfheap");
|
||||||
|
break;
|
||||||
|
}
|
||||||
tp.t_data = (HeapTupleHeader) PageGetItem(Cpage, Citemid);
|
tp.t_data = (HeapTupleHeader) PageGetItem(Cpage, Citemid);
|
||||||
tp.t_self = Ctid;
|
tp.t_self = Ctid;
|
||||||
tlen = tp.t_len = ItemIdGetLength(Citemid);
|
tlen = tp.t_len = ItemIdGetLength(Citemid);
|
||||||
}
|
}
|
||||||
|
if (vtmove == NULL)
|
||||||
|
break;
|
||||||
/* first, can chain be moved ? */
|
/* first, can chain be moved ? */
|
||||||
for (;;)
|
for (;;)
|
||||||
{
|
{
|
||||||
|
@ -1336,6 +1353,7 @@ vc_rpfheap(VRelStats *vacrelstats, Relation onerel,
|
||||||
Ptp.t_data = (HeapTupleHeader) PageGetItem(Ppage, Pitemid);
|
Ptp.t_data = (HeapTupleHeader) PageGetItem(Ppage, Pitemid);
|
||||||
Assert(Ptp.t_data->t_xmax == tp.t_data->t_xmin);
|
Assert(Ptp.t_data->t_xmax == tp.t_data->t_xmin);
|
||||||
|
|
||||||
|
#ifdef NOT_USED /* I'm not sure that this will wotk properly... */
|
||||||
/*
|
/*
|
||||||
* If this tuple is updated version of row and it
|
* If this tuple is updated version of row and it
|
||||||
* was created by the same transaction then no one
|
* was created by the same transaction then no one
|
||||||
|
@ -1353,6 +1371,7 @@ vc_rpfheap(VRelStats *vacrelstats, Relation onerel,
|
||||||
WriteBuffer(Pbuf);
|
WriteBuffer(Pbuf);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
tp.t_data = Ptp.t_data;
|
tp.t_data = Ptp.t_data;
|
||||||
tlen = tp.t_len = ItemIdGetLength(Pitemid);
|
tlen = tp.t_len = ItemIdGetLength(Pitemid);
|
||||||
if (freeCbuf)
|
if (freeCbuf)
|
||||||
|
@ -1763,7 +1782,7 @@ Elapsed %u/%u sec.",
|
||||||
page = BufferGetPage(buf);
|
page = BufferGetPage(buf);
|
||||||
num_tuples = 0;
|
num_tuples = 0;
|
||||||
for (offnum = FirstOffsetNumber;
|
for (offnum = FirstOffsetNumber;
|
||||||
offnum < maxoff;
|
offnum <= maxoff;
|
||||||
offnum = OffsetNumberNext(offnum))
|
offnum = OffsetNumberNext(offnum))
|
||||||
{
|
{
|
||||||
itemid = PageGetItemId(page, offnum);
|
itemid = PageGetItemId(page, offnum);
|
||||||
|
|
|
@ -7,7 +7,7 @@
|
||||||
*
|
*
|
||||||
*
|
*
|
||||||
* IDENTIFICATION
|
* IDENTIFICATION
|
||||||
* $Header: /cvsroot/pgsql/src/backend/storage/buffer/Attic/s_lock.c,v 1.20 1999/05/25 22:04:32 momjian Exp $
|
* $Header: /cvsroot/pgsql/src/backend/storage/buffer/Attic/s_lock.c,v 1.21 1999/06/06 20:19:35 vadim Exp $
|
||||||
*
|
*
|
||||||
*-------------------------------------------------------------------------
|
*-------------------------------------------------------------------------
|
||||||
*/
|
*/
|
||||||
|
@ -28,7 +28,7 @@
|
||||||
* note: total time to cycle through all 16 entries might be about .07 sec.
|
* note: total time to cycle through all 16 entries might be about .07 sec.
|
||||||
*/
|
*/
|
||||||
#define S_NSPINCYCLE 20
|
#define S_NSPINCYCLE 20
|
||||||
#define S_MAX_BUSY 500 * S_NSPINCYCLE
|
#define S_MAX_BUSY 1000 * S_NSPINCYCLE
|
||||||
|
|
||||||
int s_spincycle[S_NSPINCYCLE] =
|
int s_spincycle[S_NSPINCYCLE] =
|
||||||
{0, 0, 0, 0, 10000, 0, 0, 0, 10000, 0,
|
{0, 0, 0, 0, 10000, 0, 0, 0, 10000, 0,
|
||||||
|
|
|
@ -7,7 +7,7 @@
|
||||||
*
|
*
|
||||||
*
|
*
|
||||||
* IDENTIFICATION
|
* IDENTIFICATION
|
||||||
* $Header: /cvsroot/pgsql/src/backend/storage/ipc/shmem.c,v 1.41 1999/06/03 13:33:13 vadim Exp $
|
* $Header: /cvsroot/pgsql/src/backend/storage/ipc/shmem.c,v 1.42 1999/06/06 20:19:35 vadim Exp $
|
||||||
*
|
*
|
||||||
*-------------------------------------------------------------------------
|
*-------------------------------------------------------------------------
|
||||||
*/
|
*/
|
||||||
|
@ -652,9 +652,15 @@ GetSnapshotData(bool serializable)
|
||||||
|
|
||||||
snapshot->xip = (TransactionId *) malloc(have * sizeof(TransactionId));
|
snapshot->xip = (TransactionId *) malloc(have * sizeof(TransactionId));
|
||||||
snapshot->xmin = cid;
|
snapshot->xmin = cid;
|
||||||
ReadNewTransactionId(&(snapshot->xmax));
|
|
||||||
|
|
||||||
SpinAcquire(ShmemIndexLock);
|
SpinAcquire(ShmemIndexLock);
|
||||||
|
/*
|
||||||
|
* Unfortunately, we have to call ReadNewTransactionId()
|
||||||
|
* after acquiring ShmemIndexLock above. It's not good because of
|
||||||
|
* ReadNewTransactionId() does SpinAcquire(OidGenLockId) but
|
||||||
|
* _necessary_.
|
||||||
|
*/
|
||||||
|
ReadNewTransactionId(&(snapshot->xmax));
|
||||||
|
|
||||||
hash_seq((HTAB *) NULL);
|
hash_seq((HTAB *) NULL);
|
||||||
while ((result = (ShmemIndexEnt *) hash_seq(ShmemIndex)) != NULL)
|
while ((result = (ShmemIndexEnt *) hash_seq(ShmemIndex)) != NULL)
|
||||||
|
|
Loading…
Reference in New Issue