diff options
Diffstat (limited to 'src/backend/executor/nodeModifyTable.c')
-rw-r--r-- | src/backend/executor/nodeModifyTable.c | 26 |
1 files changed, 17 insertions, 9 deletions
diff --git a/src/backend/executor/nodeModifyTable.c b/src/backend/executor/nodeModifyTable.c index c0eab4bf0db..cb64cfc857a 100644 --- a/src/backend/executor/nodeModifyTable.c +++ b/src/backend/executor/nodeModifyTable.c @@ -715,6 +715,18 @@ ExecModifyTable(ModifyTableState *node) HeapTupleHeader oldtuple = NULL; /* + * This should NOT get called during EvalPlanQual; we should have passed a + * subplan tree to EvalPlanQual, instead. Use a runtime test not just + * Assert because this condition is easy to miss in testing. (Note: + * although ModifyTable should not get executed within an EvalPlanQual + * operation, we do have to allow it to be initialized and shut down in + * case it is within a CTE subplan. Hence this test must be here, not in + * ExecInitModifyTable.) + */ + if (estate->es_epqTuple != NULL) + elog(ERROR, "ModifyTable should not be called during EvalPlanQual"); + + /* * If we've already completed processing, don't try to do more. We need * this test because ExecPostprocessPlan might call us an extra time, and * our subplan's nodes aren't necessarily robust against being called @@ -892,14 +904,6 @@ ExecInitModifyTable(ModifyTable *node, EState *estate, int eflags) Assert(!(eflags & (EXEC_FLAG_BACKWARD | EXEC_FLAG_MARK))); /* - * This should NOT get called during EvalPlanQual; we should have passed a - * subplan tree to EvalPlanQual, instead. Use a runtime test not just - * Assert because this condition is easy to miss in testing ... - */ - if (estate->es_epqTuple != NULL) - elog(ERROR, "ModifyTable should not be called during EvalPlanQual"); - - /* * create state structure */ mtstate = makeNode(ModifyTableState); @@ -946,9 +950,13 @@ ExecInitModifyTable(ModifyTable *node, EState *estate, int eflags) * descriptors in the result relation info, so that we can add new * index entries for the tuples we add/update. We need not do this * for a DELETE, however, since deletion doesn't affect indexes. + * Also, inside an EvalPlanQual operation, the indexes might be open + * already, since we share the resultrel state with the original + * query. */ if (resultRelInfo->ri_RelationDesc->rd_rel->relhasindex && - operation != CMD_DELETE) + operation != CMD_DELETE && + resultRelInfo->ri_IndexRelationDescs == NULL) ExecOpenIndices(resultRelInfo); /* Now init the plan for this result rel */ |