diff options
Diffstat (limited to 'src/backend/utils/adt')
-rw-r--r-- | src/backend/utils/adt/ri_triggers.c | 58 | ||||
-rw-r--r-- | src/backend/utils/adt/ruleutils.c | 6 |
2 files changed, 38 insertions, 26 deletions
diff --git a/src/backend/utils/adt/ri_triggers.c b/src/backend/utils/adt/ri_triggers.c index 9c32d57c111..20ad56c31f1 100644 --- a/src/backend/utils/adt/ri_triggers.c +++ b/src/backend/utils/adt/ri_triggers.c @@ -17,7 +17,7 @@ * * Portions Copyright (c) 1996-2004, PostgreSQL Global Development Group * - * $PostgreSQL: pgsql/src/backend/utils/adt/ri_triggers.c,v 1.72 2004/09/10 18:40:04 tgl Exp $ + * $PostgreSQL: pgsql/src/backend/utils/adt/ri_triggers.c,v 1.73 2004/09/13 20:07:13 tgl Exp $ * * ---------- */ @@ -2698,16 +2698,20 @@ RI_Initial_Check(FkConstraint *fkconstraint, Relation rel, Relation pkrel) elog(ERROR, "SPI_prepare returned %d for %s", SPI_result, querystr); /* - * Run the plan. For safety we force a current query snapshot to be - * used. (In serializable mode, this arguably violates - * serializability, but we really haven't got much choice.) We need - * at most one tuple returned, so pass limit = 1. + * Run the plan. For safety we force a current snapshot to be used. + * (In serializable mode, this arguably violates serializability, but we + * really haven't got much choice.) We need at most one tuple returned, + * so pass limit = 1. */ - spi_result = SPI_execp_current(qplan, NULL, NULL, true, 1); + spi_result = SPI_execute_snapshot(qplan, + NULL, NULL, + CopySnapshot(GetLatestSnapshot()), + InvalidSnapshot, + true, 1); /* Check result */ if (spi_result != SPI_OK_SELECT) - elog(ERROR, "SPI_execp_current returned %d", spi_result); + elog(ERROR, "SPI_execute_snapshot returned %d", spi_result); /* Did we find a tuple violating the constraint? */ if (SPI_processed > 0) @@ -3043,7 +3047,8 @@ ri_PerformCheck(RI_QueryKey *qkey, void *qplan, Relation query_rel, source_rel; int key_idx; - bool useCurrentSnapshot; + Snapshot test_snapshot; + Snapshot crosscheck_snapshot; int limit; int spi_result; AclId save_uid; @@ -3094,21 +3099,26 @@ ri_PerformCheck(RI_QueryKey *qkey, void *qplan, } /* - * In READ COMMITTED mode, we just need to make sure the regular query - * snapshot is up-to-date, and we will see all rows that could be - * interesting. In SERIALIZABLE mode, we can't update the regular - * query snapshot. If the caller passes detectNewRows == false then - * it's okay to do the query with the transaction snapshot; otherwise - * we tell the executor to force a current snapshot (and error out if - * it finds any rows under current snapshot that wouldn't be visible - * per the transaction snapshot). + * In READ COMMITTED mode, we just need to use an up-to-date regular + * snapshot, and we will see all rows that could be interesting. + * But in SERIALIZABLE mode, we can't change the transaction snapshot. + * If the caller passes detectNewRows == false then it's okay to do the + * query with the transaction snapshot; otherwise we use a current + * snapshot, and tell the executor to error out if it finds any rows under + * the current snapshot that wouldn't be visible per the transaction + * snapshot. */ - if (IsXactIsoLevelSerializable) - useCurrentSnapshot = detectNewRows; + if (IsXactIsoLevelSerializable && detectNewRows) + { + CommandCounterIncrement(); /* be sure all my own work is visible */ + test_snapshot = CopySnapshot(GetLatestSnapshot()); + crosscheck_snapshot = CopySnapshot(GetTransactionSnapshot()); + } else { - SetQuerySnapshot(); - useCurrentSnapshot = false; + /* the default SPI behavior is okay */ + test_snapshot = InvalidSnapshot; + crosscheck_snapshot = InvalidSnapshot; } /* @@ -3124,15 +3134,17 @@ ri_PerformCheck(RI_QueryKey *qkey, void *qplan, SetUserId(RelationGetForm(query_rel)->relowner); /* Finally we can run the query. */ - spi_result = SPI_execp_current(qplan, vals, nulls, - useCurrentSnapshot, limit); + spi_result = SPI_execute_snapshot(qplan, + vals, nulls, + test_snapshot, crosscheck_snapshot, + false, limit); /* Restore UID */ SetUserId(save_uid); /* Check result */ if (spi_result < 0) - elog(ERROR, "SPI_execp_current returned %d", spi_result); + elog(ERROR, "SPI_execute_snapshot returned %d", spi_result); if (expect_OK >= 0 && spi_result != expect_OK) ri_ReportViolation(qkey, constrname ? constrname : "", diff --git a/src/backend/utils/adt/ruleutils.c b/src/backend/utils/adt/ruleutils.c index af859222c36..89a9e2451dd 100644 --- a/src/backend/utils/adt/ruleutils.c +++ b/src/backend/utils/adt/ruleutils.c @@ -3,7 +3,7 @@ * back to source text * * IDENTIFICATION - * $PostgreSQL: pgsql/src/backend/utils/adt/ruleutils.c,v 1.180 2004/09/01 23:58:38 tgl Exp $ + * $PostgreSQL: pgsql/src/backend/utils/adt/ruleutils.c,v 1.181 2004/09/13 20:07:13 tgl Exp $ * * This software is copyrighted by Jan Wieck - Hamburg. * @@ -290,7 +290,7 @@ pg_get_ruledef_worker(Oid ruleoid, int prettyFlags) */ args[0] = ObjectIdGetDatum(ruleoid); nulls[0] = ' '; - spirc = SPI_execp(plan_getrulebyoid, args, nulls, 1); + spirc = SPI_execute_plan(plan_getrulebyoid, args, nulls, true, 1); if (spirc != SPI_OK_SELECT) elog(ERROR, "failed to get pg_rewrite tuple for rule %u", ruleoid); if (SPI_processed != 1) @@ -425,7 +425,7 @@ pg_get_viewdef_worker(Oid viewoid, int prettyFlags) args[1] = PointerGetDatum(ViewSelectRuleName); nulls[0] = ' '; nulls[1] = ' '; - spirc = SPI_execp(plan_getviewrule, args, nulls, 2); + spirc = SPI_execute_plan(plan_getviewrule, args, nulls, true, 2); if (spirc != SPI_OK_SELECT) elog(ERROR, "failed to get pg_rewrite tuple for view %u", viewoid); if (SPI_processed != 1) |