aboutsummaryrefslogtreecommitdiff
path: root/src/backend/optimizer/plan
diff options
context:
space:
mode:
Diffstat (limited to 'src/backend/optimizer/plan')
-rw-r--r--src/backend/optimizer/plan/createplan.c29
-rw-r--r--src/backend/optimizer/plan/initsplan.c29
-rw-r--r--src/backend/optimizer/plan/planner.c10
-rw-r--r--src/backend/optimizer/plan/setrefs.c62
-rw-r--r--src/backend/optimizer/plan/subselect.c44
5 files changed, 82 insertions, 92 deletions
diff --git a/src/backend/optimizer/plan/createplan.c b/src/backend/optimizer/plan/createplan.c
index 0414fdf2f3f..a67e23fbf20 100644
--- a/src/backend/optimizer/plan/createplan.c
+++ b/src/backend/optimizer/plan/createplan.c
@@ -10,7 +10,7 @@
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/backend/optimizer/plan/createplan.c,v 1.127 2002/12/05 15:50:35 tgl Exp $
+ * $Header: /cvsroot/pgsql/src/backend/optimizer/plan/createplan.c,v 1.128 2002/12/12 15:49:32 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -1041,12 +1041,12 @@ fix_indxqual_sublist(List *indexqual, int baserelid, IndexOptInfo *index,
foreach(i, indexqual)
{
- Expr *clause = (Expr *) lfirst(i);
- Expr *newclause;
+ OpExpr *clause = (OpExpr *) lfirst(i);
+ OpExpr *newclause;
List *leftvarnos;
Oid opclass;
- if (!is_opclause((Node *) clause) || length(clause->args) != 2)
+ if (!IsA(clause, OpExpr) || length(clause->args) != 2)
elog(ERROR, "fix_indxqual_sublist: indexqual clause is not binary opclause");
/*
@@ -1056,7 +1056,7 @@ fix_indxqual_sublist(List *indexqual, int baserelid, IndexOptInfo *index,
* is a subplan in the arguments of the opclause. So just do a
* full copy.
*/
- newclause = (Expr *) copyObject((Node *) clause);
+ newclause = (OpExpr *) copyObject((Node *) clause);
/*
* Check to see if the indexkey is on the right; if so, commute
@@ -1083,7 +1083,7 @@ fix_indxqual_sublist(List *indexqual, int baserelid, IndexOptInfo *index,
* Finally, check to see if index is lossy for this operator. If
* so, add (a copy of) original form of clause to recheck list.
*/
- if (op_requires_recheck(((Oper *) newclause->oper)->opno, opclass))
+ if (op_requires_recheck(newclause->opno, opclass))
recheck_qual = lappend(recheck_qual,
copyObject((Node *) clause));
}
@@ -1100,7 +1100,7 @@ fix_indxqual_operand(Node *node, int baserelid, IndexOptInfo *index,
* Remove any binary-compatible relabeling of the indexkey
*/
if (IsA(node, RelabelType))
- node = ((RelabelType *) node)->arg;
+ node = (Node *) ((RelabelType *) node)->arg;
/*
* We represent index keys by Var nodes having the varno of the base
@@ -1168,11 +1168,11 @@ switch_outer(List *clauses)
foreach(i, clauses)
{
- Expr *clause = (Expr *) lfirst(i);
+ OpExpr *clause = (OpExpr *) lfirst(i);
Var *op;
- Assert(is_opclause((Node *) clause));
- op = get_rightop(clause);
+ Assert(is_opclause(clause));
+ op = get_rightop((Expr *) clause);
Assert(op && IsA(op, Var));
if (var_is_outer(op))
{
@@ -1181,10 +1181,13 @@ switch_outer(List *clauses)
* the clause without changing the original list. Could use
* copyObject, but a complete deep copy is overkill.
*/
- Expr *temp;
+ OpExpr *temp = makeNode(OpExpr);
- temp = make_clause(clause->opType, clause->oper,
- listCopy(clause->args));
+ temp->opno = clause->opno;
+ temp->opfuncid = InvalidOid;
+ temp->opresulttype = clause->opresulttype;
+ temp->opretset = clause->opretset;
+ temp->args = listCopy(clause->args);
/* Commute it --- note this modifies the temp node in-place. */
CommuteClause(temp);
t_list = lappend(t_list, temp);
diff --git a/src/backend/optimizer/plan/initsplan.c b/src/backend/optimizer/plan/initsplan.c
index 529ba712f41..aca2c6f4f67 100644
--- a/src/backend/optimizer/plan/initsplan.c
+++ b/src/backend/optimizer/plan/initsplan.c
@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/backend/optimizer/plan/initsplan.c,v 1.77 2002/11/24 21:52:14 tgl Exp $
+ * $Header: /cvsroot/pgsql/src/backend/optimizer/plan/initsplan.c,v 1.78 2002/12/12 15:49:32 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -761,14 +761,11 @@ process_implied_equality(Query *root, Node *item1, Node *item2,
elog(ERROR, "Equality operator for types '%s' and '%s' should be mergejoinable, but isn't",
format_type_be(ltype), format_type_be(rtype));
- clause = makeNode(Expr);
- clause->typeOid = BOOLOID;
- clause->opType = OP_EXPR;
- clause->oper = (Node *) makeOper(oprid(eq_operator), /* opno */
- InvalidOid, /* opid */
- BOOLOID, /* opresulttype */
- false); /* opretset */
- clause->args = makeList2(item1, item2);
+ clause = make_opclause(oprid(eq_operator), /* opno */
+ BOOLOID, /* opresulttype */
+ false, /* opretset */
+ (Expr *) item1,
+ (Expr *) item2);
ReleaseSysCache(eq_operator);
@@ -969,7 +966,7 @@ check_mergejoinable(RestrictInfo *restrictinfo)
leftOp,
rightOp;
- if (!is_opclause((Node *) clause))
+ if (!is_opclause(clause))
return;
left = get_leftop(clause);
@@ -978,10 +975,11 @@ check_mergejoinable(RestrictInfo *restrictinfo)
/* caution: is_opclause accepts more than I do, so check it */
if (!right)
return; /* unary opclauses need not apply */
- if (!IsA(left, Var) ||!IsA(right, Var))
+ if (!IsA(left, Var) ||
+ !IsA(right, Var))
return;
- opno = ((Oper *) clause->oper)->opno;
+ opno = ((OpExpr *) clause)->opno;
if (op_mergejoinable(opno,
left->vartype,
@@ -1012,7 +1010,7 @@ check_hashjoinable(RestrictInfo *restrictinfo)
*right;
Oid opno;
- if (!is_opclause((Node *) clause))
+ if (!is_opclause(clause))
return;
left = get_leftop(clause);
@@ -1021,10 +1019,11 @@ check_hashjoinable(RestrictInfo *restrictinfo)
/* caution: is_opclause accepts more than I do, so check it */
if (!right)
return; /* unary opclauses need not apply */
- if (!IsA(left, Var) ||!IsA(right, Var))
+ if (!IsA(left, Var) ||
+ !IsA(right, Var))
return;
- opno = ((Oper *) clause->oper)->opno;
+ opno = ((OpExpr *) clause)->opno;
if (op_hashjoinable(opno,
left->vartype,
diff --git a/src/backend/optimizer/plan/planner.c b/src/backend/optimizer/plan/planner.c
index ebb9f3d2092..b3d7b5303c4 100644
--- a/src/backend/optimizer/plan/planner.c
+++ b/src/backend/optimizer/plan/planner.c
@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/backend/optimizer/plan/planner.c,v 1.133 2002/12/05 21:46:37 tgl Exp $
+ * $Header: /cvsroot/pgsql/src/backend/optimizer/plan/planner.c,v 1.134 2002/12/12 15:49:32 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -91,7 +91,7 @@ planner(Query *parse)
* purpose is communication across multiple sub-Queries.
*
* Note we do NOT save and restore PlannerPlanId: it exists to assign
- * unique IDs to SubPlan nodes, and we want those IDs to be unique for
+ * unique IDs to SubPlanExpr nodes, and we want those IDs to be unique for
* the life of a backend. Also, PlannerInitPlan is saved/restored in
* subquery_planner, not here.
*/
@@ -278,7 +278,7 @@ subquery_planner(Query *parse, double tuple_fraction)
/* Must add the initPlans' extParams to the topmost node's, too */
foreach(lst, plan->initPlan)
{
- SubPlan *subplan = (SubPlan *) lfirst(lst);
+ SubPlanExpr *subplan = (SubPlanExpr *) lfirst(lst);
plan->extParam = set_unioni(plan->extParam,
subplan->plan->extParam);
@@ -1015,7 +1015,7 @@ grouping_planner(Query *parse, double tuple_fraction)
-1,
0);
- ctid = makeTargetEntry(resdom, (Node *) var);
+ ctid = makeTargetEntry(resdom, (Expr *) var);
tlist = lappend(tlist, ctid);
}
}
@@ -1707,7 +1707,7 @@ make_subplanTargetList(Query *parse,
exprTypmod(groupexpr),
NULL,
false),
- groupexpr);
+ (Expr *) groupexpr);
sub_tlist = lappend(sub_tlist, te);
}
diff --git a/src/backend/optimizer/plan/setrefs.c b/src/backend/optimizer/plan/setrefs.c
index b23843a030c..0d66c97964c 100644
--- a/src/backend/optimizer/plan/setrefs.c
+++ b/src/backend/optimizer/plan/setrefs.c
@@ -9,7 +9,7 @@
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/backend/optimizer/plan/setrefs.c,v 1.84 2002/12/05 15:50:35 tgl Exp $
+ * $Header: /cvsroot/pgsql/src/backend/optimizer/plan/setrefs.c,v 1.85 2002/12/12 15:49:32 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -52,7 +52,7 @@ static Node *replace_vars_with_subplan_refs(Node *node,
bool tlist_has_non_vars);
static Node *replace_vars_with_subplan_refs_mutator(Node *node,
replace_vars_with_subplan_refs_context *context);
-static bool fix_opids_walker(Node *node, void *context);
+static bool fix_opfuncids_walker(Node *node, void *context);
/*****************************************************************************
*
@@ -219,7 +219,7 @@ set_plan_references(Plan *plan, List *rtable)
* subplan references in this plan's tlist and quals. If we did the
* reference-adjustments bottom-up, then we would fail to match this
* plan's var nodes against the already-modified nodes of the
- * children. Fortunately, that consideration doesn't apply to SubPlan
+ * children. Fortunately, that consideration doesn't apply to SubPlanExpr
* nodes; else we'd need two passes over the expression trees.
*/
set_plan_references(plan->lefttree, rtable);
@@ -227,9 +227,9 @@ set_plan_references(Plan *plan, List *rtable)
foreach(pl, plan->initPlan)
{
- SubPlan *sp = (SubPlan *) lfirst(pl);
+ SubPlanExpr *sp = (SubPlanExpr *) lfirst(pl);
- Assert(IsA(sp, SubPlan));
+ Assert(IsA(sp, SubPlanExpr));
set_plan_references(sp->plan, sp->rtable);
}
}
@@ -238,8 +238,8 @@ set_plan_references(Plan *plan, List *rtable)
* fix_expr_references
* Do final cleanup on expressions (targetlists or quals).
*
- * This consists of looking up operator opcode info for Oper nodes
- * and recursively performing set_plan_references on SubPlans.
+ * This consists of looking up operator opcode info for OpExpr nodes
+ * and recursively performing set_plan_references on subplans.
*
* The Plan argument is currently unused, but might be needed again someday.
*/
@@ -255,20 +255,15 @@ fix_expr_references_walker(Node *node, void *context)
{
if (node == NULL)
return false;
- if (IsA(node, Expr))
+ if (IsA(node, OpExpr))
+ set_opfuncid((OpExpr *) node);
+ else if (IsA(node, DistinctExpr))
+ set_opfuncid((OpExpr *) node); /* rely on struct equivalence */
+ else if (IsA(node, SubPlanExpr))
{
- Expr *expr = (Expr *) node;
+ SubPlanExpr *sp = (SubPlanExpr *) node;
- if (expr->opType == OP_EXPR ||
- expr->opType == DISTINCT_EXPR)
- replace_opid((Oper *) expr->oper);
- else if (expr->opType == SUBPLAN_EXPR)
- {
- SubPlan *sp = (SubPlan *) expr->oper;
-
- Assert(IsA(sp, SubPlan));
- set_plan_references(sp->plan, sp->rtable);
- }
+ set_plan_references(sp->plan, sp->rtable);
}
return expression_tree_walker(node, fix_expr_references_walker, context);
}
@@ -362,12 +357,13 @@ set_uppernode_references(Plan *plan, Index subvarno)
TargetEntry *tle = (TargetEntry *) lfirst(l);
Node *newexpr;
- newexpr = replace_vars_with_subplan_refs(tle->expr,
+ newexpr = replace_vars_with_subplan_refs((Node *) tle->expr,
subvarno,
subplan_targetlist,
tlist_has_non_vars);
output_targetlist = lappend(output_targetlist,
- makeTargetEntry(tle->resdom, newexpr));
+ makeTargetEntry(tle->resdom,
+ (Expr *) newexpr));
}
plan->targetlist = output_targetlist;
@@ -570,8 +566,8 @@ replace_vars_with_subplan_refs_mutator(Node *node,
*****************************************************************************/
/*
- * fix_opids
- * Calculate opid field from opno for each Oper node in given tree.
+ * fix_opfuncids
+ * Calculate opfuncid field from opno for each OpExpr node in given tree.
* The given tree can be anything expression_tree_walker handles.
*
* The argument is modified in-place. (This is OK since we'd want the
@@ -579,24 +575,20 @@ replace_vars_with_subplan_refs_mutator(Node *node,
* shared structure.)
*/
void
-fix_opids(Node *node)
+fix_opfuncids(Node *node)
{
/* This tree walk requires no special setup, so away we go... */
- fix_opids_walker(node, NULL);
+ fix_opfuncids_walker(node, NULL);
}
static bool
-fix_opids_walker(Node *node, void *context)
+fix_opfuncids_walker(Node *node, void *context)
{
if (node == NULL)
return false;
- if (IsA(node, Expr))
- {
- Expr *expr = (Expr *) node;
-
- if (expr->opType == OP_EXPR ||
- expr->opType == DISTINCT_EXPR)
- replace_opid((Oper *) expr->oper);
- }
- return expression_tree_walker(node, fix_opids_walker, context);
+ if (IsA(node, OpExpr))
+ set_opfuncid((OpExpr *) node);
+ else if (IsA(node, DistinctExpr))
+ set_opfuncid((OpExpr *) node); /* rely on struct equivalence */
+ return expression_tree_walker(node, fix_opfuncids_walker, context);
}
diff --git a/src/backend/optimizer/plan/subselect.c b/src/backend/optimizer/plan/subselect.c
index a65de72c90b..fe17b8ebb01 100644
--- a/src/backend/optimizer/plan/subselect.c
+++ b/src/backend/optimizer/plan/subselect.c
@@ -7,7 +7,7 @@
* Portions Copyright (c) 1994, Regents of the University of California
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/backend/optimizer/plan/subselect.c,v 1.59 2002/12/05 15:50:35 tgl Exp $
+ * $Header: /cvsroot/pgsql/src/backend/optimizer/plan/subselect.c,v 1.60 2002/12/12 15:49:32 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -144,12 +144,12 @@ generate_new_param(Oid paramtype, int32 paramtypmod)
}
/*
- * Convert a bare SubLink (as created by the parser) into a SubPlan.
+ * Convert a bare SubLink (as created by the parser) into a SubPlanExpr.
*/
static Node *
make_subplan(SubLink *slink)
{
- SubPlan *node = makeNode(SubPlan);
+ SubPlanExpr *node = makeNode(SubPlanExpr);
Query *subquery = (Query *) (slink->subselect);
Oid result_type = exprType((Node *) slink);
double tuple_fraction;
@@ -210,11 +210,13 @@ make_subplan(SubLink *slink)
node->plan = plan = subquery_planner(subquery, tuple_fraction);
node->plan_id = PlannerPlanId++; /* Assign unique ID to this
- * SubPlan */
+ * SubPlanExpr */
node->rtable = subquery->rtable;
node->sublink = slink;
+ node->typeOid = result_type;
+
slink->subselect = NULL; /* cool ?! see error check above! */
/*
@@ -270,7 +272,6 @@ make_subplan(SubLink *slink)
}
else
{
- Expr *expr = makeNode(Expr);
List *args = NIL;
/*
@@ -350,14 +351,7 @@ make_subplan(SubLink *slink)
convert_sublink_opers(slink, plan->targetlist, NULL);
/*
- * Make expression of SUBPLAN type
- */
- expr->typeOid = result_type;
- expr->opType = SUBPLAN_EXPR;
- expr->oper = (Node *) node;
-
- /*
- * Make expr->args from parParam.
+ * Make node->args from parParam.
*/
foreach(lst, node->parParam)
{
@@ -373,9 +367,9 @@ make_subplan(SubLink *slink)
var->varlevelsup = 0;
args = lappend(args, var);
}
- expr->args = args;
+ node->args = args;
- result = (Node *) expr;
+ result = (Node *) node;
}
return result;
@@ -385,7 +379,7 @@ make_subplan(SubLink *slink)
* convert_sublink_opers: convert a SubLink's oper list from the
* parser/rewriter format into the executor's format.
*
- * The oper list is initially just a list of Oper nodes. We replace it
+ * The oper list is initially just a list of OpExpr nodes. We replace it
* with a list of actually executable expressions, in which the specified
* operators are applied to corresponding elements of the lefthand list
* and Params representing the results of the subplan. lefthand is then
@@ -404,7 +398,7 @@ convert_sublink_opers(SubLink *slink, List *targetlist,
foreach(lst, slink->oper)
{
- Oper *oper = (Oper *) lfirst(lst);
+ OpExpr *oper = (OpExpr *) lfirst(lst);
Node *lefthand = lfirst(leftlist);
TargetEntry *te = lfirst(targetlist);
Param *prm;
@@ -422,7 +416,7 @@ convert_sublink_opers(SubLink *slink, List *targetlist,
*setParams = lappendi(*setParams, prm->paramid);
/* Look up the operator to check its declared input types */
- Assert(IsA(oper, Oper));
+ Assert(IsA(oper, OpExpr));
tup = SearchSysCache(OPEROID,
ObjectIdGetDatum(oper->opno),
0, 0, 0);
@@ -439,9 +433,11 @@ convert_sublink_opers(SubLink *slink, List *targetlist,
left = make_operand(lefthand, exprType(lefthand), opform->oprleft);
right = make_operand((Node *) prm, prm->paramtype, opform->oprright);
newoper = lappend(newoper,
- make_opclause(oper,
- (Var *) left,
- (Var *) right));
+ make_opclause(oper->opno,
+ oper->opresulttype,
+ oper->opretset,
+ (Expr *) left,
+ (Expr *) right));
ReleaseSysCache(tup);
@@ -482,7 +478,7 @@ finalize_primnode(Node *node, finalize_primnode_results *results)
}
if (is_subplan(node))
{
- SubPlan *subplan = (SubPlan *) ((Expr *) node)->oper;
+ SubPlanExpr *subplan = (SubPlanExpr *) node;
List *lst;
/* Check extParam list for params to add to paramids */
@@ -559,12 +555,12 @@ process_sublinks_mutator(Node *node, void *context)
*/
sublink->lefthand = (List *)
process_sublinks_mutator((Node *) sublink->lefthand, context);
- /* Now build the SubPlan node and make the expr to return */
+ /* Now build the SubPlanExpr node and make the expr to return */
return make_subplan(sublink);
}
/*
- * Note that we will never see a SubPlan expression in the input
+ * Note that we will never see a SubPlanExpr expression in the input
* (since this is the very routine that creates 'em to begin with). So
* the code in expression_tree_mutator() that might do inappropriate
* things with SubPlans or SubLinks will not be exercised.