@@ -34,7 +34,7 @@ typedef struct
3434static void make_inh_translation_list (Relation oldrelation ,
3535Relation newrelation ,
3636Index newvarno ,
37- List * * translated_vars );
37+ AppendRelInfo * appinfo );
3838static Node * adjust_appendrel_attrs_mutator (Node * node ,
3939adjust_appendrel_attrs_context * context );
4040static List * adjust_inherited_tlist (List * tlist ,
@@ -55,8 +55,7 @@ make_append_rel_info(Relation parentrel, Relation childrel,
5555appinfo -> child_relid = childRTindex ;
5656appinfo -> parent_reltype = parentrel -> rd_rel -> reltype ;
5757appinfo -> child_reltype = childrel -> rd_rel -> reltype ;
58- make_inh_translation_list (parentrel ,childrel ,childRTindex ,
59- & appinfo -> translated_vars );
58+ make_inh_translation_list (parentrel ,childrel ,childRTindex ,appinfo );
6059appinfo -> parent_reloid = RelationGetRelid (parentrel );
6160
6261return appinfo ;
@@ -65,16 +64,23 @@ make_append_rel_info(Relation parentrel, Relation childrel,
6564/*
6665 * make_inh_translation_list
6766 * Build the list of translations from parent Vars to child Vars for
68- * an inheritance child.
67+ * an inheritance child, as well as a reverse-translation array.
68+ *
69+ * The reverse-translation array has an entry for each child relation
70+ * column, which is either the 1-based index of the corresponding parent
71+ * column, or 0 if there's no match (that happens for dropped child columns,
72+ * as well as child columns beyond those of the parent, which are allowed in
73+ * traditional inheritance though not partitioning).
6974 *
7075 * For paranoia's sake, we match type/collation as well as attribute name.
7176 */
7277static void
7378make_inh_translation_list (Relation oldrelation ,Relation newrelation ,
7479Index newvarno ,
75- List * * translated_vars )
80+ AppendRelInfo * appinfo )
7681{
7782List * vars = NIL ;
83+ AttrNumber * pcolnos ;
7884TupleDesc old_tupdesc = RelationGetDescr (oldrelation );
7985TupleDesc new_tupdesc = RelationGetDescr (newrelation );
8086Oid new_relid = RelationGetRelid (newrelation );
@@ -83,6 +89,11 @@ make_inh_translation_list(Relation oldrelation, Relation newrelation,
8389int old_attno ;
8490int new_attno = 0 ;
8591
92+ /* Initialize reverse-translation array with all entries zero */
93+ appinfo -> num_child_cols = newnatts ;
94+ appinfo -> parent_colnos = pcolnos =
95+ (AttrNumber * )palloc0 (newnatts * sizeof (AttrNumber ));
96+
8697for (old_attno = 0 ;old_attno < oldnatts ;old_attno ++ )
8798{
8899Form_pg_attribute att ;
@@ -115,6 +126,7 @@ make_inh_translation_list(Relation oldrelation, Relation newrelation,
115126atttypmod ,
116127attcollation ,
1171280 ));
129+ pcolnos [old_attno ]= old_attno + 1 ;
118130continue ;
119131}
120132
@@ -138,6 +150,7 @@ make_inh_translation_list(Relation oldrelation, Relation newrelation,
138150elog (ERROR ,"could not find inherited attribute \"%s\" of relation \"%s\"" ,
139151attname ,RelationGetRelationName (newrelation ));
140152new_attno = ((Form_pg_attribute )GETSTRUCT (newtup ))-> attnum - 1 ;
153+ Assert (new_attno >=0 && new_attno < newnatts );
141154ReleaseSysCache (newtup );
142155
143156att = TupleDescAttr (new_tupdesc ,new_attno );
@@ -157,10 +170,11 @@ make_inh_translation_list(Relation oldrelation, Relation newrelation,
157170atttypmod ,
158171attcollation ,
1591720 ));
173+ pcolnos [new_attno ]= old_attno + 1 ;
160174new_attno ++ ;
161175}
162176
163- * translated_vars = vars ;
177+ appinfo -> translated_vars = vars ;
164178}
165179
166180/*