From df4fe58bda41ef0f033e102568f65d5bb44964cc Mon Sep 17 00:00:00 2001 From: fairyfar Date: Wed, 2 Sep 2026 08:15:18 +0800 Subject: [PATCH] Fix assert failure triggered by "CREATE INDEX CONCURRENTLY" When resource group is enabled, StartTransaction() may take a catalog snapshot while assigning a resource group, leaving a valid xmin in MyProc. That fails the assertion in set_indexsafe_procflags() that the process must not advertise an xmin when running "CREATE INDEX CONCURRENTLY". Fix it at the point the invariant lives: set_indexsafe_procflags() now invalidates any stale catalog snapshot before asserting, so every REINDEX CONCURRENTLY phase clears the xmin ahead of setting PROC_IN_SAFE_IC. --- src/backend/commands/indexcmds.c | 11 +++++++++++ .../expected/resgroup/resgroup_transaction.out | 13 +++++++++++++ .../sql/resgroup/resgroup_transaction.sql | 9 +++++++++ 3 files changed, 33 insertions(+) diff --git a/src/backend/commands/indexcmds.c b/src/backend/commands/indexcmds.c index ba66cf6baff..11beb0664fb 100644 --- a/src/backend/commands/indexcmds.c +++ b/src/backend/commands/indexcmds.c @@ -5444,6 +5444,17 @@ update_relispartition(Oid relationId, bool newval) static inline void set_indexsafe_procflags(void) { + /* + * A catalog snapshot taken earlier in this transaction (for example, by + * resource-group slot assignment during StartTransaction) leaves a valid + * xmin advertised in MyProc. Drop it here so the assertion below holds; + * CREATE INDEX CONCURRENTLY phases must not hold any snapshot at this + * point anyway. + */ + if (MyProc->xid != InvalidTransactionId || + MyProc->xmin != InvalidTransactionId) + InvalidateCatalogSnapshot(); + /* * This should only be called before installing xid or xmin in MyProc; * otherwise, concurrent processes could see an Xmin that moves backwards. diff --git a/src/test/isolation2/expected/resgroup/resgroup_transaction.out b/src/test/isolation2/expected/resgroup/resgroup_transaction.out index baad66ef535..a302f77236f 100644 --- a/src/test/isolation2/expected/resgroup/resgroup_transaction.out +++ b/src/test/isolation2/expected/resgroup/resgroup_transaction.out @@ -237,3 +237,16 @@ DROP -- cleanup DROP VIEW rg_test_monitor; DROP + +-- ---------------------------------------------------------------------- +-- Test: "CREATE INDEX CONCURRENTLY" when compiled with enable-cassert +-- ---------------------------------------------------------------------- + +CREATE TABLE t(a text, b text); +CREATE +CREATE INDEX CONCURRENTLY t_idx ON t(a, b); +CREATE +DROP INDEX CONCURRENTLY t_idx; +DROP +DROP TABLE t; +DROP diff --git a/src/test/isolation2/sql/resgroup/resgroup_transaction.sql b/src/test/isolation2/sql/resgroup/resgroup_transaction.sql index da29d48f208..7ab6f40b33b 100644 --- a/src/test/isolation2/sql/resgroup/resgroup_transaction.sql +++ b/src/test/isolation2/sql/resgroup/resgroup_transaction.sql @@ -134,3 +134,12 @@ DROP FUNCTION rg_drop_func(); -- cleanup DROP VIEW rg_test_monitor; + +-- ---------------------------------------------------------------------- +-- Test: "CREATE INDEX CONCURRENTLY" when compiled with enable-cassert +-- ---------------------------------------------------------------------- + +CREATE TABLE t(a text, b text); +CREATE INDEX CONCURRENTLY t_idx ON t(a, b); +DROP INDEX CONCURRENTLY t_idx; +DROP TABLE t;