Skip to content

Commit d2fd7f7

Browse files
committed
Fix off-by-one error in txid_status().
The transaction ID returned by GetNextXidAndEpoch() is in the future, so we can't attempt to access its status or we might try to read a CLOG page that doesn't exist. The > vs >= confusion probably stemmed from the choice of a variable name containing the word "last" instead of "next", so fix that too. Back-patch to 10 where the function arrived. Author: Thomas Munro Discussion: https://postgr.es/m/CA%2BhUKG%2Buua_BV5cyfsioKVN2d61Lukg28ECsWTXKvh%3DBtN2DPA%40mail.gmail.com
1 parent 1983af8 commit d2fd7f7

File tree

1 file changed

+4
-4
lines changed

1 file changed

+4
-4
lines changed

src/backend/utils/adt/txid.c

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -113,9 +113,9 @@ TransactionIdInRecentPast(uint64 xid_with_epoch, TransactionId *extracted_xid)
113113
uint32 xid_epoch = (uint32) (xid_with_epoch >> 32);
114114
TransactionId xid = (TransactionId) xid_with_epoch;
115115
uint32 now_epoch;
116-
TransactionId now_epoch_last_xid;
116+
TransactionId now_epoch_next_xid;
117117

118-
GetNextXidAndEpoch(&now_epoch_last_xid, &now_epoch);
118+
GetNextXidAndEpoch(&now_epoch_next_xid, &now_epoch);
119119

120120
if (extracted_xid != NULL)
121121
*extracted_xid = xid;
@@ -129,7 +129,7 @@ TransactionIdInRecentPast(uint64 xid_with_epoch, TransactionId *extracted_xid)
129129

130130
/* If the transaction ID is in the future, throw an error. */
131131
if (xid_epoch > now_epoch
132-
|| (xid_epoch == now_epoch && xid > now_epoch_last_xid))
132+
|| (xid_epoch == now_epoch && xid >= now_epoch_next_xid))
133133
ereport(ERROR,
134134
(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
135135
errmsg("transaction ID %s is in the future",
@@ -151,7 +151,7 @@ TransactionIdInRecentPast(uint64 xid_with_epoch, TransactionId *extracted_xid)
151151
* CLOG entry is guaranteed to still exist.
152152
*/
153153
if (xid_epoch + 1 < now_epoch
154-
|| (xid_epoch + 1 == now_epoch && xid < now_epoch_last_xid)
154+
|| (xid_epoch + 1 == now_epoch && xid < now_epoch_next_xid)
155155
|| TransactionIdPrecedes(xid, ShmemVariableCache->oldestClogXid))
156156
return false;
157157

0 commit comments

Comments
 (0)