1
0
mirror of https://github.com/postgres/postgres.git synced 2025-07-30 11:03:19 +03:00

Fix up the remaining places where the expression node structure would lose

available information about the typmod of an expression; namely, Const,
ArrayRef, ArrayExpr, and EXPR and ARRAY SubLinks.  In the ArrayExpr and
SubLink cases it wasn't really the data structure's fault, but exprTypmod()
being lazy.  This seems like a good idea in view of the expected increase in
typmod usage from Teodor's work to allow user-defined types to have typmods.
In particular this responds to the concerns we had about eliminating the
special-purpose hack that exprTypmod() used to have for BPCHAR Consts.
We can now tell whether or not such a Const has been cast to a specific
length, and report or display properly if so.

initdb forced due to changes in stored rules.
This commit is contained in:
Tom Lane
2007-03-17 00:11:05 +00:00
parent 51d7741db1
commit 0f4ff460c4
21 changed files with 239 additions and 117 deletions

View File

@ -9,7 +9,7 @@
*
*
* IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/optimizer/path/indxpath.c,v 1.216 2007/01/20 20:45:39 tgl Exp $
* $PostgreSQL: pgsql/src/backend/optimizer/path/indxpath.c,v 1.217 2007/03/17 00:11:04 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@ -2628,7 +2628,7 @@ network_prefix_quals(Node *leftop, Oid expr_op, Oid opfamily, Datum rightop)
expr = make_opclause(opr1oid, BOOLOID, false,
(Expr *) leftop,
(Expr *) makeConst(datatype, -1, opr1right,
(Expr *) makeConst(datatype, -1, -1, opr1right,
false, false));
result = list_make1(make_restrictinfo(expr, true, false, false, NULL));
@ -2643,7 +2643,7 @@ network_prefix_quals(Node *leftop, Oid expr_op, Oid opfamily, Datum rightop)
expr = make_opclause(opr2oid, BOOLOID, false,
(Expr *) leftop,
(Expr *) makeConst(datatype, -1, opr2right,
(Expr *) makeConst(datatype, -1, -1, opr2right,
false, false));
result = lappend(result,
make_restrictinfo(expr, true, false, false, NULL));
@ -2683,6 +2683,7 @@ string_to_const(const char *str, Oid datatype)
{
Datum conval = string_to_datum(str, datatype);
return makeConst(datatype, ((datatype == NAMEOID) ? NAMEDATALEN : -1),
return makeConst(datatype, -1,
((datatype == NAMEOID) ? NAMEDATALEN : -1),
conval, false, false);
}

View File

@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/optimizer/plan/planagg.c,v 1.29 2007/02/22 22:00:24 tgl Exp $
* $PostgreSQL: pgsql/src/backend/optimizer/plan/planagg.c,v 1.30 2007/03/17 00:11:04 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@ -477,7 +477,7 @@ make_agg_subplan(PlannerInfo *root, MinMaxAggInfo *info)
/* set up LIMIT 1 */
subparse->limitOffset = NULL;
subparse->limitCount = (Node *) makeConst(INT8OID, sizeof(int64),
subparse->limitCount = (Node *) makeConst(INT8OID, -1, sizeof(int64),
Int64GetDatum(1),
false, false /* not by val */ );

View File

@ -16,7 +16,7 @@
* Portions Copyright (c) 1994, Regents of the University of California
*
* IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/optimizer/prep/preptlist.c,v 1.86 2007/02/19 07:03:30 tgl Exp $
* $PostgreSQL: pgsql/src/backend/optimizer/prep/preptlist.c,v 1.87 2007/03/17 00:11:04 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@ -281,6 +281,7 @@ expand_targetlist(List *tlist, int command_type,
if (!att_tup->attisdropped)
{
new_expr = (Node *) makeConst(atttype,
-1,
att_tup->attlen,
(Datum) 0,
true, /* isnull */
@ -296,6 +297,7 @@ expand_targetlist(List *tlist, int command_type,
{
/* Insert NULL for dropped column */
new_expr = (Node *) makeConst(INT4OID,
-1,
sizeof(int32),
(Datum) 0,
true, /* isnull */
@ -315,6 +317,7 @@ expand_targetlist(List *tlist, int command_type,
{
/* Insert NULL for dropped column */
new_expr = (Node *) makeConst(INT4OID,
-1,
sizeof(int32),
(Datum) 0,
true, /* isnull */

View File

@ -22,7 +22,7 @@
*
*
* IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/optimizer/prep/prepunion.c,v 1.139 2007/02/22 22:00:24 tgl Exp $
* $PostgreSQL: pgsql/src/backend/optimizer/prep/prepunion.c,v 1.140 2007/03/17 00:11:04 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@ -545,6 +545,7 @@ generate_setop_tlist(List *colTypes, int flag,
/* Add a resjunk flag column */
/* flag value is the given constant */
expr = (Node *) makeConst(INT4OID,
-1,
sizeof(int4),
Int32GetDatum(flag),
false,

View File

@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/optimizer/util/clauses.c,v 1.238 2007/03/13 00:33:41 tgl Exp $
* $PostgreSQL: pgsql/src/backend/optimizer/util/clauses.c,v 1.239 2007/03/17 00:11:04 tgl Exp $
*
* HISTORY
* AUTHOR DATE MAJOR EVENT
@ -82,10 +82,12 @@ static List *simplify_and_arguments(List *args,
eval_const_expressions_context *context,
bool *haveNull, bool *forceFalse);
static Expr *simplify_boolean_equality(List *args);
static Expr *simplify_function(Oid funcid, Oid result_type, List *args,
static Expr *simplify_function(Oid funcid,
Oid result_type, int32 result_typmod, List *args,
bool allow_inline,
eval_const_expressions_context *context);
static Expr *evaluate_function(Oid funcid, Oid result_type, List *args,
static Expr *evaluate_function(Oid funcid,
Oid result_type, int32 result_typmod, List *args,
HeapTuple func_tuple,
eval_const_expressions_context *context);
static Expr *inline_function(Oid funcid, Oid result_type, List *args,
@ -96,7 +98,7 @@ static Node *substitute_actual_parameters(Node *expr, int nargs, List *args,
static Node *substitute_actual_parameters_mutator(Node *node,
substitute_actual_parameters_context *context);
static void sql_inline_error_callback(void *arg);
static Expr *evaluate_expr(Expr *expr, Oid result_type);
static Expr *evaluate_expr(Expr *expr, Oid result_type, int32 result_typmod);
/*****************************************************************************
@ -934,8 +936,6 @@ contain_nonstrict_functions_walker(Node *node, void *context)
return true;
if (IsA(node, CaseExpr))
return true;
if (IsA(node, CaseWhen))
return true;
if (IsA(node, ArrayExpr))
return true;
if (IsA(node, RowExpr))
@ -1654,6 +1654,7 @@ eval_const_expressions_mutator(Node *node,
else
pval = datumCopy(prm->value, typByVal, typLen);
return (Node *) makeConst(param->paramtype,
param->paramtypmod,
(int) typLen,
pval,
prm->isnull,
@ -1682,9 +1683,13 @@ eval_const_expressions_mutator(Node *node,
/*
* Code for op/func reduction is pretty bulky, so split it out as a
* separate function.
* separate function. Note: exprTypmod normally returns -1 for a
* FuncExpr, but not when the node is recognizably a length coercion;
* we want to preserve the typmod in the eventual Const if so.
*/
simple = simplify_function(expr->funcid, expr->funcresulttype, args,
simple = simplify_function(expr->funcid,
expr->funcresulttype, exprTypmod(node),
args,
true, context);
if (simple) /* successfully simplified it */
return (Node *) simple;
@ -1728,7 +1733,9 @@ eval_const_expressions_mutator(Node *node,
* Code for op/func reduction is pretty bulky, so split it out as a
* separate function.
*/
simple = simplify_function(expr->opfuncid, expr->opresulttype, args,
simple = simplify_function(expr->opfuncid,
expr->opresulttype, -1,
args,
true, context);
if (simple) /* successfully simplified it */
return (Node *) simple;
@ -1816,8 +1823,10 @@ eval_const_expressions_mutator(Node *node,
* Code for op/func reduction is pretty bulky, so split it out as
* a separate function.
*/
simple = simplify_function(expr->opfuncid, expr->opresulttype,
args, false, context);
simple = simplify_function(expr->opfuncid,
expr->opresulttype, -1,
args,
false, context);
if (simple) /* successfully simplified it */
{
/*
@ -1961,12 +1970,7 @@ eval_const_expressions_mutator(Node *node,
Const *con = (Const *) arg;
con->consttype = relabel->resulttype;
/*
* relabel's resulttypmod is discarded, which is OK for now; if
* the type actually needs a runtime length coercion then there
* should be a function call to do it just above this node.
*/
con->consttypmod = relabel->resulttypmod;
return (Node *) con;
}
else
@ -2134,7 +2138,8 @@ eval_const_expressions_mutator(Node *node,
if (all_const)
return (Node *) evaluate_expr((Expr *) newarray,
newarray->array_typeid);
newarray->array_typeid,
exprTypmod(node));
return (Node *) newarray;
}
@ -2637,14 +2642,15 @@ simplify_boolean_equality(List *args)
* (which might originally have been an operator; we don't care)
*
* Inputs are the function OID, actual result type OID (which is needed for
* polymorphic functions), and the pre-simplified argument list;
* polymorphic functions) and typmod, and the pre-simplified argument list;
* also the context data for eval_const_expressions.
*
* Returns a simplified expression if successful, or NULL if cannot
* simplify the function call.
*/
static Expr *
simplify_function(Oid funcid, Oid result_type, List *args,
simplify_function(Oid funcid, Oid result_type, int32 result_typmod,
List *args,
bool allow_inline,
eval_const_expressions_context *context)
{
@ -2665,7 +2671,7 @@ simplify_function(Oid funcid, Oid result_type, List *args,
if (!HeapTupleIsValid(func_tuple))
elog(ERROR, "cache lookup failed for function %u", funcid);
newexpr = evaluate_function(funcid, result_type, args,
newexpr = evaluate_function(funcid, result_type, result_typmod, args,
func_tuple, context);
if (!newexpr && allow_inline)
@ -2689,7 +2695,7 @@ simplify_function(Oid funcid, Oid result_type, List *args,
* simplify the function.
*/
static Expr *
evaluate_function(Oid funcid, Oid result_type, List *args,
evaluate_function(Oid funcid, Oid result_type, int32 result_typmod, List *args,
HeapTuple func_tuple,
eval_const_expressions_context *context)
{
@ -2773,7 +2779,7 @@ evaluate_function(Oid funcid, Oid result_type, List *args,
newexpr->funcformat = COERCE_DONTCARE; /* doesn't matter */
newexpr->args = args;
return evaluate_expr((Expr *) newexpr, result_type);
return evaluate_expr((Expr *) newexpr, result_type, result_typmod);
}
/*
@ -3133,7 +3139,7 @@ sql_inline_error_callback(void *arg)
* code and ensure we get the same result as the executor would get.
*/
static Expr *
evaluate_expr(Expr *expr, Oid result_type)
evaluate_expr(Expr *expr, Oid result_type, int32 result_typmod)
{
EState *estate;
ExprState *exprstate;
@ -3184,7 +3190,7 @@ evaluate_expr(Expr *expr, Oid result_type)
/*
* Make the constant result node.
*/
return (Expr *) makeConst(result_type, resultTypLen,
return (Expr *) makeConst(result_type, result_typmod, resultTypLen,
const_val, const_is_null,
resultTypByVal);
}

View File

@ -9,7 +9,7 @@
*
*
* IDENTIFICATION
* $PostgreSQL: pgsql/src/backend/optimizer/util/predtest.c,v 1.13 2007/01/05 22:19:33 momjian Exp $
* $PostgreSQL: pgsql/src/backend/optimizer/util/predtest.c,v 1.14 2007/03/17 00:11:04 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@ -828,6 +828,7 @@ arrayconst_startup_fn(Node *clause, PredIterInfo info)
/* Set up a dummy Const node to hold the per-element values */
state->constexpr.xpr.type = T_Const;
state->constexpr.consttype = ARR_ELEMTYPE(arrayval);
state->constexpr.consttypmod = -1;
state->constexpr.constlen = elmlen;
state->constexpr.constbyval = elmbyval;
lsecond(state->opexpr.args) = &state->constexpr;