diff --git a/src/backend/storage/lmgr/predicate.c b/src/backend/storage/lmgr/predicate.c index 49de95a5dbbdd..f0d1a6e5b5f0c 100644 --- a/src/backend/storage/lmgr/predicate.c +++ b/src/backend/storage/lmgr/predicate.c @@ -1821,24 +1821,6 @@ GetSerializableTransactionSnapshotInt(Snapshot snapshot, return snapshot; } - /* Maintain serializable global xmin info. */ - if (!TransactionIdIsValid(PredXact->SxactGlobalXmin)) - { - Assert(PredXact->SxactGlobalXminCount == 0); - PredXact->SxactGlobalXmin = snapshot->xmin; - PredXact->SxactGlobalXminCount = 1; - OldSerXidSetActiveSerXmin(snapshot->xmin); - } - else if (TransactionIdEquals(snapshot->xmin, PredXact->SxactGlobalXmin)) - { - Assert(PredXact->SxactGlobalXminCount > 0); - PredXact->SxactGlobalXminCount++; - } - else - { - Assert(TransactionIdFollows(snapshot->xmin, PredXact->SxactGlobalXmin)); - } - /* Initialize the structure. */ sxact->vxid = vxid; sxact->SeqNo.lastCommitBeforeSnapshot = PredXact->LastSxactCommitSeqNo; @@ -1875,6 +1857,19 @@ GetSerializableTransactionSnapshotInt(Snapshot snapshot, SetPossibleUnsafeConflict(sxact, othersxact); } } + + /* + * If we didn't find any possibly unsafe conflicts because every + * uncommitted writable transaction turned out to be doomed, then we + * can "opt out" immediately. See comments above the earlier check for + * PredXact->WritableSxactCount == 0. + */ + if (SHMQueueEmpty(&sxact->possibleUnsafeConflicts)) + { + ReleasePredXact(sxact); + LWLockRelease(SerializableXactHashLock); + return snapshot; + } } else { @@ -1883,6 +1878,24 @@ GetSerializableTransactionSnapshotInt(Snapshot snapshot, (MaxBackends + max_prepared_xacts)); } + /* Maintain serializable global xmin info. */ + if (!TransactionIdIsValid(PredXact->SxactGlobalXmin)) + { + Assert(PredXact->SxactGlobalXminCount == 0); + PredXact->SxactGlobalXmin = snapshot->xmin; + PredXact->SxactGlobalXminCount = 1; + OldSerXidSetActiveSerXmin(snapshot->xmin); + } + else if (TransactionIdEquals(snapshot->xmin, PredXact->SxactGlobalXmin)) + { + Assert(PredXact->SxactGlobalXminCount > 0); + PredXact->SxactGlobalXminCount++; + } + else + { + Assert(TransactionIdFollows(snapshot->xmin, PredXact->SxactGlobalXmin)); + } + MySerializableXact = sxact; MyXactDidWrite = false; /* haven't written anything yet */