aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorAmit Kapila <akapila@postgresql.org>2021-06-28 08:42:48 +0530
committerAmit Kapila <akapila@postgresql.org>2021-06-28 08:42:48 +0530
commit741deb2603c758c67f199c9129d2e92bd80cec2e (patch)
treee8a859fce2d94a1121c8860d0e65454623218376 /src
parentfd7bc10ab4c6a88846d1b8a35d16cfe0b8f5a487 (diff)
downloadpostgresql-741deb2603c758c67f199c9129d2e92bd80cec2e.tar.gz
postgresql-741deb2603c758c67f199c9129d2e92bd80cec2e.zip
Fix race condition in TransactionGroupUpdateXidStatus().
When we cannot immediately acquire XactSLRULock in exclusive mode at commit time, we add ourselves to a list of processes that need their XIDs status update. We do this if the clog page where we need to update the current transaction status is the same as the group leader's clog page, otherwise, we allow the caller to clear it by itself. Now, when we can't add ourselves to any group, we were not clearing the current proc if it has already become a member of some group which was leading to an assertion failure when the same proc was assigned to another backend after the current backend exits. Reported-by: Alexander Lakhin Bug: 17072 Author: Amit Kapila Tested-By: Alexander Lakhin Backpatch-through: 11, where it was introduced Discussion: https://postgr.es/m/17072-2f8764857ef2c92a@postgresql.org
Diffstat (limited to 'src')
-rw-r--r--src/backend/access/transam/clog.c5
1 files changed, 5 insertions, 0 deletions
diff --git a/src/backend/access/transam/clog.c b/src/backend/access/transam/clog.c
index 5d6e088e8bd..40170b868ba 100644
--- a/src/backend/access/transam/clog.c
+++ b/src/backend/access/transam/clog.c
@@ -450,7 +450,12 @@ TransactionGroupUpdateXidStatus(TransactionId xid, XidStatus status,
if (nextidx != INVALID_PGPROCNO &&
ProcGlobal->allProcs[nextidx].clogGroupMemberPage != proc->clogGroupMemberPage)
{
+ /*
+ * Ensure that this proc is not a member of any clog group that
+ * needs an XID status update.
+ */
proc->clogGroupMember = false;
+ pg_atomic_write_u32(&proc->clogGroupNext, INVALID_PGPROCNO);
return false;
}