diff options
author | Tom Lane | 2016-06-29 20:02:08 +0000 |
---|---|---|
committer | Tom Lane | 2016-06-29 20:02:08 +0000 |
commit | b32e63506cfec8c8bd3237ec5043de7414564d10 (patch) | |
tree | 2e4560ea909aaa47fa32fec31796aababc4ecad0 /src/backend | |
parent | 4242a715c3fca1a8fa31f810b7cffa88b4d4e439 (diff) |
Fix match_foreign_keys_to_quals for FKs linking to unused rtable entries.
Since get_relation_foreign_keys doesn't try to determine whether RTEs
are actually part of the query semantics, it might make FK info records
linking to RTEs that won't have a RelOptInfo at all. Cope with that.
Per bug #14219 from Andrew Gierth.
Report: <20160629183338.1397.43514@wrigleys.postgresql.org>
Diffstat (limited to 'src/backend')
-rw-r--r-- | src/backend/optimizer/plan/initsplan.c | 19 |
1 files changed, 17 insertions, 2 deletions
diff --git a/src/backend/optimizer/plan/initsplan.c b/src/backend/optimizer/plan/initsplan.c index db8db75b6e3..84ce6b31254 100644 --- a/src/backend/optimizer/plan/initsplan.c +++ b/src/backend/optimizer/plan/initsplan.c @@ -2329,11 +2329,26 @@ match_foreign_keys_to_quals(PlannerInfo *root) foreach(lc, root->fkey_list) { ForeignKeyOptInfo *fkinfo = (ForeignKeyOptInfo *) lfirst(lc); - RelOptInfo *con_rel = find_base_rel(root, fkinfo->con_relid); - RelOptInfo *ref_rel = find_base_rel(root, fkinfo->ref_relid); + RelOptInfo *con_rel; + RelOptInfo *ref_rel; int colno; /* + * Either relid might identify a rel that is in the query's rtable but + * isn't referenced by the jointree so won't have a RelOptInfo. Hence + * don't use find_base_rel() here. We can ignore such FKs. + */ + if (fkinfo->con_relid >= root->simple_rel_array_size || + fkinfo->ref_relid >= root->simple_rel_array_size) + continue; /* just paranoia */ + con_rel = root->simple_rel_array[fkinfo->con_relid]; + if (con_rel == NULL) + continue; + ref_rel = root->simple_rel_array[fkinfo->ref_relid]; + if (ref_rel == NULL) + continue; + + /* * Ignore FK unless both rels are baserels. This gets rid of FKs that * link to inheritance child rels (otherrels) and those that link to * rels removed by join removal (dead rels). |