Re: BUG #17596: "invalid attribute number 11" when updating partitioned table with a MULTIEXPR_SUBLINK
Tom Lane <tgl@sss.pgh.pa.us>
From: Tom Lane <tgl@sss.pgh.pa.us>
To: 857348270@qq.com
Cc: pgsql-bugs@lists.postgresql.org
Date: 2022-08-26T23:59:06Z
Lists: pgsql-bugs
Attachments
- fix-bug-17596.patch (text/x-diff) patch
PG Bug reporting form <noreply@postgresql.org> writes: > ERROR: XX000: invalid attribute number 11 > LOCATION: slot_getsomeattrs_int, execTuples.c:1909 > I did some investigations. The current implementation, the update plans of > different partitions use the same param id for the subplan param, but they > correspond to different SubPlanStates during execution, SubPlanState are > generated during ExecInitSubPlan and linked to ParamExecData->execPlan. > Since the plans of multiple partitions share one Param, according to the > execution order, the final execPlan will be set to the SubPlanState of the > last partition in the InitPlan phase. > And because the order of joins in different partition plans is different, > the final SubPlanState->args does not match the expectation (some are > OUTER_VAR, some are INNER_VAR), and an error is occurred (failed assertion > if "--enable-cassert" and coredump) Thanks for the report! I find that this bug doesn't reproduce in v14 and up, now that we got rid of inheritance_planner(). It is a live issue before that though, because as you say MULTIEXPR_SUBLINK SubPlans can do the wrong thing if their "args" lists aren't all identical. I was confused for awhile as to why the problem hadn't emerged long before, because the business with setting ParamExecData.execPlan to point to a SubPlan is ancient. I eventually realized that it's safe in the context of initplans, because *those don't have any values to be passed in*, so their args lists are always empty. This means that it doesn't matter if we clone an initplan SubPlan and let the clones share output parameters, because they'll all be alike enough for ExecSetParamPlan's purposes. But it does matter for MULTIEXPR_SUBLINK, which abused that ancient design by adding the possibility of passed-in arguments. So what we need to do is guarantee that MULTIEXPR_SUBLINKs don't share output parameters. Fortunately, this isn't too hard, because that could only happen when inheritance_planner() clones an UPDATE targetlist, and the stuff we need to change will all be at top level of that targetlist. Proposed patch against v13 attached; it'll need to be back-patched as far as v10. We don't need any of this logic in v14 and up, but I'm thinking of putting a slightly modified version of the new comment in nodeSubplan.c into HEAD, just to memorialize the issue. regards, tom lane
Commits
-
Fix oversight in recent MULTIEXPR_SUBLINK fix.
- 42d0d46f9825 10.23 landed
- df92bc115ec8 12.13 landed
- 56dc4424472c 11.18 landed
- 18f51083c990 13.9 landed
-
Doc: add comment about bug fixed in back branches as of 3f7323cbb.
- d1ce745db2d7 16.0 landed
-
Repair rare failure of MULTIEXPR_SUBLINK subplans in inherited updates.
- f8e70cfb8fd4 12.13 landed
- e1ea6f37452a 10.23 landed
- d9ebc582fbc6 11.18 landed
- 3f7323cbbdd3 13.9 landed