From 646b12115a81604fe083d555441d50c8967cee5f Mon Sep 17 00:00:00 2001 From: Alvaro Herrera Date: Fri, 2 Aug 2013 14:34:56 -0400 Subject: [PATCH] Fix old visibility bug in HeapTupleSatisfiesDirty If a tuple is locked but not updated by a concurrent transaction, HeapTupleSatisfiesDirty would return that transaction's Xid in xmax, causing callers to wait on it, when it is not necessary (in fact, if the other transaction had used a multixact instead of a plain Xid to mark the tuple, HeapTupleSatisfiesDirty would have behave differently and *not* returned the Xmax). This bug was introduced in commit 3f7fbf85dc5b42, dated December 1998, so it's almost 15 years old now. However, it's hard to see this misbehave, because before we had NOWAIT the only consequence of this is that transactions would wait for slightly more time than necessary; so it's not surprising that this hasn't been reported yet. Craig Ringer and Andres Freund --- src/backend/utils/time/tqual.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/backend/utils/time/tqual.c b/src/backend/utils/time/tqual.c index 96e480bc07..52d42e5614 100644 --- a/src/backend/utils/time/tqual.c +++ b/src/backend/utils/time/tqual.c @@ -861,7 +861,8 @@ HeapTupleSatisfiesDirty(HeapTupleHeader tuple, Snapshot snapshot, if (TransactionIdIsInProgress(HeapTupleHeaderGetXmax(tuple))) { - snapshot->xmax = HeapTupleHeaderGetXmax(tuple); + if (!(tuple->t_infomask & HEAP_IS_LOCKED)) + snapshot->xmax = HeapTupleHeaderGetXmax(tuple); return true; }