aboutsummaryrefslogtreecommitdiff
path: root/src/backend/optimizer/prep/preptlist.c
diff options
context:
space:
mode:
authorTom Lane <tgl@sss.pgh.pa.us>2003-05-12 00:17:03 +0000
committerTom Lane <tgl@sss.pgh.pa.us>2003-05-12 00:17:03 +0000
commitd97c9b366273a49f0469184df9dfb3a312b2f3ff (patch)
tree38e38e6c1d443aa69fb7418a2b0685e10f52de36 /src/backend/optimizer/prep/preptlist.c
parenta7c50cd92b17885d926fdf4f0df084849f285d58 (diff)
downloadpostgresql-d97c9b366273a49f0469184df9dfb3a312b2f3ff.tar.gz
postgresql-d97c9b366273a49f0469184df9dfb3a312b2f3ff.zip
Apply fixes for problems with dropped columns whose types have also been
dropped. The simplest fix for INSERT/UPDATE cases turns out to be for preptlist.c to insert NULLs of a known-good type (I used INT4) rather than making them match the deleted column's type. Since the representation of NULL is actually datatype-independent, this should work fine. I also re-reverted the patch to disable the use_physical_tlist optimization in the presence of dropped columns. It still doesn't look worth the trouble to be smarter, if there are no other bugs to fix. Added a regression test to catch future problems in this area.
Diffstat (limited to 'src/backend/optimizer/prep/preptlist.c')
-rw-r--r--src/backend/optimizer/prep/preptlist.c58
1 files changed, 44 insertions, 14 deletions
diff --git a/src/backend/optimizer/prep/preptlist.c b/src/backend/optimizer/prep/preptlist.c
index dc8faa9d837..00132a53cde 100644
--- a/src/backend/optimizer/prep/preptlist.c
+++ b/src/backend/optimizer/prep/preptlist.c
@@ -15,7 +15,7 @@
* Portions Copyright (c) 1994, Regents of the University of California
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/backend/optimizer/prep/preptlist.c,v 1.60 2003/02/03 21:15:44 tgl Exp $
+ * $Header: /cvsroot/pgsql/src/backend/optimizer/prep/preptlist.c,v 1.61 2003/05/12 00:17:03 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -171,6 +171,15 @@ expand_targetlist(List *tlist, int command_type,
* the attribute, so that it gets copied to the new tuple. But
* generate a NULL for dropped columns (we want to drop any
* old values).
+ *
+ * When generating a NULL constant for a dropped column, we label
+ * it INT4 (any other guaranteed-to-exist datatype would do as
+ * well). We can't label it with the dropped column's datatype
+ * since that might not exist anymore. It does not really
+ * matter what we claim the type is, since NULL is NULL --- its
+ * representation is datatype-independent. This could perhaps
+ * confuse code comparing the finished plan to the target
+ * relation, however.
*/
Oid atttype = att_tup->atttypid;
int32 atttypmod = att_tup->atttypmod;
@@ -179,31 +188,52 @@ expand_targetlist(List *tlist, int command_type,
switch (command_type)
{
case CMD_INSERT:
- new_expr = (Node *) makeConst(atttype,
- att_tup->attlen,
- (Datum) 0,
- true, /* isnull */
- att_tup->attbyval);
if (!att_tup->attisdropped)
+ {
+ new_expr = (Node *) makeConst(atttype,
+ att_tup->attlen,
+ (Datum) 0,
+ true, /* isnull */
+ att_tup->attbyval);
new_expr = coerce_to_domain(new_expr,
InvalidOid,
atttype,
COERCE_IMPLICIT_CAST);
+ }
+ else
+ {
+ /* Insert NULL for dropped column */
+ new_expr = (Node *) makeConst(INT4OID,
+ sizeof(int32),
+ (Datum) 0,
+ true, /* isnull */
+ true /* byval */);
+ /* label resdom with INT4, too */
+ atttype = INT4OID;
+ atttypmod = -1;
+ }
break;
case CMD_UPDATE:
- /* Insert NULLs for dropped columns */
- if (att_tup->attisdropped)
- new_expr = (Node *) makeConst(atttype,
- att_tup->attlen,
- (Datum) 0,
- true, /* isnull */
- att_tup->attbyval);
- else
+ if (!att_tup->attisdropped)
+ {
new_expr = (Node *) makeVar(result_relation,
attrno,
atttype,
atttypmod,
0);
+ }
+ else
+ {
+ /* Insert NULL for dropped column */
+ new_expr = (Node *) makeConst(INT4OID,
+ sizeof(int32),
+ (Datum) 0,
+ true, /* isnull */
+ true /* byval */);
+ /* label resdom with INT4, too */
+ atttype = INT4OID;
+ atttypmod = -1;
+ }
break;
default:
elog(ERROR, "expand_targetlist: unexpected command_type");