summaryrefslogtreecommitdiff
path: root/src/backend/access/transam/xact.c
diff options
context:
space:
mode:
authorTom Lane <tgl@sss.pgh.pa.us>2010-01-24 21:49:39 +0000
committerTom Lane <tgl@sss.pgh.pa.us>2010-01-24 21:49:39 +0000
commit7309f3340c46bdb8109e0465becbc078b1e1858a (patch)
tree93ab7462a25c2fa10eedf38d2a46221ed9fc3479 /src/backend/access/transam/xact.c
parent61da9c4e2520b3ec4735c8eee1c3adbe9c697ca2 (diff)
Fix assorted core dumps and Assert failures that could occur during
AbortTransaction or AbortSubTransaction, when trying to clean up after an error that prevented (sub)transaction start from completing: * access to TopTransactionResourceOwner that might not exist * assert failure in AtEOXact_GUC, if AtStart_GUC not called yet * assert failure or core dump in AfterTriggerEndSubXact, if AfterTriggerBeginSubXact not called yet Per testing by injecting elog(ERROR) at successive steps in StartTransaction and StartSubTransaction. It's not clear whether all of these cases could really occur in the field, but at least one of them is easily exposed by simple stress testing, as per my accidental discovery yesterday.
Diffstat (limited to 'src/backend/access/transam/xact.c')
-rw-r--r--src/backend/access/transam/xact.c63
1 files changed, 33 insertions, 30 deletions
diff --git a/src/backend/access/transam/xact.c b/src/backend/access/transam/xact.c
index 2c440ca1fac..cc38c6ff131 100644
--- a/src/backend/access/transam/xact.c
+++ b/src/backend/access/transam/xact.c
@@ -10,7 +10,7 @@
*
*
* IDENTIFICATION
- * $PostgreSQL: pgsql/src/backend/access/transam/xact.c,v 1.257.2.5 2009/12/09 21:58:16 tgl Exp $
+ * $PostgreSQL: pgsql/src/backend/access/transam/xact.c,v 1.257.2.6 2010/01/24 21:49:39 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -2097,38 +2097,41 @@ AbortTransaction(void)
/*
* Post-abort cleanup. See notes in CommitTransaction() concerning
- * ordering.
+ * ordering. We can skip all of it if the transaction failed before
+ * creating a resource owner.
*/
+ if (TopTransactionResourceOwner != NULL)
+ {
+ CallXactCallbacks(XACT_EVENT_ABORT);
- CallXactCallbacks(XACT_EVENT_ABORT);
-
- ResourceOwnerRelease(TopTransactionResourceOwner,
- RESOURCE_RELEASE_BEFORE_LOCKS,
- false, true);
- AtEOXact_Buffers(false);
- AtEOXact_RelationCache(false);
- AtEOXact_Inval(false);
- smgrDoPendingDeletes(false);
- AtEOXact_MultiXact();
- ResourceOwnerRelease(TopTransactionResourceOwner,
- RESOURCE_RELEASE_LOCKS,
- false, true);
- ResourceOwnerRelease(TopTransactionResourceOwner,
- RESOURCE_RELEASE_AFTER_LOCKS,
- false, true);
- AtEOXact_CatCache(false);
+ ResourceOwnerRelease(TopTransactionResourceOwner,
+ RESOURCE_RELEASE_BEFORE_LOCKS,
+ false, true);
+ AtEOXact_Buffers(false);
+ AtEOXact_RelationCache(false);
+ AtEOXact_Inval(false);
+ smgrDoPendingDeletes(false);
+ AtEOXact_MultiXact();
+ ResourceOwnerRelease(TopTransactionResourceOwner,
+ RESOURCE_RELEASE_LOCKS,
+ false, true);
+ ResourceOwnerRelease(TopTransactionResourceOwner,
+ RESOURCE_RELEASE_AFTER_LOCKS,
+ false, true);
+ AtEOXact_CatCache(false);
- AtEOXact_GUC(false, 1);
- AtEOXact_SPI(false);
- AtEOXact_xml();
- AtEOXact_on_commit_actions(false);
- AtEOXact_Namespace(false);
- smgrabort();
- AtEOXact_Files();
- AtEOXact_ComboCid();
- AtEOXact_HashTables(false);
- AtEOXact_PgStat(false);
- pgstat_report_xact_timestamp(0);
+ AtEOXact_GUC(false, 1);
+ AtEOXact_SPI(false);
+ AtEOXact_xml();
+ AtEOXact_on_commit_actions(false);
+ AtEOXact_Namespace(false);
+ smgrabort();
+ AtEOXact_Files();
+ AtEOXact_ComboCid();
+ AtEOXact_HashTables(false);
+ AtEOXact_PgStat(false);
+ pgstat_report_xact_timestamp(0);
+ }
/*
* State remains TRANS_ABORT until CleanupTransaction().