From: | Tom Lane <tgl(at)sss(dot)pgh(dot)pa(dot)us> |
---|---|
To: | pgsql-committers(at)lists(dot)postgresql(dot)org |
Subject: | pgsql: Fix tupdesc lifespan bug with AfterTriggersTableData.storeslot. |
Date: | 2022-09-25 21:11:14 |
Message-ID: | E1ocYuA-001zuD-96@gemulon.postgresql.org |
Views: | Raw Message | Whole Thread | Download mbox | Resend email |
Thread: | |
Lists: | pgsql-committers |
Fix tupdesc lifespan bug with AfterTriggersTableData.storeslot.
Commit 25936fd46 adjusted things so that the "storeslot" we use
for remapping trigger tuples would have adequate lifespan, but it
neglected to consider the lifespan of the tuple descriptor that
the slot depends on. It turns out that in at least some cases, the
tupdesc we are passing is a refcounted tupdesc, and the refcount for
the slot's reference can get assigned to a resource owner having
different lifespan than the slot does. That leads to an error like
"tupdesc reference 0x7fdef236a1b8 is not owned by resource owner
SubTransaction". Worse, because of a second oversight in the same
commit, we'd try to free the same tupdesc refcount again while
cleaning up after that error, leading to recursive errors and an
"ERRORDATA_STACK_SIZE exceeded" PANIC.
To fix the initial problem, let's just make a non-refcounted copy
of the tupdesc we're supposed to use. That seems likely to guard
against additional problems, since there's no strong reason for
this code to assume that what it's given is a refcounted tupdesc;
in which case there's an independent hazard of the tupdesc having
shorter lifespan than the slot does. (I didn't bother trying to
free said copy, since it should go away anyway when the (sub)
transaction context is cleaned up.)
The other issue can be fixed by making the code added to
AfterTriggerFreeQuery work like the rest of that function, ie be
sure that it doesn't try to free the same slot twice in the event
of recursive error cleanup.
While here, also clean up minor stylistic issues in the test case
added by 25936fd46: don't use "create or replace function", as any
name collision within the tests is likely to have ill effects
that that won't mask; and don't use function names as generic as
trigger_function1, especially if you're not going to drop them
at the end of the test stanza.
Per bug #17607 from Thomas Mc Kay. Back-patch to v12, as the
previous fix was.
Discussion: https://postgr.es/m/17607-bd8ccc81226f7f80@postgresql.org
Branch
------
REL_12_STABLE
Details
-------
https://git.postgresql.org/pg/commitdiff/51976309450c58e79b46015223888db8f5c8159f
Modified Files
--------------
src/backend/commands/trigger.c | 15 +++++++++---
src/test/regress/expected/triggers.out | 38 +++++++++++++++++++++++-----
src/test/regress/sql/triggers.sql | 45 +++++++++++++++++++++++++++++-----
3 files changed, 82 insertions(+), 16 deletions(-)
From | Date | Subject | |
---|---|---|---|
Next Message | Michael Paquier | 2022-09-26 02:19:52 | pgsql: Refactor creation of backup_label and backup history files |
Previous Message | Tom Lane | 2022-09-25 17:10:26 | pgsql: Avoid loss of code coverage with unlogged-index test cases. |