OSDN Git Service

65721e0863dbb04339a219f333185625c7d34810
[pg-rex/syncrep.git] / src / backend / executor / execQual.c
1 /*-------------------------------------------------------------------------
2  *
3  * execQual.c
4  *        Routines to evaluate qualification and targetlist expressions
5  *
6  * Portions Copyright (c) 1996-2004, PostgreSQL Global Development Group
7  * Portions Copyright (c) 1994, Regents of the University of California
8  *
9  *
10  * IDENTIFICATION
11  *        $PostgreSQL: pgsql/src/backend/executor/execQual.c,v 1.167 2004/08/29 04:12:31 momjian Exp $
12  *
13  *-------------------------------------------------------------------------
14  */
15 /*
16  *       INTERFACE ROUTINES
17  *              ExecEvalExpr    - (now a macro) evaluate an expression, return a datum
18  *              ExecEvalExprSwitchContext - same, but switch into eval memory context
19  *              ExecQual                - return true/false if qualification is satisfied
20  *              ExecProject             - form a new tuple by projecting the given tuple
21  *
22  *       NOTES
23  *              The more heavily used ExecEvalExpr routines, such as ExecEvalVar(),
24  *              are hotspots. Making these faster will speed up the entire system.
25  *
26  *              ExecProject() is used to make tuple projections.  Rather then
27  *              trying to speed it up, the execution plan should be pre-processed
28  *              to facilitate attribute sharing between nodes wherever possible,
29  *              instead of doing needless copying.      -cim 5/31/91
30  *
31  *              During expression evaluation, we check_stack_depth only in
32  *              ExecMakeFunctionResult rather than at every single node.  This
33  *              is a compromise that trades off precision of the stack limit setting
34  *              to gain speed.
35  */
36
37 #include "postgres.h"
38
39 #include "access/heapam.h"
40 #include "catalog/pg_type.h"
41 #include "commands/typecmds.h"
42 #include "executor/execdebug.h"
43 #include "executor/functions.h"
44 #include "executor/nodeSubplan.h"
45 #include "funcapi.h"
46 #include "miscadmin.h"
47 #include "nodes/makefuncs.h"
48 #include "optimizer/planmain.h"
49 #include "parser/parse_expr.h"
50 #include "utils/acl.h"
51 #include "utils/array.h"
52 #include "utils/builtins.h"
53 #include "utils/lsyscache.h"
54 #include "utils/typcache.h"
55
56
57 /* static function decls */
58 static Datum ExecEvalArrayRef(ArrayRefExprState *astate,
59                                  ExprContext *econtext,
60                                  bool *isNull, ExprDoneCond *isDone);
61 static Datum ExecEvalAggref(AggrefExprState *aggref,
62                                                         ExprContext *econtext,
63                                                         bool *isNull, ExprDoneCond *isDone);
64 static Datum ExecEvalVar(ExprState *exprstate, ExprContext *econtext,
65                                                  bool *isNull, ExprDoneCond *isDone);
66 static Datum ExecEvalConst(ExprState *exprstate, ExprContext *econtext,
67                                                  bool *isNull, ExprDoneCond *isDone);
68 static Datum ExecEvalParam(ExprState *exprstate, ExprContext *econtext,
69                                                    bool *isNull, ExprDoneCond *isDone);
70 static ExprDoneCond ExecEvalFuncArgs(FunctionCallInfo fcinfo,
71                                  List *argList, ExprContext *econtext);
72 static Datum ExecMakeFunctionResultNoSets(FuncExprState *fcache,
73                                                                                   ExprContext *econtext,
74                                                                                   bool *isNull, ExprDoneCond *isDone);
75 static Datum ExecEvalFunc(FuncExprState *fcache, ExprContext *econtext,
76                          bool *isNull, ExprDoneCond *isDone);
77 static Datum ExecEvalOper(FuncExprState *fcache, ExprContext *econtext,
78                          bool *isNull, ExprDoneCond *isDone);
79 static Datum ExecEvalDistinct(FuncExprState *fcache, ExprContext *econtext,
80                                                           bool *isNull, ExprDoneCond *isDone);
81 static Datum ExecEvalScalarArrayOp(ScalarArrayOpExprState *sstate,
82                                                                    ExprContext *econtext,
83                                                                    bool *isNull, ExprDoneCond *isDone);
84 static Datum ExecEvalNot(BoolExprState *notclause, ExprContext *econtext,
85                                                  bool *isNull, ExprDoneCond *isDone);
86 static Datum ExecEvalOr(BoolExprState *orExpr, ExprContext *econtext,
87                                                 bool *isNull, ExprDoneCond *isDone);
88 static Datum ExecEvalAnd(BoolExprState *andExpr, ExprContext *econtext,
89                                                  bool *isNull, ExprDoneCond *isDone);
90 static Datum ExecEvalCase(CaseExprState *caseExpr, ExprContext *econtext,
91                          bool *isNull, ExprDoneCond *isDone);
92 static Datum ExecEvalCaseTestExpr(ExprState *exprstate,
93                                                                   ExprContext *econtext,
94                                                                   bool *isNull, ExprDoneCond *isDone);
95 static Datum ExecEvalArray(ArrayExprState *astate,
96                                                    ExprContext *econtext,
97                                                    bool *isNull, ExprDoneCond *isDone);
98 static Datum ExecEvalRow(RowExprState *rstate,
99                                                  ExprContext *econtext,
100                                                  bool *isNull, ExprDoneCond *isDone);
101 static Datum ExecEvalCoalesce(CoalesceExprState *coalesceExpr,
102                                                           ExprContext *econtext,
103                                                           bool *isNull, ExprDoneCond *isDone);
104 static Datum ExecEvalNullIf(FuncExprState *nullIfExpr,
105                                                         ExprContext *econtext,
106                                                         bool *isNull, ExprDoneCond *isDone);
107 static Datum ExecEvalNullTest(GenericExprState *nstate,
108                                  ExprContext *econtext,
109                                  bool *isNull, ExprDoneCond *isDone);
110 static Datum ExecEvalBooleanTest(GenericExprState *bstate,
111                                         ExprContext *econtext,
112                                         bool *isNull, ExprDoneCond *isDone);
113 static Datum ExecEvalCoerceToDomain(CoerceToDomainState *cstate,
114                                            ExprContext *econtext,
115                                            bool *isNull, ExprDoneCond *isDone);
116 static Datum ExecEvalCoerceToDomainValue(ExprState *exprstate,
117                                                                                  ExprContext *econtext,
118                                                                                  bool *isNull, ExprDoneCond *isDone);
119 static Datum ExecEvalFieldSelect(FieldSelectState *fstate,
120                                         ExprContext *econtext,
121                                         bool *isNull, ExprDoneCond *isDone);
122 static Datum ExecEvalFieldStore(FieldStoreState *fstate,
123                                         ExprContext *econtext,
124                                         bool *isNull, ExprDoneCond *isDone);
125 static Datum ExecEvalRelabelType(GenericExprState *exprstate,
126                                         ExprContext *econtext,
127                                         bool *isNull, ExprDoneCond *isDone);
128
129
130 /* ----------------------------------------------------------------
131  *              ExecEvalExpr routines
132  *
133  *              Recursively evaluate a targetlist or qualification expression.
134  *
135  * Each of the following routines having the signature
136  *              Datum ExecEvalFoo(ExprState *expression,
137  *                                                ExprContext *econtext,
138  *                                                bool *isNull,
139  *                                                ExprDoneCond *isDone);
140  * is responsible for evaluating one type or subtype of ExprState node.
141  * They are normally called via the ExecEvalExpr macro, which makes use of
142  * the function pointer set up when the ExprState node was built by
143  * ExecInitExpr.  (In some cases, we change this pointer later to avoid
144  * re-executing one-time overhead.)
145  *
146  * Note: for notational simplicity we declare these functions as taking the
147  * specific type of ExprState that they work on.  This requires casting when
148  * assigning the function pointer in ExecInitExpr.  Be careful that the
149  * function signature is declared correctly, because the cast suppresses
150  * automatic checking!
151  *
152  *
153  * All these functions share this calling convention:
154  *
155  * Inputs:
156  *              expression: the expression state tree to evaluate
157  *              econtext: evaluation context information
158  *
159  * Outputs:
160  *              return value: Datum value of result
161  *              *isNull: set to TRUE if result is NULL (actual return value is
162  *                               meaningless if so); set to FALSE if non-null result
163  *              *isDone: set to indicator of set-result status
164  *
165  * A caller that can only accept a singleton (non-set) result should pass
166  * NULL for isDone; if the expression computes a set result then an error
167  * will be reported via ereport.  If the caller does pass an isDone pointer
168  * then *isDone is set to one of these three states:
169  *              ExprSingleResult                singleton result (not a set)
170  *              ExprMultipleResult              return value is one element of a set
171  *              ExprEndResult                   there are no more elements in the set
172  * When ExprMultipleResult is returned, the caller should invoke
173  * ExecEvalExpr() repeatedly until ExprEndResult is returned.  ExprEndResult
174  * is returned after the last real set element.  For convenience isNull will
175  * always be set TRUE when ExprEndResult is returned, but this should not be
176  * taken as indicating a NULL element of the set.  Note that these return
177  * conventions allow us to distinguish among a singleton NULL, a NULL element
178  * of a set, and an empty set.
179  *
180  * The caller should already have switched into the temporary memory
181  * context econtext->ecxt_per_tuple_memory.  The convenience entry point
182  * ExecEvalExprSwitchContext() is provided for callers who don't prefer to
183  * do the switch in an outer loop.      We do not do the switch in these routines
184  * because it'd be a waste of cycles during nested expression evaluation.
185  * ----------------------------------------------------------------
186  */
187
188
189 /*----------
190  *        ExecEvalArrayRef
191  *
192  *         This function takes an ArrayRef and returns the extracted Datum
193  *         if it's a simple reference, or the modified array value if it's
194  *         an array assignment (i.e., array element or slice insertion).
195  *
196  * NOTE: if we get a NULL result from a subexpression, we return NULL when
197  * it's an array reference, or the unmodified source array when it's an
198  * array assignment.  This may seem peculiar, but if we return NULL (as was
199  * done in versions up through 7.0) then an assignment like
200  *                      UPDATE table SET arrayfield[4] = NULL
201  * will result in setting the whole array to NULL, which is certainly not
202  * very desirable.      By returning the source array we make the assignment
203  * into a no-op, instead.  (Eventually we need to redesign arrays so that
204  * individual elements can be NULL, but for now, let's try to protect users
205  * from shooting themselves in the foot.)
206  *
207  * NOTE: we deliberately refrain from applying DatumGetArrayTypeP() here,
208  * even though that might seem natural, because this code needs to support
209  * both varlena arrays and fixed-length array types.  DatumGetArrayTypeP()
210  * only works for the varlena kind.  The routines we call in arrayfuncs.c
211  * have to know the difference (that's what they need refattrlength for).
212  *----------
213  */
214 static Datum
215 ExecEvalArrayRef(ArrayRefExprState *astate,
216                                  ExprContext *econtext,
217                                  bool *isNull,
218                                  ExprDoneCond *isDone)
219 {
220         ArrayRef   *arrayRef = (ArrayRef *) astate->xprstate.expr;
221         ArrayType  *array_source;
222         ArrayType  *resultArray;
223         bool            isAssignment = (arrayRef->refassgnexpr != NULL);
224         bool            eisnull;
225         ListCell   *l;
226         int                     i = 0,
227                                 j = 0;
228         IntArray        upper,
229                                 lower;
230         int                *lIndex;
231
232         array_source = (ArrayType *)
233                 DatumGetPointer(ExecEvalExpr(astate->refexpr,
234                                                                          econtext,
235                                                                          isNull,
236                                                                          isDone));
237
238         /*
239          * If refexpr yields NULL, and it's a fetch, then result is NULL.
240          * In the assignment case, we'll cons up something below.
241          */
242         if (*isNull)
243         {
244                 if (isDone && *isDone == ExprEndResult)
245                         return (Datum) NULL; /* end of set result */
246                 if (!isAssignment)
247                         return (Datum) NULL;
248         }
249
250         foreach(l, astate->refupperindexpr)
251         {
252                 ExprState  *eltstate = (ExprState *) lfirst(l);
253
254                 if (i >= MAXDIM)
255                         ereport(ERROR,
256                                         (errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
257                                          errmsg("number of array dimensions (%d) exceeds the maximum allowed (%d)",
258                                                         i, MAXDIM)));
259
260                 upper.indx[i++] = DatumGetInt32(ExecEvalExpr(eltstate,
261                                                                                                          econtext,
262                                                                                                          &eisnull,
263                                                                                                          NULL));
264                 /* If any index expr yields NULL, result is NULL or source array */
265                 if (eisnull)
266                 {
267                         if (!isAssignment)
268                         {
269                                 *isNull = true;
270                                 return (Datum) NULL;
271                         }
272                         return PointerGetDatum(array_source);
273                 }
274         }
275
276         if (astate->reflowerindexpr != NIL)
277         {
278                 foreach(l, astate->reflowerindexpr)
279                 {
280                         ExprState  *eltstate = (ExprState *) lfirst(l);
281
282                         if (j >= MAXDIM)
283                                 ereport(ERROR,
284                                                 (errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
285                                                  errmsg("number of array dimensions (%d) exceeds the maximum allowed (%d)",
286                                                                 i, MAXDIM)));
287
288                         lower.indx[j++] = DatumGetInt32(ExecEvalExpr(eltstate,
289                                                                                                                  econtext,
290                                                                                                                  &eisnull,
291                                                                                                                  NULL));
292
293                         /*
294                          * If any index expr yields NULL, result is NULL or source
295                          * array
296                          */
297                         if (eisnull)
298                         {
299                                 if (!isAssignment)
300                                 {
301                                         *isNull = true;
302                                         return (Datum) NULL;
303                                 }
304                                 return PointerGetDatum(array_source);
305                         }
306                 }
307                 /* this can't happen unless parser messed up */
308                 if (i != j)
309                         elog(ERROR, "upper and lower index lists are not same length");
310                 lIndex = lower.indx;
311         }
312         else
313                 lIndex = NULL;
314
315         if (isAssignment)
316         {
317                 Datum           sourceData;
318
319                 /*
320                  * Evaluate the value to be assigned into the array.
321                  *
322                  * XXX At some point we'll need to look into making the old value of
323                  * the array element available via CaseTestExpr, as is done by
324                  * ExecEvalFieldStore.  This is not needed now but will be needed
325                  * to support arrays of composite types; in an assignment to a field
326                  * of an array member, the parser would generate a FieldStore that
327                  * expects to fetch its input tuple via CaseTestExpr.
328                  */
329                 sourceData = ExecEvalExpr(astate->refassgnexpr,
330                                                                   econtext,
331                                                                   &eisnull,
332                                                                   NULL);
333
334                 /*
335                  * For now, can't cope with inserting NULL into an array, so make
336                  * it a no-op per discussion above...
337                  */
338                 if (eisnull)
339                         return PointerGetDatum(array_source);
340
341                 /*
342                  * For an assignment, if all the subscripts and the input expression
343                  * are non-null but the original array is null, then substitute an
344                  * empty (zero-dimensional) array and proceed with the assignment.
345                  * This only works for varlena arrays, though; for fixed-length
346                  * array types we punt and return the null input array.
347                  */
348                 if (*isNull)
349                 {
350                         if (astate->refattrlength > 0) /* fixed-length array? */
351                                 return PointerGetDatum(array_source);
352
353                         array_source = construct_md_array(NULL, 0, NULL, NULL,
354                                                                                           arrayRef->refelemtype,
355                                                                                           astate->refelemlength,
356                                                                                           astate->refelembyval,
357                                                                                           astate->refelemalign);
358                         *isNull = false;
359                 }
360
361                 if (lIndex == NULL)
362                         resultArray = array_set(array_source, i,
363                                                                         upper.indx,
364                                                                         sourceData,
365                                                                         astate->refattrlength,
366                                                                         astate->refelemlength,
367                                                                         astate->refelembyval,
368                                                                         astate->refelemalign,
369                                                                         isNull);
370                 else
371                         resultArray = array_set_slice(array_source, i,
372                                                                                   upper.indx, lower.indx,
373                                                            (ArrayType *) DatumGetPointer(sourceData),
374                                                                                   astate->refattrlength,
375                                                                                   astate->refelemlength,
376                                                                                   astate->refelembyval,
377                                                                                   astate->refelemalign,
378                                                                                   isNull);
379                 return PointerGetDatum(resultArray);
380         }
381
382         if (lIndex == NULL)
383                 return array_ref(array_source, i, upper.indx,
384                                                  astate->refattrlength,
385                                                  astate->refelemlength,
386                                                  astate->refelembyval,
387                                                  astate->refelemalign,
388                                                  isNull);
389         else
390         {
391                 resultArray = array_get_slice(array_source, i,
392                                                                           upper.indx, lower.indx,
393                                                                           astate->refattrlength,
394                                                                           astate->refelemlength,
395                                                                           astate->refelembyval,
396                                                                           astate->refelemalign,
397                                                                           isNull);
398                 return PointerGetDatum(resultArray);
399         }
400 }
401
402
403 /* ----------------------------------------------------------------
404  *              ExecEvalAggref
405  *
406  *              Returns a Datum whose value is the value of the precomputed
407  *              aggregate found in the given expression context.
408  * ----------------------------------------------------------------
409  */
410 static Datum
411 ExecEvalAggref(AggrefExprState *aggref, ExprContext *econtext,
412                            bool *isNull, ExprDoneCond *isDone)
413 {
414         if (isDone)
415                 *isDone = ExprSingleResult;
416
417         if (econtext->ecxt_aggvalues == NULL)           /* safety check */
418                 elog(ERROR, "no aggregates in this expression context");
419
420         *isNull = econtext->ecxt_aggnulls[aggref->aggno];
421         return econtext->ecxt_aggvalues[aggref->aggno];
422 }
423
424 /* ----------------------------------------------------------------
425  *              ExecEvalVar
426  *
427  *              Returns a Datum whose value is the value of a range
428  *              variable with respect to given expression context.
429  * ---------------------------------------------------------------- */
430 static Datum
431 ExecEvalVar(ExprState *exprstate, ExprContext *econtext,
432                         bool *isNull, ExprDoneCond *isDone)
433 {
434         Var                *variable = (Var *) exprstate->expr;
435         Datum           result;
436         TupleTableSlot *slot;
437         AttrNumber      attnum;
438         HeapTuple       heapTuple;
439         TupleDesc       tuple_type;
440
441         if (isDone)
442                 *isDone = ExprSingleResult;
443
444         /*
445          * Get the slot and attribute number we want
446          *
447          * The asserts check that references to system attributes only appear
448          * at the level of a relation scan; at higher levels, system attributes
449          * must be treated as ordinary variables (since we no longer have access
450          * to the original tuple).
451          */
452         attnum = variable->varattno;
453
454         switch (variable->varno)
455         {
456                 case INNER:                             /* get the tuple from the inner node */
457                         slot = econtext->ecxt_innertuple;
458                         Assert(attnum > 0);
459                         break;
460
461                 case OUTER:                             /* get the tuple from the outer node */
462                         slot = econtext->ecxt_outertuple;
463                         Assert(attnum > 0);
464                         break;
465
466                 default:                                /* get the tuple from the relation being
467                                                                  * scanned */
468                         slot = econtext->ecxt_scantuple;
469                         break;
470         }
471
472         /*
473          * extract tuple information from the slot
474          */
475         heapTuple = slot->val;
476         tuple_type = slot->ttc_tupleDescriptor;
477
478         /*
479          * Some checks that are only applied for user attribute numbers
480          * (bogus system attnums will be caught inside heap_getattr).
481          */
482         if (attnum > 0)
483         {
484                 /*
485                  * This assert checks that the attnum is valid.
486                  */
487                 Assert(attnum <= tuple_type->natts &&
488                            tuple_type->attrs[attnum - 1] != NULL);
489
490                 /*
491                  * If the attribute's column has been dropped, we force a NULL result.
492                  * This case should not happen in normal use, but it could happen if
493                  * we are executing a plan cached before the column was dropped.
494                  */
495                 if (tuple_type->attrs[attnum - 1]->attisdropped)
496                 {
497                         *isNull = true;
498                         return (Datum) 0;
499                 }
500
501                 /*
502                  * This assert checks that the datatype the plan expects to get (as
503                  * told by our "variable" argument) is in fact the datatype of the
504                  * attribute being fetched (as seen in the current context, identified
505                  * by our "econtext" argument).  Otherwise crashes are likely.
506                  *
507                  * Note that we can't check dropped columns, since their atttypid
508                  * has been zeroed.
509                  */
510                 Assert(variable->vartype == tuple_type->attrs[attnum - 1]->atttypid);
511         }
512
513         result = heap_getattr(heapTuple,        /* tuple containing attribute */
514                                                   attnum,               /* attribute number of desired
515                                                                                  * attribute */
516                                                   tuple_type,   /* tuple descriptor of tuple */
517                                                   isNull);              /* return: is attribute null? */
518
519         return result;
520 }
521
522 /* ----------------------------------------------------------------
523  *              ExecEvalConst
524  *
525  *              Returns the value of a constant.
526  *
527  *              Note that for pass-by-ref datatypes, we return a pointer to the
528  *              actual constant node.  This is one of the reasons why functions
529  *              must treat their input arguments as read-only.
530  * ----------------------------------------------------------------
531  */
532 static Datum
533 ExecEvalConst(ExprState *exprstate, ExprContext *econtext,
534                           bool *isNull, ExprDoneCond *isDone)
535 {
536         Const      *con = (Const *) exprstate->expr;
537
538         if (isDone)
539                 *isDone = ExprSingleResult;
540
541         *isNull = con->constisnull;
542         return con->constvalue;
543 }
544
545 /* ----------------------------------------------------------------
546  *              ExecEvalParam
547  *
548  *              Returns the value of a parameter.  A param node contains
549  *              something like ($.name) and the expression context contains
550  *              the current parameter bindings (name = "sam") (age = 34)...
551  *              so our job is to find and return the appropriate datum ("sam").
552  *
553  *              Q: if we have a parameter ($.foo) without a binding, i.e.
554  *                 there is no (foo = xxx) in the parameter list info,
555  *                 is this a fatal error or should this be a "not available"
556  *                 (in which case we could return NULL)?        -cim 10/13/89
557  * ----------------------------------------------------------------
558  */
559 static Datum
560 ExecEvalParam(ExprState *exprstate, ExprContext *econtext,
561                           bool *isNull, ExprDoneCond *isDone)
562 {
563         Param      *expression = (Param *) exprstate->expr;
564         int                     thisParamKind = expression->paramkind;
565         AttrNumber      thisParamId = expression->paramid;
566
567         if (isDone)
568                 *isDone = ExprSingleResult;
569
570         if (thisParamKind == PARAM_EXEC)
571         {
572                 /*
573                  * PARAM_EXEC params (internal executor parameters) are stored in
574                  * the ecxt_param_exec_vals array, and can be accessed by array
575                  * index.
576                  */
577                 ParamExecData *prm;
578
579                 prm = &(econtext->ecxt_param_exec_vals[thisParamId]);
580                 if (prm->execPlan != NULL)
581                 {
582                         /* Parameter not evaluated yet, so go do it */
583                         ExecSetParamPlan(prm->execPlan, econtext);
584                         /* ExecSetParamPlan should have processed this param... */
585                         Assert(prm->execPlan == NULL);
586                 }
587                 *isNull = prm->isnull;
588                 return prm->value;
589         }
590         else
591         {
592                 /*
593                  * All other parameter types must be sought in ecxt_param_list_info.
594                  */
595                 ParamListInfo paramInfo;
596
597                 paramInfo = lookupParam(econtext->ecxt_param_list_info,
598                                                                 thisParamKind,
599                                                                 expression->paramname,
600                                                                 thisParamId,
601                                                                 false);
602                 Assert(paramInfo->ptype == expression->paramtype);
603                 *isNull = paramInfo->isnull;
604                 return paramInfo->value;
605         }
606 }
607
608
609 /* ----------------------------------------------------------------
610  *              ExecEvalOper / ExecEvalFunc support routines
611  * ----------------------------------------------------------------
612  */
613
614 /*
615  *              GetAttributeByName
616  *              GetAttributeByNum
617  *
618  *              These functions return the value of the requested attribute
619  *              out of the given tuple Datum.
620  *              C functions which take a tuple as an argument are expected
621  *              to use these.  Ex: overpaid(EMP) might call GetAttributeByNum().
622  *              Note: these are actually rather slow because they do a typcache
623  *              lookup on each call.
624  */
625 Datum
626 GetAttributeByNum(HeapTupleHeader tuple,
627                                   AttrNumber attrno,
628                                   bool *isNull)
629 {
630         Datum           result;
631         Oid                     tupType;
632         int32           tupTypmod;
633         TupleDesc       tupDesc;
634         HeapTupleData tmptup;
635
636         if (!AttributeNumberIsValid(attrno))
637                 elog(ERROR, "invalid attribute number %d", attrno);
638
639         if (isNull == NULL)
640                 elog(ERROR, "a NULL isNull pointer was passed");
641
642         if (tuple == NULL)
643         {
644                 /* Kinda bogus but compatible with old behavior... */
645                 *isNull = true;
646                 return (Datum) 0;
647         }
648
649         tupType = HeapTupleHeaderGetTypeId(tuple);
650         tupTypmod = HeapTupleHeaderGetTypMod(tuple);
651         tupDesc = lookup_rowtype_tupdesc(tupType, tupTypmod);
652
653         /*
654          * heap_getattr needs a HeapTuple not a bare HeapTupleHeader.  We set
655          * all the fields in the struct just in case user tries to inspect
656          * system columns.
657          */
658         tmptup.t_len = HeapTupleHeaderGetDatumLength(tuple);
659         ItemPointerSetInvalid(&(tmptup.t_self));
660         tmptup.t_tableOid = InvalidOid;
661         tmptup.t_data = tuple;
662
663         result = heap_getattr(&tmptup,
664                                                   attrno,
665                                                   tupDesc,
666                                                   isNull);
667         return result;
668 }
669
670 Datum
671 GetAttributeByName(HeapTupleHeader tuple, const char *attname, bool *isNull)
672 {
673         AttrNumber      attrno;
674         Datum           result;
675         Oid                     tupType;
676         int32           tupTypmod;
677         TupleDesc       tupDesc;
678         HeapTupleData tmptup;
679         int                     i;
680
681         if (attname == NULL)
682                 elog(ERROR, "invalid attribute name");
683
684         if (isNull == NULL)
685                 elog(ERROR, "a NULL isNull pointer was passed");
686
687         if (tuple == NULL)
688         {
689                 /* Kinda bogus but compatible with old behavior... */
690                 *isNull = true;
691                 return (Datum) 0;
692         }
693
694         tupType = HeapTupleHeaderGetTypeId(tuple);
695         tupTypmod = HeapTupleHeaderGetTypMod(tuple);
696         tupDesc = lookup_rowtype_tupdesc(tupType, tupTypmod);
697
698         attrno = InvalidAttrNumber;
699         for (i = 0; i < tupDesc->natts; i++)
700         {
701                 if (namestrcmp(&(tupDesc->attrs[i]->attname), attname) == 0)
702                 {
703                         attrno = tupDesc->attrs[i]->attnum;
704                         break;
705                 }
706         }
707
708         if (attrno == InvalidAttrNumber)
709                 elog(ERROR, "attribute \"%s\" does not exist", attname);
710
711         /*
712          * heap_getattr needs a HeapTuple not a bare HeapTupleHeader.  We set
713          * all the fields in the struct just in case user tries to inspect
714          * system columns.
715          */
716         tmptup.t_len = HeapTupleHeaderGetDatumLength(tuple);
717         ItemPointerSetInvalid(&(tmptup.t_self));
718         tmptup.t_tableOid = InvalidOid;
719         tmptup.t_data = tuple;
720
721         result = heap_getattr(&tmptup,
722                                                   attrno,
723                                                   tupDesc,
724                                                   isNull);
725         return result;
726 }
727
728 /*
729  * init_fcache - initialize a FuncExprState node during first use
730  */
731 void
732 init_fcache(Oid foid, FuncExprState *fcache, MemoryContext fcacheCxt)
733 {
734         AclResult       aclresult;
735
736         /* Check permission to call function */
737         aclresult = pg_proc_aclcheck(foid, GetUserId(), ACL_EXECUTE);
738         if (aclresult != ACLCHECK_OK)
739                 aclcheck_error(aclresult, ACL_KIND_PROC, get_func_name(foid));
740
741         /* Safety check (should never fail, as parser should check sooner) */
742         if (list_length(fcache->args) > FUNC_MAX_ARGS)
743                 elog(ERROR, "too many arguments");
744
745         /* Set up the primary fmgr lookup information */
746         fmgr_info_cxt(foid, &(fcache->func), fcacheCxt);
747
748         /* Initialize additional info */
749         fcache->setArgsValid = false;
750         fcache->shutdown_reg = false;
751         fcache->func.fn_expr = (Node *) fcache->xprstate.expr;
752 }
753
754 /*
755  * callback function in case a FuncExpr returning a set needs to be shut down
756  * before it has been run to completion
757  */
758 static void
759 ShutdownFuncExpr(Datum arg)
760 {
761         FuncExprState *fcache = (FuncExprState *) DatumGetPointer(arg);
762
763         /* Clear any active set-argument state */
764         fcache->setArgsValid = false;
765
766         /* execUtils will deregister the callback... */
767         fcache->shutdown_reg = false;
768 }
769
770 /*
771  * Evaluate arguments for a function.
772  */
773 static ExprDoneCond
774 ExecEvalFuncArgs(FunctionCallInfo fcinfo,
775                                  List *argList,
776                                  ExprContext *econtext)
777 {
778         ExprDoneCond argIsDone;
779         int                     i;
780         ListCell   *arg;
781
782         argIsDone = ExprSingleResult;           /* default assumption */
783
784         i = 0;
785         foreach(arg, argList)
786         {
787                 ExprState  *argstate = (ExprState *) lfirst(arg);
788                 ExprDoneCond thisArgIsDone;
789
790                 fcinfo->arg[i] = ExecEvalExpr(argstate,
791                                                                           econtext,
792                                                                           &fcinfo->argnull[i],
793                                                                           &thisArgIsDone);
794
795                 if (thisArgIsDone != ExprSingleResult)
796                 {
797                         /*
798                          * We allow only one argument to have a set value; we'd need
799                          * much more complexity to keep track of multiple set
800                          * arguments (cf. ExecTargetList) and it doesn't seem worth
801                          * it.
802                          */
803                         if (argIsDone != ExprSingleResult)
804                                 ereport(ERROR,
805                                                 (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
806                                                  errmsg("functions and operators can take at most one set argument")));
807                         argIsDone = thisArgIsDone;
808                 }
809                 i++;
810         }
811
812         fcinfo->nargs = i;
813
814         return argIsDone;
815 }
816
817 /*
818  *              ExecMakeFunctionResult
819  *
820  * Evaluate the arguments to a function and then the function itself.
821  */
822 Datum
823 ExecMakeFunctionResult(FuncExprState *fcache,
824                                            ExprContext *econtext,
825                                            bool *isNull,
826                                            ExprDoneCond *isDone)
827 {
828         List       *arguments = fcache->args;
829         Datum           result;
830         FunctionCallInfoData fcinfo;
831         ReturnSetInfo rsinfo;           /* for functions returning sets */
832         ExprDoneCond argDone;
833         bool            hasSetArg;
834         int                     i;
835
836         /* Guard against stack overflow due to overly complex expressions */
837         check_stack_depth();
838
839         /*
840          * arguments is a list of expressions to evaluate before passing to
841          * the function manager.  We skip the evaluation if it was already
842          * done in the previous call (ie, we are continuing the evaluation of
843          * a set-valued function).      Otherwise, collect the current argument
844          * values into fcinfo.
845          */
846         if (!fcache->setArgsValid)
847         {
848                 /* Need to prep callinfo structure */
849                 MemSet(&fcinfo, 0, sizeof(fcinfo));
850                 fcinfo.flinfo = &(fcache->func);
851                 argDone = ExecEvalFuncArgs(&fcinfo, arguments, econtext);
852                 if (argDone == ExprEndResult)
853                 {
854                         /* input is an empty set, so return an empty set. */
855                         *isNull = true;
856                         if (isDone)
857                                 *isDone = ExprEndResult;
858                         else
859                                 ereport(ERROR,
860                                                 (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
861                                                  errmsg("set-valued function called in context that cannot accept a set")));
862                         return (Datum) 0;
863                 }
864                 hasSetArg = (argDone != ExprSingleResult);
865         }
866         else
867         {
868                 /* Copy callinfo from previous evaluation */
869                 memcpy(&fcinfo, &fcache->setArgs, sizeof(fcinfo));
870                 hasSetArg = fcache->setHasSetArg;
871                 /* Reset flag (we may set it again below) */
872                 fcache->setArgsValid = false;
873         }
874
875         /*
876          * If function returns set, prepare a resultinfo node for
877          * communication
878          */
879         if (fcache->func.fn_retset)
880         {
881                 fcinfo.resultinfo = (Node *) &rsinfo;
882                 rsinfo.type = T_ReturnSetInfo;
883                 rsinfo.econtext = econtext;
884                 rsinfo.expectedDesc = NULL;
885                 rsinfo.allowedModes = (int) SFRM_ValuePerCall;
886                 rsinfo.returnMode = SFRM_ValuePerCall;
887                 /* isDone is filled below */
888                 rsinfo.setResult = NULL;
889                 rsinfo.setDesc = NULL;
890         }
891
892         /*
893          * now return the value gotten by calling the function manager,
894          * passing the function the evaluated parameter values.
895          */
896         if (fcache->func.fn_retset || hasSetArg)
897         {
898                 /*
899                  * We need to return a set result.      Complain if caller not ready
900                  * to accept one.
901                  */
902                 if (isDone == NULL)
903                         ereport(ERROR,
904                                         (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
905                                          errmsg("set-valued function called in context that cannot accept a set")));
906
907                 /*
908                  * This loop handles the situation where we have both a set
909                  * argument and a set-valued function.  Once we have exhausted the
910                  * function's value(s) for a particular argument value, we have to
911                  * get the next argument value and start the function over again.
912                  * We might have to do it more than once, if the function produces
913                  * an empty result set for a particular input value.
914                  */
915                 for (;;)
916                 {
917                         /*
918                          * If function is strict, and there are any NULL arguments,
919                          * skip calling the function (at least for this set of args).
920                          */
921                         bool            callit = true;
922
923                         if (fcache->func.fn_strict)
924                         {
925                                 for (i = 0; i < fcinfo.nargs; i++)
926                                 {
927                                         if (fcinfo.argnull[i])
928                                         {
929                                                 callit = false;
930                                                 break;
931                                         }
932                                 }
933                         }
934
935                         if (callit)
936                         {
937                                 fcinfo.isnull = false;
938                                 rsinfo.isDone = ExprSingleResult;
939                                 result = FunctionCallInvoke(&fcinfo);
940                                 *isNull = fcinfo.isnull;
941                                 *isDone = rsinfo.isDone;
942                         }
943                         else
944                         {
945                                 result = (Datum) 0;
946                                 *isNull = true;
947                                 *isDone = ExprEndResult;
948                         }
949
950                         if (*isDone != ExprEndResult)
951                         {
952                                 /*
953                                  * Got a result from current argument.  If function itself
954                                  * returns set, save the current argument values to re-use
955                                  * on the next call.
956                                  */
957                                 if (fcache->func.fn_retset)
958                                 {
959                                         memcpy(&fcache->setArgs, &fcinfo, sizeof(fcinfo));
960                                         fcache->setHasSetArg = hasSetArg;
961                                         fcache->setArgsValid = true;
962                                         /* Register cleanup callback if we didn't already */
963                                         if (!fcache->shutdown_reg)
964                                         {
965                                                 RegisterExprContextCallback(econtext,
966                                                                                                         ShutdownFuncExpr,
967                                                                                                         PointerGetDatum(fcache));
968                                                 fcache->shutdown_reg = true;
969                                         }
970                                 }
971
972                                 /*
973                                  * Make sure we say we are returning a set, even if the
974                                  * function itself doesn't return sets.
975                                  */
976                                 *isDone = ExprMultipleResult;
977                                 break;
978                         }
979
980                         /* Else, done with this argument */
981                         if (!hasSetArg)
982                                 break;                  /* input not a set, so done */
983
984                         /* Re-eval args to get the next element of the input set */
985                         argDone = ExecEvalFuncArgs(&fcinfo, arguments, econtext);
986
987                         if (argDone != ExprMultipleResult)
988                         {
989                                 /* End of argument set, so we're done. */
990                                 *isNull = true;
991                                 *isDone = ExprEndResult;
992                                 result = (Datum) 0;
993                                 break;
994                         }
995
996                         /*
997                          * If we reach here, loop around to run the function on the
998                          * new argument.
999                          */
1000                 }
1001         }
1002         else
1003         {
1004                 /*
1005                  * Non-set case: much easier.
1006                  *
1007                  * We change the ExprState function pointer to use the simpler
1008                  * ExecMakeFunctionResultNoSets on subsequent calls.  This amounts
1009                  * to assuming that no argument can return a set if it didn't do so
1010                  * the first time.
1011                  */
1012                 fcache->xprstate.evalfunc = (ExprStateEvalFunc) ExecMakeFunctionResultNoSets;
1013
1014                 if (isDone)
1015                         *isDone = ExprSingleResult;
1016
1017                 /*
1018                  * If function is strict, and there are any NULL arguments, skip
1019                  * calling the function and return NULL.
1020                  */
1021                 if (fcache->func.fn_strict)
1022                 {
1023                         for (i = 0; i < fcinfo.nargs; i++)
1024                         {
1025                                 if (fcinfo.argnull[i])
1026                                 {
1027                                         *isNull = true;
1028                                         return (Datum) 0;
1029                                 }
1030                         }
1031                 }
1032                 fcinfo.isnull = false;
1033                 result = FunctionCallInvoke(&fcinfo);
1034                 *isNull = fcinfo.isnull;
1035         }
1036
1037         return result;
1038 }
1039
1040 /*
1041  *              ExecMakeFunctionResultNoSets
1042  *
1043  * Simplified version of ExecMakeFunctionResult that can only handle
1044  * non-set cases.  Hand-tuned for speed.
1045  */
1046 static Datum
1047 ExecMakeFunctionResultNoSets(FuncExprState *fcache,
1048                                                          ExprContext *econtext,
1049                                                          bool *isNull,
1050                                                          ExprDoneCond *isDone)
1051 {
1052         ListCell   *arg;
1053         Datum           result;
1054         FunctionCallInfoData fcinfo;
1055         int                     i;
1056
1057         /* Guard against stack overflow due to overly complex expressions */
1058         check_stack_depth();
1059
1060         if (isDone)
1061                 *isDone = ExprSingleResult;
1062
1063         MemSet(&fcinfo, 0, sizeof(fcinfo));
1064         fcinfo.flinfo = &(fcache->func);
1065
1066         /* inlined, simplified version of ExecEvalFuncArgs */
1067         i = 0;
1068         foreach(arg, fcache->args)
1069         {
1070                 ExprState  *argstate = (ExprState *) lfirst(arg);
1071                 ExprDoneCond thisArgIsDone;
1072
1073                 fcinfo.arg[i] = ExecEvalExpr(argstate,
1074                                                                          econtext,
1075                                                                          &fcinfo.argnull[i],
1076                                                                          &thisArgIsDone);
1077
1078                 if (thisArgIsDone != ExprSingleResult)
1079                         ereport(ERROR,
1080                                         (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
1081                                          errmsg("set-valued function called in context that cannot accept a set")));
1082                 i++;
1083         }
1084         fcinfo.nargs = i;
1085
1086         /*
1087          * If function is strict, and there are any NULL arguments, skip
1088          * calling the function and return NULL.
1089          */
1090         if (fcache->func.fn_strict)
1091         {
1092                 while (--i >= 0)
1093                 {
1094                         if (fcinfo.argnull[i])
1095                         {
1096                                 *isNull = true;
1097                                 return (Datum) 0;
1098                         }
1099                 }
1100         }
1101         /* fcinfo.isnull = false; */            /* handled by MemSet */
1102         result = FunctionCallInvoke(&fcinfo);
1103         *isNull = fcinfo.isnull;
1104
1105         return result;
1106 }
1107
1108
1109 /*
1110  *              ExecMakeTableFunctionResult
1111  *
1112  * Evaluate a table function, producing a materialized result in a Tuplestore
1113  * object.      (If function returns an empty set, we just return NULL instead.)
1114  */
1115 Tuplestorestate *
1116 ExecMakeTableFunctionResult(ExprState *funcexpr,
1117                                                         ExprContext *econtext,
1118                                                         TupleDesc expectedDesc,
1119                                                         TupleDesc *returnDesc)
1120 {
1121         Tuplestorestate *tupstore = NULL;
1122         TupleDesc       tupdesc = NULL;
1123         Oid                     funcrettype;
1124         bool            returnsTuple;
1125         FunctionCallInfoData fcinfo;
1126         ReturnSetInfo rsinfo;
1127         HeapTupleData tmptup;
1128         MemoryContext callerContext;
1129         MemoryContext oldcontext;
1130         bool            direct_function_call;
1131         bool            first_time = true;
1132
1133         /*
1134          * Normally the passed expression tree will be a FuncExprState, since
1135          * the grammar only allows a function call at the top level of a table
1136          * function reference.  However, if the function doesn't return set
1137          * then the planner might have replaced the function call via
1138          * constant-folding or inlining.  So if we see any other kind of
1139          * expression node, execute it via the general ExecEvalExpr() code;
1140          * the only difference is that we don't get a chance to pass a special
1141          * ReturnSetInfo to any functions buried in the expression.
1142          */
1143         if (funcexpr && IsA(funcexpr, FuncExprState) &&
1144                 IsA(funcexpr->expr, FuncExpr))
1145         {
1146                 FuncExprState *fcache = (FuncExprState *) funcexpr;
1147                 ExprDoneCond argDone;
1148
1149                 /*
1150                  * This path is similar to ExecMakeFunctionResult.
1151                  */
1152                 direct_function_call = true;
1153
1154                 /*
1155                  * Initialize function cache if first time through
1156                  */
1157                 if (fcache->func.fn_oid == InvalidOid)
1158                 {
1159                         FuncExpr   *func = (FuncExpr *) fcache->xprstate.expr;
1160
1161                         init_fcache(func->funcid, fcache, econtext->ecxt_per_query_memory);
1162                 }
1163
1164                 /*
1165                  * Evaluate the function's argument list.
1166                  *
1167                  * Note: ideally, we'd do this in the per-tuple context, but then the
1168                  * argument values would disappear when we reset the context in
1169                  * the inner loop.      So do it in caller context.  Perhaps we should
1170                  * make a separate context just to hold the evaluated arguments?
1171                  */
1172                 MemSet(&fcinfo, 0, sizeof(fcinfo));
1173                 fcinfo.flinfo = &(fcache->func);
1174                 argDone = ExecEvalFuncArgs(&fcinfo, fcache->args, econtext);
1175                 /* We don't allow sets in the arguments of the table function */
1176                 if (argDone != ExprSingleResult)
1177                         ereport(ERROR,
1178                                         (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
1179                                          errmsg("set-valued function called in context that cannot accept a set")));
1180
1181                 /*
1182                  * If function is strict, and there are any NULL arguments, skip
1183                  * calling the function and return NULL (actually an empty set).
1184                  */
1185                 if (fcache->func.fn_strict)
1186                 {
1187                         int                     i;
1188
1189                         for (i = 0; i < fcinfo.nargs; i++)
1190                         {
1191                                 if (fcinfo.argnull[i])
1192                                 {
1193                                         *returnDesc = NULL;
1194                                         return NULL;
1195                                 }
1196                         }
1197                 }
1198         }
1199         else
1200         {
1201                 /* Treat funcexpr as a generic expression */
1202                 direct_function_call = false;
1203         }
1204
1205         funcrettype = exprType((Node *) funcexpr->expr);
1206
1207         returnsTuple = (funcrettype == RECORDOID ||
1208                                         get_typtype(funcrettype) == 'c');
1209
1210         /*
1211          * Prepare a resultinfo node for communication.  We always do this
1212          * even if not expecting a set result, so that we can pass
1213          * expectedDesc.  In the generic-expression case, the expression
1214          * doesn't actually get to see the resultinfo, but set it up anyway
1215          * because we use some of the fields as our own state variables.
1216          */
1217         fcinfo.resultinfo = (Node *) &rsinfo;
1218         rsinfo.type = T_ReturnSetInfo;
1219         rsinfo.econtext = econtext;
1220         rsinfo.expectedDesc = expectedDesc;
1221         rsinfo.allowedModes = (int) (SFRM_ValuePerCall | SFRM_Materialize);
1222         rsinfo.returnMode = SFRM_ValuePerCall;
1223         /* isDone is filled below */
1224         rsinfo.setResult = NULL;
1225         rsinfo.setDesc = NULL;
1226
1227         /*
1228          * Switch to short-lived context for calling the function or
1229          * expression.
1230          */
1231         callerContext = MemoryContextSwitchTo(econtext->ecxt_per_tuple_memory);
1232
1233         /*
1234          * Loop to handle the ValuePerCall protocol (which is also the same
1235          * behavior needed in the generic ExecEvalExpr path).
1236          */
1237         for (;;)
1238         {
1239                 Datum           result;
1240                 HeapTuple       tuple;
1241
1242                 /*
1243                  * reset per-tuple memory context before each call of the function
1244                  * or expression. This cleans up any local memory the function may
1245                  * leak when called.
1246                  */
1247                 ResetExprContext(econtext);
1248
1249                 /* Call the function or expression one time */
1250                 if (direct_function_call)
1251                 {
1252                         fcinfo.isnull = false;
1253                         rsinfo.isDone = ExprSingleResult;
1254                         result = FunctionCallInvoke(&fcinfo);
1255                 }
1256                 else
1257                 {
1258                         result = ExecEvalExpr(funcexpr, econtext,
1259                                                                   &fcinfo.isnull, &rsinfo.isDone);
1260                 }
1261
1262                 /* Which protocol does function want to use? */
1263                 if (rsinfo.returnMode == SFRM_ValuePerCall)
1264                 {
1265                         /*
1266                          * Check for end of result set.
1267                          *
1268                          * Note: if function returns an empty set, we don't build a
1269                          * tupdesc or tuplestore (since we can't get a tupdesc in the
1270                          * function-returning-tuple case)
1271                          */
1272                         if (rsinfo.isDone == ExprEndResult)
1273                                 break;
1274
1275                         /*
1276                          * Can't do anything useful with NULL rowtype values.  Currently
1277                          * we raise an error, but another alternative is to just ignore
1278                          * the result and "continue" to get another row.
1279                          */
1280                         if (returnsTuple && fcinfo.isnull)
1281                                 ereport(ERROR,
1282                                                 (errcode(ERRCODE_NULL_VALUE_NOT_ALLOWED),
1283                                                  errmsg("function returning row cannot return null value")));
1284
1285                         /*
1286                          * If first time through, build tupdesc and tuplestore for
1287                          * result
1288                          */
1289                         if (first_time)
1290                         {
1291                                 oldcontext = MemoryContextSwitchTo(econtext->ecxt_per_query_memory);
1292                                 if (returnsTuple)
1293                                 {
1294                                         /*
1295                                          * Use the type info embedded in the rowtype Datum to
1296                                          * look up the needed tupdesc.  Make a copy for the query.
1297                                          */
1298                                         HeapTupleHeader td;
1299
1300                                         td = DatumGetHeapTupleHeader(result);
1301                                         tupdesc = lookup_rowtype_tupdesc(HeapTupleHeaderGetTypeId(td),
1302                                                                                                          HeapTupleHeaderGetTypMod(td));
1303                                         tupdesc = CreateTupleDescCopy(tupdesc);
1304                                 }
1305                                 else
1306                                 {
1307                                         /*
1308                                          * Scalar type, so make a single-column descriptor
1309                                          */
1310                                         tupdesc = CreateTemplateTupleDesc(1, false);
1311                                         TupleDescInitEntry(tupdesc,
1312                                                                            (AttrNumber) 1,
1313                                                                            "column",
1314                                                                            funcrettype,
1315                                                                            -1,
1316                                                                            0);
1317                                 }
1318                                 tupstore = tuplestore_begin_heap(true, false, work_mem);
1319                                 MemoryContextSwitchTo(oldcontext);
1320                                 rsinfo.setResult = tupstore;
1321                                 rsinfo.setDesc = tupdesc;
1322                         }
1323
1324                         /*
1325                          * Store current resultset item.
1326                          */
1327                         if (returnsTuple)
1328                         {
1329                                 HeapTupleHeader td;
1330
1331                                 td = DatumGetHeapTupleHeader(result);
1332
1333                                 /*
1334                                  * tuplestore_puttuple needs a HeapTuple not a bare
1335                                  * HeapTupleHeader, but it doesn't need all the fields.
1336                                  */
1337                                 tmptup.t_len = HeapTupleHeaderGetDatumLength(td);
1338                                 tmptup.t_data = td;
1339                                 tuple = &tmptup;
1340                         }
1341                         else
1342                         {
1343                                 char            nullflag;
1344
1345                                 nullflag = fcinfo.isnull ? 'n' : ' ';
1346                                 tuple = heap_formtuple(tupdesc, &result, &nullflag);
1347                         }
1348
1349                         oldcontext = MemoryContextSwitchTo(econtext->ecxt_per_query_memory);
1350                         tuplestore_puttuple(tupstore, tuple);
1351                         MemoryContextSwitchTo(oldcontext);
1352
1353                         /*
1354                          * Are we done?
1355                          */
1356                         if (rsinfo.isDone != ExprMultipleResult)
1357                                 break;
1358                 }
1359                 else if (rsinfo.returnMode == SFRM_Materialize)
1360                 {
1361                         /* check we're on the same page as the function author */
1362                         if (!first_time || rsinfo.isDone != ExprSingleResult)
1363                                 ereport(ERROR,
1364                                                 (errcode(ERRCODE_E_R_I_E_SRF_PROTOCOL_VIOLATED),
1365                                                  errmsg("table-function protocol for materialize mode was not followed")));
1366                         /* Done evaluating the set result */
1367                         break;
1368                 }
1369                 else
1370                         ereport(ERROR,
1371                                         (errcode(ERRCODE_E_R_I_E_SRF_PROTOCOL_VIOLATED),
1372                                          errmsg("unrecognized table-function returnMode: %d",
1373                                                         (int) rsinfo.returnMode)));
1374
1375                 first_time = false;
1376         }
1377
1378         MemoryContextSwitchTo(callerContext);
1379
1380         /* The returned pointers are those in rsinfo */
1381         *returnDesc = rsinfo.setDesc;
1382         return rsinfo.setResult;
1383 }
1384
1385
1386 /* ----------------------------------------------------------------
1387  *              ExecEvalFunc
1388  *              ExecEvalOper
1389  *
1390  *              Evaluate the functional result of a list of arguments by calling the
1391  *              function manager.
1392  * ----------------------------------------------------------------
1393  */
1394
1395 /* ----------------------------------------------------------------
1396  *              ExecEvalFunc
1397  * ----------------------------------------------------------------
1398  */
1399 static Datum
1400 ExecEvalFunc(FuncExprState *fcache,
1401                          ExprContext *econtext,
1402                          bool *isNull,
1403                          ExprDoneCond *isDone)
1404 {
1405         /* This is called only the first time through */
1406         FuncExpr   *func = (FuncExpr *) fcache->xprstate.expr;
1407
1408         /* Initialize function lookup info */
1409         init_fcache(func->funcid, fcache, econtext->ecxt_per_query_memory);
1410
1411         /* Go directly to ExecMakeFunctionResult on subsequent uses */
1412         fcache->xprstate.evalfunc = (ExprStateEvalFunc) ExecMakeFunctionResult;
1413
1414         return ExecMakeFunctionResult(fcache, econtext, isNull, isDone);
1415 }
1416
1417 /* ----------------------------------------------------------------
1418  *              ExecEvalOper
1419  * ----------------------------------------------------------------
1420  */
1421 static Datum
1422 ExecEvalOper(FuncExprState *fcache,
1423                          ExprContext *econtext,
1424                          bool *isNull,
1425                          ExprDoneCond *isDone)
1426 {
1427         /* This is called only the first time through */
1428         OpExpr     *op = (OpExpr *) fcache->xprstate.expr;
1429
1430         /* Initialize function lookup info */
1431         init_fcache(op->opfuncid, fcache, econtext->ecxt_per_query_memory);
1432
1433         /* Go directly to ExecMakeFunctionResult on subsequent uses */
1434         fcache->xprstate.evalfunc = (ExprStateEvalFunc) ExecMakeFunctionResult;
1435
1436         return ExecMakeFunctionResult(fcache, econtext, isNull, isDone);
1437 }
1438
1439 /* ----------------------------------------------------------------
1440  *              ExecEvalDistinct
1441  *
1442  * IS DISTINCT FROM must evaluate arguments to determine whether
1443  * they are NULL; if either is NULL then the result is already
1444  * known. If neither is NULL, then proceed to evaluate the
1445  * function. Note that this is *always* derived from the equals
1446  * operator, but since we need special processing of the arguments
1447  * we can not simply reuse ExecEvalOper() or ExecEvalFunc().
1448  * ----------------------------------------------------------------
1449  */
1450 static Datum
1451 ExecEvalDistinct(FuncExprState *fcache,
1452                                  ExprContext *econtext,
1453                                  bool *isNull,
1454                                  ExprDoneCond *isDone)
1455 {
1456         Datum           result;
1457         FunctionCallInfoData fcinfo;
1458         ExprDoneCond argDone;
1459         List       *argList;
1460
1461         /* Set default values for result flags: non-null, not a set result */
1462         *isNull = false;
1463         if (isDone)
1464                 *isDone = ExprSingleResult;
1465
1466         /*
1467          * Initialize function cache if first time through
1468          */
1469         if (fcache->func.fn_oid == InvalidOid)
1470         {
1471                 DistinctExpr *op = (DistinctExpr *) fcache->xprstate.expr;
1472
1473                 init_fcache(op->opfuncid, fcache, econtext->ecxt_per_query_memory);
1474                 Assert(!fcache->func.fn_retset);
1475         }
1476
1477         /*
1478          * extract info from fcache
1479          */
1480         argList = fcache->args;
1481
1482         /* Need to prep callinfo structure */
1483         MemSet(&fcinfo, 0, sizeof(fcinfo));
1484         fcinfo.flinfo = &(fcache->func);
1485         argDone = ExecEvalFuncArgs(&fcinfo, argList, econtext);
1486         if (argDone != ExprSingleResult)
1487                 ereport(ERROR,
1488                                 (errcode(ERRCODE_DATATYPE_MISMATCH),
1489                          errmsg("IS DISTINCT FROM does not support set arguments")));
1490         Assert(fcinfo.nargs == 2);
1491
1492         if (fcinfo.argnull[0] && fcinfo.argnull[1])
1493         {
1494                 /* Both NULL? Then is not distinct... */
1495                 result = BoolGetDatum(FALSE);
1496         }
1497         else if (fcinfo.argnull[0] || fcinfo.argnull[1])
1498         {
1499                 /* Only one is NULL? Then is distinct... */
1500                 result = BoolGetDatum(TRUE);
1501         }
1502         else
1503         {
1504                 fcinfo.isnull = false;
1505                 result = FunctionCallInvoke(&fcinfo);
1506                 *isNull = fcinfo.isnull;
1507                 /* Must invert result of "=" */
1508                 result = BoolGetDatum(!DatumGetBool(result));
1509         }
1510
1511         return result;
1512 }
1513
1514 /*
1515  * ExecEvalScalarArrayOp
1516  *
1517  * Evaluate "scalar op ANY/ALL (array)".  The operator always yields boolean,
1518  * and we combine the results across all array elements using OR and AND
1519  * (for ANY and ALL respectively).      Of course we short-circuit as soon as
1520  * the result is known.
1521  */
1522 static Datum
1523 ExecEvalScalarArrayOp(ScalarArrayOpExprState *sstate,
1524                                           ExprContext *econtext,
1525                                           bool *isNull, ExprDoneCond *isDone)
1526 {
1527         ScalarArrayOpExpr *opexpr = (ScalarArrayOpExpr *) sstate->fxprstate.xprstate.expr;
1528         bool            useOr = opexpr->useOr;
1529         ArrayType  *arr;
1530         int                     nitems;
1531         Datum           result;
1532         bool            resultnull;
1533         FunctionCallInfoData fcinfo;
1534         ExprDoneCond argDone;
1535         int                     i;
1536         int16           typlen;
1537         bool            typbyval;
1538         char            typalign;
1539         char       *s;
1540
1541         /* Set default values for result flags: non-null, not a set result */
1542         *isNull = false;
1543         if (isDone)
1544                 *isDone = ExprSingleResult;
1545
1546         /*
1547          * Initialize function cache if first time through
1548          */
1549         if (sstate->fxprstate.func.fn_oid == InvalidOid)
1550         {
1551                 init_fcache(opexpr->opfuncid, &sstate->fxprstate,
1552                                         econtext->ecxt_per_query_memory);
1553                 Assert(!sstate->fxprstate.func.fn_retset);
1554         }
1555
1556         /* Need to prep callinfo structure */
1557         MemSet(&fcinfo, 0, sizeof(fcinfo));
1558         fcinfo.flinfo = &(sstate->fxprstate.func);
1559         argDone = ExecEvalFuncArgs(&fcinfo, sstate->fxprstate.args, econtext);
1560         if (argDone != ExprSingleResult)
1561                 ereport(ERROR,
1562                                 (errcode(ERRCODE_DATATYPE_MISMATCH),
1563                    errmsg("op ANY/ALL (array) does not support set arguments")));
1564         Assert(fcinfo.nargs == 2);
1565
1566         /*
1567          * If the array is NULL then we return NULL --- it's not very
1568          * meaningful to do anything else, even if the operator isn't strict.
1569          */
1570         if (fcinfo.argnull[1])
1571         {
1572                 *isNull = true;
1573                 return (Datum) 0;
1574         }
1575         /* Else okay to fetch and detoast the array */
1576         arr = DatumGetArrayTypeP(fcinfo.arg[1]);
1577
1578         /*
1579          * If the array is empty, we return either FALSE or TRUE per the useOr
1580          * flag.  This is correct even if the scalar is NULL; since we would
1581          * evaluate the operator zero times, it matters not whether it would
1582          * want to return NULL.
1583          */
1584         nitems = ArrayGetNItems(ARR_NDIM(arr), ARR_DIMS(arr));
1585         if (nitems <= 0)
1586                 return BoolGetDatum(!useOr);
1587
1588         /*
1589          * If the scalar is NULL, and the function is strict, return NULL.
1590          * This is just to avoid having to test for strictness inside the
1591          * loop.  (XXX but if arrays could have null elements, we'd need a
1592          * test anyway.)
1593          */
1594         if (fcinfo.argnull[0] && sstate->fxprstate.func.fn_strict)
1595         {
1596                 *isNull = true;
1597                 return (Datum) 0;
1598         }
1599
1600         /*
1601          * We arrange to look up info about the element type only once per
1602          * series of calls, assuming the element type doesn't change
1603          * underneath us.
1604          */
1605         if (sstate->element_type != ARR_ELEMTYPE(arr))
1606         {
1607                 get_typlenbyvalalign(ARR_ELEMTYPE(arr),
1608                                                          &sstate->typlen,
1609                                                          &sstate->typbyval,
1610                                                          &sstate->typalign);
1611                 sstate->element_type = ARR_ELEMTYPE(arr);
1612         }
1613         typlen = sstate->typlen;
1614         typbyval = sstate->typbyval;
1615         typalign = sstate->typalign;
1616
1617         result = BoolGetDatum(!useOr);
1618         resultnull = false;
1619
1620         /* Loop over the array elements */
1621         s = (char *) ARR_DATA_PTR(arr);
1622         for (i = 0; i < nitems; i++)
1623         {
1624                 Datum           elt;
1625                 Datum           thisresult;
1626
1627                 /* Get array element */
1628                 elt = fetch_att(s, typbyval, typlen);
1629
1630                 s = att_addlength(s, typlen, PointerGetDatum(s));
1631                 s = (char *) att_align(s, typalign);
1632
1633                 /* Call comparison function */
1634                 fcinfo.arg[1] = elt;
1635                 fcinfo.argnull[1] = false;
1636                 fcinfo.isnull = false;
1637                 thisresult = FunctionCallInvoke(&fcinfo);
1638
1639                 /* Combine results per OR or AND semantics */
1640                 if (fcinfo.isnull)
1641                         resultnull = true;
1642                 else if (useOr)
1643                 {
1644                         if (DatumGetBool(thisresult))
1645                         {
1646                                 result = BoolGetDatum(true);
1647                                 resultnull = false;
1648                                 break;                  /* needn't look at any more elements */
1649                         }
1650                 }
1651                 else
1652                 {
1653                         if (!DatumGetBool(thisresult))
1654                         {
1655                                 result = BoolGetDatum(false);
1656                                 resultnull = false;
1657                                 break;                  /* needn't look at any more elements */
1658                         }
1659                 }
1660         }
1661
1662         *isNull = resultnull;
1663         return result;
1664 }
1665
1666 /* ----------------------------------------------------------------
1667  *              ExecEvalNot
1668  *              ExecEvalOr
1669  *              ExecEvalAnd
1670  *
1671  *              Evaluate boolean expressions, with appropriate short-circuiting.
1672  *
1673  *              The query planner reformulates clause expressions in the
1674  *              qualification to conjunctive normal form.  If we ever get
1675  *              an AND to evaluate, we can be sure that it's not a top-level
1676  *              clause in the qualification, but appears lower (as a function
1677  *              argument, for example), or in the target list.  Not that you
1678  *              need to know this, mind you...
1679  * ----------------------------------------------------------------
1680  */
1681 static Datum
1682 ExecEvalNot(BoolExprState *notclause, ExprContext *econtext,
1683                         bool *isNull, ExprDoneCond *isDone)
1684 {
1685         ExprState  *clause = linitial(notclause->args);
1686         Datum           expr_value;
1687
1688         if (isDone)
1689                 *isDone = ExprSingleResult;
1690
1691         expr_value = ExecEvalExpr(clause, econtext, isNull, NULL);
1692
1693         /*
1694          * if the expression evaluates to null, then we just cascade the null
1695          * back to whoever called us.
1696          */
1697         if (*isNull)
1698                 return expr_value;
1699
1700         /*
1701          * evaluation of 'not' is simple.. expr is false, then return 'true'
1702          * and vice versa.
1703          */
1704         return BoolGetDatum(!DatumGetBool(expr_value));
1705 }
1706
1707 /* ----------------------------------------------------------------
1708  *              ExecEvalOr
1709  * ----------------------------------------------------------------
1710  */
1711 static Datum
1712 ExecEvalOr(BoolExprState *orExpr, ExprContext *econtext,
1713                    bool *isNull, ExprDoneCond *isDone)
1714 {
1715         List       *clauses = orExpr->args;
1716         ListCell   *clause;
1717         bool            AnyNull;
1718
1719         if (isDone)
1720                 *isDone = ExprSingleResult;
1721
1722         AnyNull = false;
1723
1724         /*
1725          * If any of the clauses is TRUE, the OR result is TRUE regardless of
1726          * the states of the rest of the clauses, so we can stop evaluating
1727          * and return TRUE immediately.  If none are TRUE and one or more is
1728          * NULL, we return NULL; otherwise we return FALSE.  This makes sense
1729          * when you interpret NULL as "don't know": if we have a TRUE then the
1730          * OR is TRUE even if we aren't sure about some of the other inputs.
1731          * If all the known inputs are FALSE, but we have one or more "don't
1732          * knows", then we have to report that we "don't know" what the OR's
1733          * result should be --- perhaps one of the "don't knows" would have
1734          * been TRUE if we'd known its value.  Only when all the inputs are
1735          * known to be FALSE can we state confidently that the OR's result is
1736          * FALSE.
1737          */
1738         foreach(clause, clauses)
1739         {
1740                 ExprState  *clausestate = (ExprState *) lfirst(clause);
1741                 Datum           clause_value;
1742
1743                 clause_value = ExecEvalExpr(clausestate, econtext, isNull, NULL);
1744
1745                 /*
1746                  * if we have a non-null true result, then return it.
1747                  */
1748                 if (*isNull)
1749                         AnyNull = true;         /* remember we got a null */
1750                 else if (DatumGetBool(clause_value))
1751                         return clause_value;
1752         }
1753
1754         /* AnyNull is true if at least one clause evaluated to NULL */
1755         *isNull = AnyNull;
1756         return BoolGetDatum(false);
1757 }
1758
1759 /* ----------------------------------------------------------------
1760  *              ExecEvalAnd
1761  * ----------------------------------------------------------------
1762  */
1763 static Datum
1764 ExecEvalAnd(BoolExprState *andExpr, ExprContext *econtext,
1765                         bool *isNull, ExprDoneCond *isDone)
1766 {
1767         List       *clauses = andExpr->args;
1768         ListCell   *clause;
1769         bool            AnyNull;
1770
1771         if (isDone)
1772                 *isDone = ExprSingleResult;
1773
1774         AnyNull = false;
1775
1776         /*
1777          * If any of the clauses is FALSE, the AND result is FALSE regardless
1778          * of the states of the rest of the clauses, so we can stop evaluating
1779          * and return FALSE immediately.  If none are FALSE and one or more is
1780          * NULL, we return NULL; otherwise we return TRUE.      This makes sense
1781          * when you interpret NULL as "don't know", using the same sort of
1782          * reasoning as for OR, above.
1783          */
1784
1785         foreach(clause, clauses)
1786         {
1787                 ExprState  *clausestate = (ExprState *) lfirst(clause);
1788                 Datum           clause_value;
1789
1790                 clause_value = ExecEvalExpr(clausestate, econtext, isNull, NULL);
1791
1792                 /*
1793                  * if we have a non-null false result, then return it.
1794                  */
1795                 if (*isNull)
1796                         AnyNull = true;         /* remember we got a null */
1797                 else if (!DatumGetBool(clause_value))
1798                         return clause_value;
1799         }
1800
1801         /* AnyNull is true if at least one clause evaluated to NULL */
1802         *isNull = AnyNull;
1803         return BoolGetDatum(!AnyNull);
1804 }
1805
1806
1807 /* ----------------------------------------------------------------
1808  *              ExecEvalCase
1809  *
1810  *              Evaluate a CASE clause. Will have boolean expressions
1811  *              inside the WHEN clauses, and will have expressions
1812  *              for results.
1813  *              - thomas 1998-11-09
1814  * ----------------------------------------------------------------
1815  */
1816 static Datum
1817 ExecEvalCase(CaseExprState *caseExpr, ExprContext *econtext,
1818                          bool *isNull, ExprDoneCond *isDone)
1819 {
1820         List       *clauses = caseExpr->args;
1821         ListCell   *clause;
1822         Datum           save_datum;
1823         bool            save_isNull;
1824
1825         if (isDone)
1826                 *isDone = ExprSingleResult;
1827
1828         /*
1829          * If there's a test expression, we have to evaluate it and save
1830          * the value where the CaseTestExpr placeholders can find it.
1831          * We must save and restore prior setting of econtext's caseValue fields,
1832          * in case this node is itself within a larger CASE.
1833          */
1834         save_datum = econtext->caseValue_datum;
1835         save_isNull = econtext->caseValue_isNull;
1836
1837         if (caseExpr->arg)
1838         {
1839                 econtext->caseValue_datum = ExecEvalExpr(caseExpr->arg,
1840                                                                                                  econtext,
1841                                                                                                  &econtext->caseValue_isNull,
1842                                                                                                  NULL);
1843         }
1844
1845         /*
1846          * we evaluate each of the WHEN clauses in turn, as soon as one is
1847          * true we return the corresponding result. If none are true then we
1848          * return the value of the default clause, or NULL if there is none.
1849          */
1850         foreach(clause, clauses)
1851         {
1852                 CaseWhenState *wclause = lfirst(clause);
1853                 Datum           clause_value;
1854
1855                 clause_value = ExecEvalExpr(wclause->expr,
1856                                                                         econtext,
1857                                                                         isNull,
1858                                                                         NULL);
1859
1860                 /*
1861                  * if we have a true test, then we return the result, since the
1862                  * case statement is satisfied.  A NULL result from the test is
1863                  * not considered true.
1864                  */
1865                 if (DatumGetBool(clause_value) && !*isNull)
1866                 {
1867                         econtext->caseValue_datum = save_datum;
1868                         econtext->caseValue_isNull = save_isNull;
1869                         return ExecEvalExpr(wclause->result,
1870                                                                 econtext,
1871                                                                 isNull,
1872                                                                 isDone);
1873                 }
1874         }
1875
1876         econtext->caseValue_datum = save_datum;
1877         econtext->caseValue_isNull = save_isNull;
1878
1879         if (caseExpr->defresult)
1880         {
1881                 return ExecEvalExpr(caseExpr->defresult,
1882                                                         econtext,
1883                                                         isNull,
1884                                                         isDone);
1885         }
1886
1887         *isNull = true;
1888         return (Datum) 0;
1889 }
1890
1891 /*
1892  * ExecEvalCaseTestExpr
1893  *
1894  * Return the value stored by CASE.
1895  */
1896 static Datum
1897 ExecEvalCaseTestExpr(ExprState *exprstate,
1898                                          ExprContext *econtext,
1899                                          bool *isNull, ExprDoneCond *isDone)
1900 {
1901         if (isDone)
1902                 *isDone = ExprSingleResult;
1903         *isNull = econtext->caseValue_isNull;
1904         return econtext->caseValue_datum;
1905 }
1906
1907 /* ----------------------------------------------------------------
1908  *              ExecEvalArray - ARRAY[] expressions
1909  *
1910  * NOTE: currently, if any input value is NULL then we return a NULL array,
1911  * so the ARRAY[] construct can be considered strict.  Eventually this will
1912  * change; when it does, be sure to fix contain_nonstrict_functions().
1913  * ----------------------------------------------------------------
1914  */
1915 static Datum
1916 ExecEvalArray(ArrayExprState *astate, ExprContext *econtext,
1917                           bool *isNull, ExprDoneCond *isDone)
1918 {
1919         ArrayExpr  *arrayExpr = (ArrayExpr *) astate->xprstate.expr;
1920         ArrayType  *result;
1921         ListCell   *element;
1922         Oid                     element_type = arrayExpr->element_typeid;
1923         int                     ndims = 0;
1924         int                     dims[MAXDIM];
1925         int                     lbs[MAXDIM];
1926
1927         /* Set default values for result flags: non-null, not a set result */
1928         *isNull = false;
1929         if (isDone)
1930                 *isDone = ExprSingleResult;
1931
1932         if (!arrayExpr->multidims)
1933         {
1934                 /* Elements are presumably of scalar type */
1935                 int                     nelems;
1936                 Datum      *dvalues;
1937                 int                     i = 0;
1938
1939                 ndims = 1;
1940                 nelems = list_length(astate->elements);
1941
1942                 /* Shouldn't happen here, but if length is 0, return NULL */
1943                 if (nelems == 0)
1944                 {
1945                         *isNull = true;
1946                         return (Datum) 0;
1947                 }
1948
1949                 dvalues = (Datum *) palloc(nelems * sizeof(Datum));
1950
1951                 /* loop through and build array of datums */
1952                 foreach(element, astate->elements)
1953                 {
1954                         ExprState  *e = (ExprState *) lfirst(element);
1955                         bool            eisnull;
1956
1957                         dvalues[i++] = ExecEvalExpr(e, econtext, &eisnull, NULL);
1958                         if (eisnull)
1959                         {
1960                                 *isNull = true;
1961                                 return (Datum) 0;
1962                         }
1963                 }
1964
1965                 /* setup for 1-D array of the given length */
1966                 dims[0] = nelems;
1967                 lbs[0] = 1;
1968
1969                 result = construct_md_array(dvalues, ndims, dims, lbs,
1970                                                                         element_type,
1971                                                                         astate->elemlength,
1972                                                                         astate->elembyval,
1973                                                                         astate->elemalign);
1974         }
1975         else
1976         {
1977                 /* Must be nested array expressions */
1978                 char       *dat = NULL;
1979                 Size            ndatabytes = 0;
1980                 int                     nbytes;
1981                 int                     outer_nelems = list_length(astate->elements);
1982                 int                     elem_ndims = 0;
1983                 int                *elem_dims = NULL;
1984                 int                *elem_lbs = NULL;
1985                 bool            firstone = true;
1986                 int                     i;
1987
1988                 /* loop through and get data area from each element */
1989                 foreach(element, astate->elements)
1990                 {
1991                         ExprState  *e = (ExprState *) lfirst(element);
1992                         bool            eisnull;
1993                         Datum           arraydatum;
1994                         ArrayType  *array;
1995                         int                     elem_ndatabytes;
1996
1997                         arraydatum = ExecEvalExpr(e, econtext, &eisnull, NULL);
1998                         if (eisnull)
1999                         {
2000                                 *isNull = true;
2001                                 return (Datum) 0;
2002                         }
2003
2004                         array = DatumGetArrayTypeP(arraydatum);
2005
2006                         /* run-time double-check on element type */
2007                         if (element_type != ARR_ELEMTYPE(array))
2008                                 ereport(ERROR,
2009                                                 (errcode(ERRCODE_DATATYPE_MISMATCH),
2010                                                  errmsg("cannot merge incompatible arrays"),
2011                                                  errdetail("Array with element type %s cannot be "
2012                                                                    "included in ARRAY construct with element type %s.",
2013                                                                    format_type_be(ARR_ELEMTYPE(array)),
2014                                                                    format_type_be(element_type))));
2015
2016                         if (firstone)
2017                         {
2018                                 /* Get sub-array details from first member */
2019                                 elem_ndims = ARR_NDIM(array);
2020                                 ndims = elem_ndims + 1;
2021                                 if (ndims <= 0 || ndims > MAXDIM)
2022                                         ereport(ERROR,
2023                                                         (errcode(ERRCODE_PROGRAM_LIMIT_EXCEEDED),
2024                                                          errmsg("number of array dimensions (%d) exceeds " \
2025                                                                         "the maximum allowed (%d)", ndims, MAXDIM)));
2026
2027                                 elem_dims = (int *) palloc(elem_ndims * sizeof(int));
2028                                 memcpy(elem_dims, ARR_DIMS(array), elem_ndims * sizeof(int));
2029                                 elem_lbs = (int *) palloc(elem_ndims * sizeof(int));
2030                                 memcpy(elem_lbs, ARR_LBOUND(array), elem_ndims * sizeof(int));
2031
2032                                 firstone = false;
2033                         }
2034                         else
2035                         {
2036                                 /* Check other sub-arrays are compatible */
2037                                 if (elem_ndims != ARR_NDIM(array) ||
2038                                         memcmp(elem_dims, ARR_DIMS(array),
2039                                                    elem_ndims * sizeof(int)) != 0 ||
2040                                         memcmp(elem_lbs, ARR_LBOUND(array),
2041                                                    elem_ndims * sizeof(int)) != 0)
2042                                         ereport(ERROR,
2043                                                         (errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR),
2044                                                 errmsg("multidimensional arrays must have array "
2045                                                            "expressions with matching dimensions")));
2046                         }
2047
2048                         elem_ndatabytes = ARR_SIZE(array) - ARR_OVERHEAD(elem_ndims);
2049                         ndatabytes += elem_ndatabytes;
2050                         if (dat == NULL)
2051                                 dat = (char *) palloc(ndatabytes);
2052                         else
2053                                 dat = (char *) repalloc(dat, ndatabytes);
2054
2055                         memcpy(dat + (ndatabytes - elem_ndatabytes),
2056                                    ARR_DATA_PTR(array),
2057                                    elem_ndatabytes);
2058                 }
2059
2060                 /* setup for multi-D array */
2061                 dims[0] = outer_nelems;
2062                 lbs[0] = 1;
2063                 for (i = 1; i < ndims; i++)
2064                 {
2065                         dims[i] = elem_dims[i - 1];
2066                         lbs[i] = elem_lbs[i - 1];
2067                 }
2068
2069                 nbytes = ndatabytes + ARR_OVERHEAD(ndims);
2070                 result = (ArrayType *) palloc(nbytes);
2071
2072                 result->size = nbytes;
2073                 result->ndim = ndims;
2074                 result->flags = 0;
2075                 result->elemtype = element_type;
2076                 memcpy(ARR_DIMS(result), dims, ndims * sizeof(int));
2077                 memcpy(ARR_LBOUND(result), lbs, ndims * sizeof(int));
2078                 if (ndatabytes > 0)
2079                         memcpy(ARR_DATA_PTR(result), dat, ndatabytes);
2080
2081                 if (dat != NULL)
2082                         pfree(dat);
2083         }
2084
2085         return PointerGetDatum(result);
2086 }
2087
2088 /* ----------------------------------------------------------------
2089  *              ExecEvalRow - ROW() expressions
2090  * ----------------------------------------------------------------
2091  */
2092 static Datum
2093 ExecEvalRow(RowExprState *rstate,
2094                         ExprContext *econtext,
2095                         bool *isNull, ExprDoneCond *isDone)
2096 {
2097         HeapTuple       tuple;
2098         Datum      *values;
2099         char       *nulls;
2100         int                     natts;
2101         ListCell   *arg;
2102         int                     i;
2103
2104         /* Set default values for result flags: non-null, not a set result */
2105         *isNull = false;
2106         if (isDone)
2107                 *isDone = ExprSingleResult;
2108
2109         /* Allocate workspace */
2110         natts = rstate->tupdesc->natts;
2111         values = (Datum *) palloc0(natts * sizeof(Datum));
2112         nulls = (char *) palloc(natts * sizeof(char));
2113
2114         /* preset to nulls in case rowtype has some later-added columns */
2115         memset(nulls, 'n', natts * sizeof(char));
2116
2117         /* Evaluate field values */
2118         i = 0;
2119         foreach(arg, rstate->args)
2120         {
2121                 ExprState  *e = (ExprState *) lfirst(arg);
2122                 bool            eisnull;
2123
2124                 values[i] = ExecEvalExpr(e, econtext, &eisnull, NULL);
2125                 nulls[i] = eisnull ? 'n' : ' ';
2126                 i++;
2127         }
2128
2129         tuple = heap_formtuple(rstate->tupdesc, values, nulls);
2130
2131         pfree(values);
2132         pfree(nulls);
2133
2134         return HeapTupleGetDatum(tuple);
2135 }
2136
2137 /* ----------------------------------------------------------------
2138  *              ExecEvalCoalesce
2139  * ----------------------------------------------------------------
2140  */
2141 static Datum
2142 ExecEvalCoalesce(CoalesceExprState *coalesceExpr, ExprContext *econtext,
2143                                  bool *isNull, ExprDoneCond *isDone)
2144 {
2145         ListCell   *arg;
2146
2147         if (isDone)
2148                 *isDone = ExprSingleResult;
2149
2150         /* Simply loop through until something NOT NULL is found */
2151         foreach(arg, coalesceExpr->args)
2152         {
2153                 ExprState  *e = (ExprState *) lfirst(arg);
2154                 Datum           value;
2155
2156                 value = ExecEvalExpr(e, econtext, isNull, NULL);
2157                 if (!*isNull)
2158                         return value;
2159         }
2160
2161         /* Else return NULL */
2162         *isNull = true;
2163         return (Datum) 0;
2164 }
2165
2166 /* ----------------------------------------------------------------
2167  *              ExecEvalNullIf
2168  *
2169  * Note that this is *always* derived from the equals operator,
2170  * but since we need special processing of the arguments
2171  * we can not simply reuse ExecEvalOper() or ExecEvalFunc().
2172  * ----------------------------------------------------------------
2173  */
2174 static Datum
2175 ExecEvalNullIf(FuncExprState *nullIfExpr,
2176                            ExprContext *econtext,
2177                            bool *isNull, ExprDoneCond *isDone)
2178 {
2179         Datum           result;
2180         FunctionCallInfoData fcinfo;
2181         ExprDoneCond argDone;
2182         List       *argList;
2183
2184         if (isDone)
2185                 *isDone = ExprSingleResult;
2186
2187         /*
2188          * Initialize function cache if first time through
2189          */
2190         if (nullIfExpr->func.fn_oid == InvalidOid)
2191         {
2192                 NullIfExpr *op = (NullIfExpr *) nullIfExpr->xprstate.expr;
2193
2194                 init_fcache(op->opfuncid, nullIfExpr, econtext->ecxt_per_query_memory);
2195                 Assert(!nullIfExpr->func.fn_retset);
2196         }
2197
2198         /*
2199          * extract info from nullIfExpr
2200          */
2201         argList = nullIfExpr->args;
2202
2203         /* Need to prep callinfo structure */
2204         MemSet(&fcinfo, 0, sizeof(fcinfo));
2205         fcinfo.flinfo = &(nullIfExpr->func);
2206         argDone = ExecEvalFuncArgs(&fcinfo, argList, econtext);
2207         if (argDone != ExprSingleResult)
2208                 ereport(ERROR,
2209                                 (errcode(ERRCODE_DATATYPE_MISMATCH),
2210                                  errmsg("NULLIF does not support set arguments")));
2211         Assert(fcinfo.nargs == 2);
2212
2213         /* if either argument is NULL they can't be equal */
2214         if (!fcinfo.argnull[0] && !fcinfo.argnull[1])
2215         {
2216                 fcinfo.isnull = false;
2217                 result = FunctionCallInvoke(&fcinfo);
2218                 /* if the arguments are equal return null */
2219                 if (!fcinfo.isnull && DatumGetBool(result))
2220                 {
2221                         *isNull = true;
2222                         return (Datum) 0;
2223                 }
2224         }
2225
2226         /* else return first argument */
2227         *isNull = fcinfo.argnull[0];
2228         return fcinfo.arg[0];
2229 }
2230
2231 /* ----------------------------------------------------------------
2232  *              ExecEvalNullTest
2233  *
2234  *              Evaluate a NullTest node.
2235  * ----------------------------------------------------------------
2236  */
2237 static Datum
2238 ExecEvalNullTest(GenericExprState *nstate,
2239                                  ExprContext *econtext,
2240                                  bool *isNull,
2241                                  ExprDoneCond *isDone)
2242 {
2243         NullTest   *ntest = (NullTest *) nstate->xprstate.expr;
2244         Datum           result;
2245
2246         result = ExecEvalExpr(nstate->arg, econtext, isNull, isDone);
2247
2248         if (isDone && *isDone == ExprEndResult)
2249                 return result;                  /* nothing to check */
2250
2251         switch (ntest->nulltesttype)
2252         {
2253                 case IS_NULL:
2254                         if (*isNull)
2255                         {
2256                                 *isNull = false;
2257                                 return BoolGetDatum(true);
2258                         }
2259                         else
2260                                 return BoolGetDatum(false);
2261                 case IS_NOT_NULL:
2262                         if (*isNull)
2263                         {
2264                                 *isNull = false;
2265                                 return BoolGetDatum(false);
2266                         }
2267                         else
2268                                 return BoolGetDatum(true);
2269                 default:
2270                         elog(ERROR, "unrecognized nulltesttype: %d",
2271                                  (int) ntest->nulltesttype);
2272                         return (Datum) 0;       /* keep compiler quiet */
2273         }
2274 }
2275
2276 /* ----------------------------------------------------------------
2277  *              ExecEvalBooleanTest
2278  *
2279  *              Evaluate a BooleanTest node.
2280  * ----------------------------------------------------------------
2281  */
2282 static Datum
2283 ExecEvalBooleanTest(GenericExprState *bstate,
2284                                         ExprContext *econtext,
2285                                         bool *isNull,
2286                                         ExprDoneCond *isDone)
2287 {
2288         BooleanTest *btest = (BooleanTest *) bstate->xprstate.expr;
2289         Datum           result;
2290
2291         result = ExecEvalExpr(bstate->arg, econtext, isNull, isDone);
2292
2293         if (isDone && *isDone == ExprEndResult)
2294                 return result;                  /* nothing to check */
2295
2296         switch (btest->booltesttype)
2297         {
2298                 case IS_TRUE:
2299                         if (*isNull)
2300                         {
2301                                 *isNull = false;
2302                                 return BoolGetDatum(false);
2303                         }
2304                         else if (DatumGetBool(result))
2305                                 return BoolGetDatum(true);
2306                         else
2307                                 return BoolGetDatum(false);
2308                 case IS_NOT_TRUE:
2309                         if (*isNull)
2310                         {
2311                                 *isNull = false;
2312                                 return BoolGetDatum(true);
2313                         }
2314                         else if (DatumGetBool(result))
2315                                 return BoolGetDatum(false);
2316                         else
2317                                 return BoolGetDatum(true);
2318                 case IS_FALSE:
2319                         if (*isNull)
2320                         {
2321                                 *isNull = false;
2322                                 return BoolGetDatum(false);
2323                         }
2324                         else if (DatumGetBool(result))
2325                                 return BoolGetDatum(false);
2326                         else
2327                                 return BoolGetDatum(true);
2328                 case IS_NOT_FALSE:
2329                         if (*isNull)
2330                         {
2331                                 *isNull = false;
2332                                 return BoolGetDatum(true);
2333                         }
2334                         else if (DatumGetBool(result))
2335                                 return BoolGetDatum(true);
2336                         else
2337                                 return BoolGetDatum(false);
2338                 case IS_UNKNOWN:
2339                         if (*isNull)
2340                         {
2341                                 *isNull = false;
2342                                 return BoolGetDatum(true);
2343                         }
2344                         else
2345                                 return BoolGetDatum(false);
2346                 case IS_NOT_UNKNOWN:
2347                         if (*isNull)
2348                         {
2349                                 *isNull = false;
2350                                 return BoolGetDatum(false);
2351                         }
2352                         else
2353                                 return BoolGetDatum(true);
2354                 default:
2355                         elog(ERROR, "unrecognized booltesttype: %d",
2356                                  (int) btest->booltesttype);
2357                         return (Datum) 0;       /* keep compiler quiet */
2358         }
2359 }
2360
2361 /*
2362  * ExecEvalCoerceToDomain
2363  *
2364  * Test the provided data against the domain constraint(s).  If the data
2365  * passes the constraint specifications, pass it through (return the
2366  * datum) otherwise throw an error.
2367  */
2368 static Datum
2369 ExecEvalCoerceToDomain(CoerceToDomainState *cstate, ExprContext *econtext,
2370                                            bool *isNull, ExprDoneCond *isDone)
2371 {
2372         CoerceToDomain *ctest = (CoerceToDomain *) cstate->xprstate.expr;
2373         Datum           result;
2374         ListCell   *l;
2375
2376         result = ExecEvalExpr(cstate->arg, econtext, isNull, isDone);
2377
2378         if (isDone && *isDone == ExprEndResult)
2379                 return result;                  /* nothing to check */
2380
2381         foreach(l, cstate->constraints)
2382         {
2383                 DomainConstraintState *con = (DomainConstraintState *) lfirst(l);
2384
2385                 switch (con->constrainttype)
2386                 {
2387                         case DOM_CONSTRAINT_NOTNULL:
2388                                 if (*isNull)
2389                                         ereport(ERROR,
2390                                                         (errcode(ERRCODE_NOT_NULL_VIOLATION),
2391                                                    errmsg("domain %s does not allow null values",
2392                                                                   format_type_be(ctest->resulttype))));
2393                                 break;
2394                         case DOM_CONSTRAINT_CHECK:
2395                                 {
2396                                         Datum           conResult;
2397                                         bool            conIsNull;
2398                                         Datum           save_datum;
2399                                         bool            save_isNull;
2400
2401                                         /*
2402                                          * Set up value to be returned by CoerceToDomainValue
2403                                          * nodes. We must save and restore prior setting of
2404                                          * econtext's domainValue fields, in case this node is
2405                                          * itself within a check expression for another
2406                                          * domain.
2407                                          */
2408                                         save_datum = econtext->domainValue_datum;
2409                                         save_isNull = econtext->domainValue_isNull;
2410
2411                                         econtext->domainValue_datum = result;
2412                                         econtext->domainValue_isNull = *isNull;
2413
2414                                         conResult = ExecEvalExpr(con->check_expr,
2415                                                                                          econtext, &conIsNull, NULL);
2416
2417                                         if (!conIsNull &&
2418                                                 !DatumGetBool(conResult))
2419                                                 ereport(ERROR,
2420                                                                 (errcode(ERRCODE_CHECK_VIOLATION),
2421                                                                  errmsg("value for domain %s violates check constraint \"%s\"",
2422                                                                                 format_type_be(ctest->resulttype),
2423                                                                                 con->name)));
2424                                         econtext->domainValue_datum = save_datum;
2425                                         econtext->domainValue_isNull = save_isNull;
2426
2427                                         break;
2428                                 }
2429                         default:
2430                                 elog(ERROR, "unrecognized constraint type: %d",
2431                                          (int) con->constrainttype);
2432                                 break;
2433                 }
2434         }
2435
2436         /* If all has gone well (constraints did not fail) return the datum */
2437         return result;
2438 }
2439
2440 /*
2441  * ExecEvalCoerceToDomainValue
2442  *
2443  * Return the value stored by CoerceToDomain.
2444  */
2445 static Datum
2446 ExecEvalCoerceToDomainValue(ExprState *exprstate,
2447                                                         ExprContext *econtext,
2448                                                         bool *isNull, ExprDoneCond *isDone)
2449 {
2450         if (isDone)
2451                 *isDone = ExprSingleResult;
2452         *isNull = econtext->domainValue_isNull;
2453         return econtext->domainValue_datum;
2454 }
2455
2456 /* ----------------------------------------------------------------
2457  *              ExecEvalFieldSelect
2458  *
2459  *              Evaluate a FieldSelect node.
2460  * ----------------------------------------------------------------
2461  */
2462 static Datum
2463 ExecEvalFieldSelect(FieldSelectState *fstate,
2464                                         ExprContext *econtext,
2465                                         bool *isNull,
2466                                         ExprDoneCond *isDone)
2467 {
2468         FieldSelect *fselect = (FieldSelect *) fstate->xprstate.expr;
2469         Datum           result;
2470         Datum           tupDatum;
2471         HeapTupleHeader tuple;
2472         Oid                     tupType;
2473         int32           tupTypmod;
2474         TupleDesc       tupDesc;
2475         HeapTupleData tmptup;
2476
2477         tupDatum = ExecEvalExpr(fstate->arg, econtext, isNull, isDone);
2478
2479         /* this test covers the isDone exception too: */
2480         if (*isNull)
2481                 return tupDatum;
2482
2483         tuple = DatumGetHeapTupleHeader(tupDatum);
2484
2485         tupType = HeapTupleHeaderGetTypeId(tuple);
2486         tupTypmod = HeapTupleHeaderGetTypMod(tuple);
2487
2488         /* Lookup tupdesc if first time through or if type changes */
2489         tupDesc = fstate->argdesc;
2490         if (tupDesc == NULL ||
2491                 tupType != tupDesc->tdtypeid ||
2492                 tupTypmod != tupDesc->tdtypmod)
2493         {
2494                 MemoryContext oldcontext;
2495
2496                 tupDesc = lookup_rowtype_tupdesc(tupType, tupTypmod);
2497                 /* Copy the tupdesc into query storage for safety */
2498                 oldcontext = MemoryContextSwitchTo(econtext->ecxt_per_query_memory);
2499                 tupDesc = CreateTupleDescCopy(tupDesc);
2500                 if (fstate->argdesc)
2501                         FreeTupleDesc(fstate->argdesc);
2502                 fstate->argdesc = tupDesc;
2503                 MemoryContextSwitchTo(oldcontext);
2504         }
2505
2506         /*
2507          * heap_getattr needs a HeapTuple not a bare HeapTupleHeader.  We set
2508          * all the fields in the struct just in case user tries to inspect
2509          * system columns.
2510          */
2511         tmptup.t_len = HeapTupleHeaderGetDatumLength(tuple);
2512         ItemPointerSetInvalid(&(tmptup.t_self));
2513         tmptup.t_tableOid = InvalidOid;
2514         tmptup.t_data = tuple;
2515
2516         result = heap_getattr(&tmptup,
2517                                                   fselect->fieldnum,
2518                                                   tupDesc,
2519                                                   isNull);
2520         return result;
2521 }
2522
2523 /* ----------------------------------------------------------------
2524  *              ExecEvalFieldStore
2525  *
2526  *              Evaluate a FieldStore node.
2527  * ----------------------------------------------------------------
2528  */
2529 static Datum
2530 ExecEvalFieldStore(FieldStoreState *fstate,
2531                                    ExprContext *econtext,
2532                                    bool *isNull,
2533                                    ExprDoneCond *isDone)
2534 {
2535         FieldStore *fstore = (FieldStore *) fstate->xprstate.expr;
2536         HeapTuple       tuple;
2537         Datum           tupDatum;
2538         TupleDesc       tupDesc;
2539         Datum      *values;
2540         char       *nulls;
2541         Datum           save_datum;
2542         bool            save_isNull;
2543         ListCell   *l1,
2544                            *l2;
2545
2546         tupDatum = ExecEvalExpr(fstate->arg, econtext, isNull, isDone);
2547
2548         if (isDone && *isDone == ExprEndResult)
2549                 return tupDatum;
2550
2551         /* Lookup tupdesc if first time through or if type changes */
2552         tupDesc = fstate->argdesc;
2553         if (tupDesc == NULL ||
2554                 fstore->resulttype != tupDesc->tdtypeid)
2555         {
2556                 MemoryContext oldcontext;
2557
2558                 tupDesc = lookup_rowtype_tupdesc(fstore->resulttype, -1);
2559                 /* Copy the tupdesc into query storage for safety */
2560                 oldcontext = MemoryContextSwitchTo(econtext->ecxt_per_query_memory);
2561                 tupDesc = CreateTupleDescCopy(tupDesc);
2562                 if (fstate->argdesc)
2563                         FreeTupleDesc(fstate->argdesc);
2564                 fstate->argdesc = tupDesc;
2565                 MemoryContextSwitchTo(oldcontext);
2566         }
2567
2568         /* Allocate workspace */
2569         values = (Datum *) palloc(tupDesc->natts * sizeof(Datum));
2570         nulls = (char *) palloc(tupDesc->natts * sizeof(char));
2571
2572         if (!*isNull)
2573         {
2574                 /*
2575                  * heap_deformtuple needs a HeapTuple not a bare HeapTupleHeader.
2576                  * We set all the fields in the struct just in case.
2577                  */
2578                 HeapTupleHeader tuphdr;
2579                 HeapTupleData tmptup;
2580
2581                 tuphdr = DatumGetHeapTupleHeader(tupDatum);
2582                 tmptup.t_len = HeapTupleHeaderGetDatumLength(tuphdr);
2583                 ItemPointerSetInvalid(&(tmptup.t_self));
2584                 tmptup.t_tableOid = InvalidOid;
2585                 tmptup.t_data = tuphdr;
2586
2587                 heap_deformtuple(&tmptup, tupDesc, values, nulls);
2588         }
2589         else
2590         {
2591                 /* Convert null input tuple into an all-nulls row */
2592                 memset(nulls, 'n', tupDesc->natts * sizeof(char));
2593         }
2594
2595         /* Result is never null */
2596         *isNull = false;
2597
2598         save_datum = econtext->caseValue_datum;
2599         save_isNull = econtext->caseValue_isNull;
2600
2601         forboth(l1, fstate->newvals, l2, fstore->fieldnums)
2602         {
2603                 ExprState *newval = (ExprState *) lfirst(l1);
2604                 AttrNumber fieldnum = lfirst_int(l2);
2605                 bool            eisnull;
2606
2607                 Assert(fieldnum > 0 && fieldnum <= tupDesc->natts);
2608
2609                 /*
2610                  * Use the CaseTestExpr mechanism to pass down the old value of the
2611                  * field being replaced; this is useful in case we have a nested field
2612                  * update situation.  It's safe to reuse the CASE mechanism because
2613                  * there cannot be a CASE between here and where the value would be
2614                  * needed.
2615                  */
2616                 econtext->caseValue_datum = values[fieldnum - 1];
2617                 econtext->caseValue_isNull = (nulls[fieldnum - 1] == 'n');
2618
2619                 values[fieldnum - 1] = ExecEvalExpr(newval,
2620                                                                                         econtext,
2621                                                                                         &eisnull,
2622                                                                                         NULL);
2623                 nulls[fieldnum - 1] = eisnull ? 'n' : ' ';
2624         }
2625
2626         econtext->caseValue_datum = save_datum;
2627         econtext->caseValue_isNull = save_isNull;
2628
2629         tuple = heap_formtuple(tupDesc, values, nulls);
2630
2631         pfree(values);
2632         pfree(nulls);
2633
2634         return HeapTupleGetDatum(tuple);
2635 }
2636
2637 /* ----------------------------------------------------------------
2638  *              ExecEvalRelabelType
2639  *
2640  *              Evaluate a RelabelType node.
2641  * ----------------------------------------------------------------
2642  */
2643 static Datum
2644 ExecEvalRelabelType(GenericExprState *exprstate,
2645                                         ExprContext *econtext,
2646                                         bool *isNull, ExprDoneCond *isDone)
2647 {
2648         return ExecEvalExpr(exprstate->arg, econtext, isNull, isDone);
2649 }
2650
2651
2652 /*
2653  * ExecEvalExprSwitchContext
2654  *
2655  * Same as ExecEvalExpr, but get into the right allocation context explicitly.
2656  */
2657 Datum
2658 ExecEvalExprSwitchContext(ExprState *expression,
2659                                                   ExprContext *econtext,
2660                                                   bool *isNull,
2661                                                   ExprDoneCond *isDone)
2662 {
2663         Datum           retDatum;
2664         MemoryContext oldContext;
2665
2666         oldContext = MemoryContextSwitchTo(econtext->ecxt_per_tuple_memory);
2667         retDatum = ExecEvalExpr(expression, econtext, isNull, isDone);
2668         MemoryContextSwitchTo(oldContext);
2669         return retDatum;
2670 }
2671
2672
2673 /*
2674  * ExecInitExpr: prepare an expression tree for execution
2675  *
2676  * This function builds and returns an ExprState tree paralleling the given
2677  * Expr node tree.      The ExprState tree can then be handed to ExecEvalExpr
2678  * for execution.  Because the Expr tree itself is read-only as far as
2679  * ExecInitExpr and ExecEvalExpr are concerned, several different executions
2680  * of the same plan tree can occur concurrently.
2681  *
2682  * This must be called in a memory context that will last as long as repeated
2683  * executions of the expression are needed.  Typically the context will be
2684  * the same as the per-query context of the associated ExprContext.
2685  *
2686  * Any Aggref and SubPlan nodes found in the tree are added to the lists
2687  * of such nodes held by the parent PlanState.  Otherwise, we do very little
2688  * initialization here other than building the state-node tree.  Any nontrivial
2689  * work associated with initializing runtime info for a node should happen
2690  * during the first actual evaluation of that node.  (This policy lets us
2691  * avoid work if the node is never actually evaluated.)
2692  *
2693  * Note: there is no ExecEndExpr function; we assume that any resource
2694  * cleanup needed will be handled by just releasing the memory context
2695  * in which the state tree is built.  Functions that require additional
2696  * cleanup work can register a shutdown callback in the ExprContext.
2697  *
2698  *      'node' is the root of the expression tree to examine
2699  *      'parent' is the PlanState node that owns the expression.
2700  *
2701  * 'parent' may be NULL if we are preparing an expression that is not
2702  * associated with a plan tree.  (If so, it can't have aggs or subplans.)
2703  * This case should usually come through ExecPrepareExpr, not directly here.
2704  */
2705 ExprState *
2706 ExecInitExpr(Expr *node, PlanState *parent)
2707 {
2708         ExprState  *state;
2709
2710         if (node == NULL)
2711                 return NULL;
2712
2713         /* Guard against stack overflow due to overly complex expressions */
2714         check_stack_depth();
2715
2716         switch (nodeTag(node))
2717         {
2718                 case T_Var:
2719                         state = (ExprState *) makeNode(ExprState);
2720                         state->evalfunc = ExecEvalVar;
2721                         break;
2722                 case T_Const:
2723                         state = (ExprState *) makeNode(ExprState);
2724                         state->evalfunc = ExecEvalConst;
2725                         break;
2726                 case T_Param:
2727                         state = (ExprState *) makeNode(ExprState);
2728                         state->evalfunc = ExecEvalParam;
2729                         break;
2730                 case T_CoerceToDomainValue:
2731                         state = (ExprState *) makeNode(ExprState);
2732                         state->evalfunc = ExecEvalCoerceToDomainValue;
2733                         break;
2734                 case T_CaseTestExpr:
2735                         state = (ExprState *) makeNode(ExprState);
2736                         state->evalfunc = ExecEvalCaseTestExpr;
2737                         break;
2738                 case T_Aggref:
2739                         {
2740                                 Aggref     *aggref = (Aggref *) node;
2741                                 AggrefExprState *astate = makeNode(AggrefExprState);
2742
2743                                 astate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalAggref;
2744                                 if (parent && IsA(parent, AggState))
2745                                 {
2746                                         AggState   *aggstate = (AggState *) parent;
2747                                         int                     naggs;
2748
2749                                         aggstate->aggs = lcons(astate, aggstate->aggs);
2750                                         naggs = ++aggstate->numaggs;
2751
2752                                         astate->target = ExecInitExpr(aggref->target, parent);
2753
2754                                         /*
2755                                          * Complain if the aggregate's argument contains any
2756                                          * aggregates; nested agg functions are semantically
2757                                          * nonsensical.  (This should have been caught
2758                                          * earlier, but we defend against it here anyway.)
2759                                          */
2760                                         if (naggs != aggstate->numaggs)
2761                                                 ereport(ERROR,
2762                                                                 (errcode(ERRCODE_GROUPING_ERROR),
2763                                                                  errmsg("aggregate function calls may not be nested")));
2764                                 }
2765                                 else
2766                                 {
2767                                         /* planner messed up */
2768                                         elog(ERROR, "aggref found in non-Agg plan node");
2769                                 }
2770                                 state = (ExprState *) astate;
2771                         }
2772                         break;
2773                 case T_ArrayRef:
2774                         {
2775                                 ArrayRef   *aref = (ArrayRef *) node;
2776                                 ArrayRefExprState *astate = makeNode(ArrayRefExprState);
2777
2778                                 astate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalArrayRef;
2779                                 astate->refupperindexpr = (List *)
2780                                         ExecInitExpr((Expr *) aref->refupperindexpr, parent);
2781                                 astate->reflowerindexpr = (List *)
2782                                         ExecInitExpr((Expr *) aref->reflowerindexpr, parent);
2783                                 astate->refexpr = ExecInitExpr(aref->refexpr, parent);
2784                                 astate->refassgnexpr = ExecInitExpr(aref->refassgnexpr,
2785                                                                                                         parent);
2786                                 /* do one-time catalog lookups for type info */
2787                                 astate->refattrlength = get_typlen(aref->refarraytype);
2788                                 get_typlenbyvalalign(aref->refelemtype,
2789                                                                          &astate->refelemlength,
2790                                                                          &astate->refelembyval,
2791                                                                          &astate->refelemalign);
2792                                 state = (ExprState *) astate;
2793                         }
2794                         break;
2795                 case T_FuncExpr:
2796                         {
2797                                 FuncExpr   *funcexpr = (FuncExpr *) node;
2798                                 FuncExprState *fstate = makeNode(FuncExprState);
2799
2800                                 fstate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalFunc;
2801                                 fstate->args = (List *)
2802                                         ExecInitExpr((Expr *) funcexpr->args, parent);
2803                                 fstate->func.fn_oid = InvalidOid;               /* not initialized */
2804                                 state = (ExprState *) fstate;
2805                         }
2806                         break;
2807                 case T_OpExpr:
2808                         {
2809                                 OpExpr     *opexpr = (OpExpr *) node;
2810                                 FuncExprState *fstate = makeNode(FuncExprState);
2811
2812                                 fstate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalOper;
2813                                 fstate->args = (List *)
2814                                         ExecInitExpr((Expr *) opexpr->args, parent);
2815                                 fstate->func.fn_oid = InvalidOid;               /* not initialized */
2816                                 state = (ExprState *) fstate;
2817                         }
2818                         break;
2819                 case T_DistinctExpr:
2820                         {
2821                                 DistinctExpr *distinctexpr = (DistinctExpr *) node;
2822                                 FuncExprState *fstate = makeNode(FuncExprState);
2823
2824                                 fstate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalDistinct;
2825                                 fstate->args = (List *)
2826                                         ExecInitExpr((Expr *) distinctexpr->args, parent);
2827                                 fstate->func.fn_oid = InvalidOid;               /* not initialized */
2828                                 state = (ExprState *) fstate;
2829                         }
2830                         break;
2831                 case T_ScalarArrayOpExpr:
2832                         {
2833                                 ScalarArrayOpExpr *opexpr = (ScalarArrayOpExpr *) node;
2834                                 ScalarArrayOpExprState *sstate = makeNode(ScalarArrayOpExprState);
2835
2836                                 sstate->fxprstate.xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalScalarArrayOp;
2837                                 sstate->fxprstate.args = (List *)
2838                                         ExecInitExpr((Expr *) opexpr->args, parent);
2839                                 sstate->fxprstate.func.fn_oid = InvalidOid;             /* not initialized */
2840                                 sstate->element_type = InvalidOid;              /* ditto */
2841                                 state = (ExprState *) sstate;
2842                         }
2843                         break;
2844                 case T_BoolExpr:
2845                         {
2846                                 BoolExpr   *boolexpr = (BoolExpr *) node;
2847                                 BoolExprState *bstate = makeNode(BoolExprState);
2848
2849                                 switch (boolexpr->boolop)
2850                                 {
2851                                         case AND_EXPR:
2852                                                 bstate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalAnd;
2853                                                 break;
2854                                         case OR_EXPR:
2855                                                 bstate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalOr;
2856                                                 break;
2857                                         case NOT_EXPR:
2858                                                 bstate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalNot;
2859                                                 break;
2860                                         default:
2861                                                 elog(ERROR, "unrecognized boolop: %d",
2862                                                          (int) boolexpr->boolop);
2863                                                 break;
2864                                 }
2865                                 bstate->args = (List *)
2866                                         ExecInitExpr((Expr *) boolexpr->args, parent);
2867                                 state = (ExprState *) bstate;
2868                         }
2869                         break;
2870                 case T_SubPlan:
2871                         {
2872                                 /* Keep this in sync with ExecInitExprInitPlan, below */
2873                                 SubPlan    *subplan = (SubPlan *) node;
2874                                 SubPlanState *sstate = makeNode(SubPlanState);
2875
2876                                 sstate->xprstate.evalfunc = (ExprStateEvalFunc) ExecSubPlan;
2877
2878                                 if (!parent)
2879                                         elog(ERROR, "SubPlan found with no parent plan");
2880
2881                                 /*
2882                                  * Here we just add the SubPlanState nodes to
2883                                  * parent->subPlan.  The subplans will be initialized
2884                                  * later.
2885                                  */
2886                                 parent->subPlan = lcons(sstate, parent->subPlan);
2887                                 sstate->sub_estate = NULL;
2888                                 sstate->planstate = NULL;
2889
2890                                 sstate->exprs = (List *)
2891                                         ExecInitExpr((Expr *) subplan->exprs, parent);
2892                                 sstate->args = (List *)
2893                                         ExecInitExpr((Expr *) subplan->args, parent);
2894
2895                                 state = (ExprState *) sstate;
2896                         }
2897                         break;
2898                 case T_FieldSelect:
2899                         {
2900                                 FieldSelect *fselect = (FieldSelect *) node;
2901                                 FieldSelectState *fstate = makeNode(FieldSelectState);
2902
2903                                 fstate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalFieldSelect;
2904                                 fstate->arg = ExecInitExpr(fselect->arg, parent);
2905                                 fstate->argdesc = NULL;
2906                                 state = (ExprState *) fstate;
2907                         }
2908                         break;
2909                 case T_FieldStore:
2910                         {
2911                                 FieldStore *fstore = (FieldStore *) node;
2912                                 FieldStoreState *fstate = makeNode(FieldStoreState);
2913
2914                                 fstate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalFieldStore;
2915                                 fstate->arg = ExecInitExpr(fstore->arg, parent);
2916                                 fstate->newvals = (List *) ExecInitExpr((Expr *) fstore->newvals, parent);
2917                                 fstate->argdesc = NULL;
2918                                 state = (ExprState *) fstate;
2919                         }
2920                         break;
2921                 case T_RelabelType:
2922                         {
2923                                 RelabelType *relabel = (RelabelType *) node;
2924                                 GenericExprState *gstate = makeNode(GenericExprState);
2925
2926                                 gstate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalRelabelType;
2927                                 gstate->arg = ExecInitExpr(relabel->arg, parent);
2928                                 state = (ExprState *) gstate;
2929                         }
2930                         break;
2931                 case T_CaseExpr:
2932                         {
2933                                 CaseExpr   *caseexpr = (CaseExpr *) node;
2934                                 CaseExprState *cstate = makeNode(CaseExprState);
2935                                 List       *outlist = NIL;
2936                                 ListCell   *l;
2937
2938                                 cstate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalCase;
2939                                 cstate->arg = ExecInitExpr(caseexpr->arg, parent);
2940                                 foreach(l, caseexpr->args)
2941                                 {
2942                                         CaseWhen   *when = (CaseWhen *) lfirst(l);
2943                                         CaseWhenState *wstate = makeNode(CaseWhenState);
2944
2945                                         Assert(IsA(when, CaseWhen));
2946                                         wstate->xprstate.evalfunc = NULL;       /* not used */
2947                                         wstate->xprstate.expr = (Expr *) when;
2948                                         wstate->expr = ExecInitExpr(when->expr, parent);
2949                                         wstate->result = ExecInitExpr(when->result, parent);
2950                                         outlist = lappend(outlist, wstate);
2951                                 }
2952                                 cstate->args = outlist;
2953                                 cstate->defresult = ExecInitExpr(caseexpr->defresult, parent);
2954                                 state = (ExprState *) cstate;
2955                         }
2956                         break;
2957                 case T_ArrayExpr:
2958                         {
2959                                 ArrayExpr  *arrayexpr = (ArrayExpr *) node;
2960                                 ArrayExprState *astate = makeNode(ArrayExprState);
2961                                 List       *outlist = NIL;
2962                                 ListCell   *l;
2963
2964                                 astate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalArray;
2965                                 foreach(l, arrayexpr->elements)
2966                                 {
2967                                         Expr       *e = (Expr *) lfirst(l);
2968                                         ExprState  *estate;
2969
2970                                         estate = ExecInitExpr(e, parent);
2971                                         outlist = lappend(outlist, estate);
2972                                 }
2973                                 astate->elements = outlist;
2974                                 /* do one-time catalog lookup for type info */
2975                                 get_typlenbyvalalign(arrayexpr->element_typeid,
2976                                                                          &astate->elemlength,
2977                                                                          &astate->elembyval,
2978                                                                          &astate->elemalign);
2979                                 state = (ExprState *) astate;
2980                         }
2981                         break;
2982                 case T_RowExpr:
2983                         {
2984                                 RowExpr    *rowexpr = (RowExpr *) node;
2985                                 RowExprState *rstate = makeNode(RowExprState);
2986                                 Form_pg_attribute *attrs;
2987                                 List       *outlist = NIL;
2988                                 ListCell   *l;
2989                                 int                     i;
2990
2991                                 rstate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalRow;
2992                                 /* Build tupdesc to describe result tuples */
2993                                 if (rowexpr->row_typeid == RECORDOID)
2994                                 {
2995                                         /* generic record, use runtime type assignment */
2996                                         rstate->tupdesc = ExecTypeFromExprList(rowexpr->args);
2997                                         rstate->tupdesc = BlessTupleDesc(rstate->tupdesc);
2998                                 }
2999                                 else
3000                                 {
3001                                         /* it's been cast to a named type, use that */
3002                                         rstate->tupdesc = lookup_rowtype_tupdesc(rowexpr->row_typeid, -1);
3003                                         rstate->tupdesc = CreateTupleDescCopy(rstate->tupdesc);
3004                                 }
3005                                 /* Set up evaluation, skipping any deleted columns */
3006                                 Assert(list_length(rowexpr->args) <= rstate->tupdesc->natts);
3007                                 attrs = rstate->tupdesc->attrs;
3008                                 i = 0;
3009                                 foreach(l, rowexpr->args)
3010                                 {
3011                                         Expr       *e = (Expr *) lfirst(l);
3012                                         ExprState  *estate;
3013
3014                                         if (!attrs[i]->attisdropped)
3015                                         {
3016                                                 /*
3017                                                  * Guard against ALTER COLUMN TYPE on rowtype
3018                                                  * since the RowExpr was created.  XXX should we
3019                                                  * check typmod too?  Not sure we can be sure it'll
3020                                                  * be the same.
3021                                                  */
3022                                                 if (exprType((Node *) e) != attrs[i]->atttypid)
3023                                                         ereport(ERROR,
3024                                                                         (errcode(ERRCODE_DATATYPE_MISMATCH),
3025                                                                          errmsg("ROW() column has type %s instead of type %s",
3026                                                                                         format_type_be(exprType((Node *) e)),
3027                                                                                         format_type_be(attrs[i]->atttypid))));
3028                                         }
3029                                         else
3030                                         {
3031                                                 /*
3032                                                  * Ignore original expression and insert a NULL.
3033                                                  * We don't really care what type of NULL it is,
3034                                                  * so always make an int4 NULL.
3035                                                  */
3036                                                 e = (Expr *) makeNullConst(INT4OID);
3037                                         }
3038                                         estate = ExecInitExpr(e, parent);
3039                                         outlist = lappend(outlist, estate);
3040                                         i++;
3041                                 }
3042                                 rstate->args = outlist;
3043                                 state = (ExprState *) rstate;
3044                         }
3045                         break;
3046                 case T_CoalesceExpr:
3047                         {
3048                                 CoalesceExpr *coalesceexpr = (CoalesceExpr *) node;
3049                                 CoalesceExprState *cstate = makeNode(CoalesceExprState);
3050                                 List       *outlist = NIL;
3051                                 ListCell   *l;
3052
3053                                 cstate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalCoalesce;
3054                                 foreach(l, coalesceexpr->args)
3055                                 {
3056                                         Expr       *e = (Expr *) lfirst(l);
3057                                         ExprState  *estate;
3058
3059                                         estate = ExecInitExpr(e, parent);
3060                                         outlist = lappend(outlist, estate);
3061                                 }
3062                                 cstate->args = outlist;
3063                                 state = (ExprState *) cstate;
3064                         }
3065                         break;
3066                 case T_NullIfExpr:
3067                         {
3068                                 NullIfExpr *nullifexpr = (NullIfExpr *) node;
3069                                 FuncExprState *fstate = makeNode(FuncExprState);
3070
3071                                 fstate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalNullIf;
3072                                 fstate->args = (List *)
3073                                         ExecInitExpr((Expr *) nullifexpr->args, parent);
3074                                 fstate->func.fn_oid = InvalidOid;               /* not initialized */
3075                                 state = (ExprState *) fstate;
3076                         }
3077                         break;
3078                 case T_NullTest:
3079                         {
3080                                 NullTest   *ntest = (NullTest *) node;
3081                                 GenericExprState *gstate = makeNode(GenericExprState);
3082
3083                                 gstate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalNullTest;
3084                                 gstate->arg = ExecInitExpr(ntest->arg, parent);
3085                                 state = (ExprState *) gstate;
3086                         }
3087                         break;
3088                 case T_BooleanTest:
3089                         {
3090                                 BooleanTest *btest = (BooleanTest *) node;
3091                                 GenericExprState *gstate = makeNode(GenericExprState);
3092
3093                                 gstate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalBooleanTest;
3094                                 gstate->arg = ExecInitExpr(btest->arg, parent);
3095                                 state = (ExprState *) gstate;
3096                         }
3097                         break;
3098                 case T_CoerceToDomain:
3099                         {
3100                                 CoerceToDomain *ctest = (CoerceToDomain *) node;
3101                                 CoerceToDomainState *cstate = makeNode(CoerceToDomainState);
3102
3103                                 cstate->xprstate.evalfunc = (ExprStateEvalFunc) ExecEvalCoerceToDomain;
3104                                 cstate->arg = ExecInitExpr(ctest->arg, parent);
3105                                 cstate->constraints = GetDomainConstraints(ctest->resulttype);
3106                                 state = (ExprState *) cstate;
3107                         }
3108                         break;
3109                 case T_TargetEntry:
3110                         {
3111                                 TargetEntry *tle = (TargetEntry *) node;
3112                                 GenericExprState *gstate = makeNode(GenericExprState);
3113
3114                                 gstate->xprstate.evalfunc = NULL;       /* not used */
3115                                 gstate->arg = ExecInitExpr(tle->expr, parent);
3116                                 state = (ExprState *) gstate;
3117                         }
3118                         break;
3119                 case T_List:
3120                         {
3121                                 List       *outlist = NIL;
3122                                 ListCell   *l;
3123
3124                                 foreach(l, (List *) node)
3125                                 {
3126                                         outlist = lappend(outlist,
3127                                                                           ExecInitExpr((Expr *) lfirst(l),
3128                                                                                                    parent));
3129                                 }
3130                                 /* Don't fall through to the "common" code below */
3131                                 return (ExprState *) outlist;
3132                         }
3133                 default:
3134                         elog(ERROR, "unrecognized node type: %d",
3135                                  (int) nodeTag(node));
3136                         state = NULL;           /* keep compiler quiet */
3137                         break;
3138         }
3139
3140         /* Common code for all state-node types */
3141         state->expr = node;
3142
3143         return state;
3144 }
3145
3146 /*
3147  * ExecInitExprInitPlan --- initialize a subplan expr that's being handled
3148  * as an InitPlan.      This is identical to ExecInitExpr's handling of a regular
3149  * subplan expr, except we do NOT want to add the node to the parent's
3150  * subplan list.
3151  */
3152 SubPlanState *
3153 ExecInitExprInitPlan(SubPlan *node, PlanState *parent)
3154 {
3155         SubPlanState *sstate = makeNode(SubPlanState);
3156
3157         if (!parent)
3158                 elog(ERROR, "SubPlan found with no parent plan");
3159
3160         /* The subplan's state will be initialized later */
3161         sstate->sub_estate = NULL;
3162         sstate->planstate = NULL;
3163
3164         sstate->exprs = (List *) ExecInitExpr((Expr *) node->exprs, parent);
3165         sstate->args = (List *) ExecInitExpr((Expr *) node->args, parent);
3166
3167         sstate->xprstate.expr = (Expr *) node;
3168
3169         return sstate;
3170 }
3171
3172 /*
3173  * ExecPrepareExpr --- initialize for expression execution outside a normal
3174  * Plan tree context.
3175  *
3176  * This differs from ExecInitExpr in that we don't assume the caller is
3177  * already running in the EState's per-query context.  Also, we apply
3178  * fix_opfuncids() to the passed expression tree to be sure it is ready
3179  * to run.      (In ordinary Plan trees the planner will have fixed opfuncids,
3180  * but callers outside the executor will not have done this.)
3181  */
3182 ExprState *
3183 ExecPrepareExpr(Expr *node, EState *estate)
3184 {
3185         ExprState  *result;
3186         MemoryContext oldcontext;
3187
3188         fix_opfuncids((Node *) node);
3189
3190         oldcontext = MemoryContextSwitchTo(estate->es_query_cxt);
3191
3192         result = ExecInitExpr(node, NULL);
3193
3194         MemoryContextSwitchTo(oldcontext);
3195
3196         return result;
3197 }
3198
3199
3200 /* ----------------------------------------------------------------
3201  *                                       ExecQual / ExecTargetList / ExecProject
3202  * ----------------------------------------------------------------
3203  */
3204
3205 /* ----------------------------------------------------------------
3206  *              ExecQual
3207  *
3208  *              Evaluates a conjunctive boolean expression (qual list) and
3209  *              returns true iff none of the subexpressions are false.
3210  *              (We also return true if the list is empty.)
3211  *
3212  *      If some of the subexpressions yield NULL but none yield FALSE,
3213  *      then the result of the conjunction is NULL (ie, unknown)
3214  *      according to three-valued boolean logic.  In this case,
3215  *      we return the value specified by the "resultForNull" parameter.
3216  *
3217  *      Callers evaluating WHERE clauses should pass resultForNull=FALSE,
3218  *      since SQL specifies that tuples with null WHERE results do not
3219  *      get selected.  On the other hand, callers evaluating constraint
3220  *      conditions should pass resultForNull=TRUE, since SQL also specifies
3221  *      that NULL constraint conditions are not failures.
3222  *
3223  *      NOTE: it would not be correct to use this routine to evaluate an
3224  *      AND subclause of a boolean expression; for that purpose, a NULL
3225  *      result must be returned as NULL so that it can be properly treated
3226  *      in the next higher operator (cf. ExecEvalAnd and ExecEvalOr).
3227  *      This routine is only used in contexts where a complete expression
3228  *      is being evaluated and we know that NULL can be treated the same
3229  *      as one boolean result or the other.
3230  *
3231  * ----------------------------------------------------------------
3232  */
3233 bool
3234 ExecQual(List *qual, ExprContext *econtext, bool resultForNull)
3235 {
3236         bool            result;
3237         MemoryContext oldContext;
3238         ListCell   *l;
3239
3240         /*
3241          * debugging stuff
3242          */
3243         EV_printf("ExecQual: qual is ");
3244         EV_nodeDisplay(qual);
3245         EV_printf("\n");
3246
3247         IncrProcessed();
3248
3249         /*
3250          * Run in short-lived per-tuple context while computing expressions.
3251          */
3252         oldContext = MemoryContextSwitchTo(econtext->ecxt_per_tuple_memory);
3253
3254         /*
3255          * Evaluate the qual conditions one at a time.  If we find a FALSE
3256          * result, we can stop evaluating and return FALSE --- the AND result
3257          * must be FALSE.  Also, if we find a NULL result when resultForNull
3258          * is FALSE, we can stop and return FALSE --- the AND result must be
3259          * FALSE or NULL in that case, and the caller doesn't care which.
3260          *
3261          * If we get to the end of the list, we can return TRUE.  This will
3262          * happen when the AND result is indeed TRUE, or when the AND result
3263          * is NULL (one or more NULL subresult, with all the rest TRUE) and
3264          * the caller has specified resultForNull = TRUE.
3265          */
3266         result = true;
3267
3268         foreach(l, qual)
3269         {
3270                 ExprState  *clause = (ExprState *) lfirst(l);
3271                 Datum           expr_value;
3272                 bool            isNull;
3273
3274                 expr_value = ExecEvalExpr(clause, econtext, &isNull, NULL);
3275
3276                 if (isNull)
3277                 {
3278                         if (resultForNull == false)
3279                         {
3280                                 result = false; /* treat NULL as FALSE */
3281                                 break;
3282                         }
3283                 }
3284                 else
3285                 {
3286                         if (!DatumGetBool(expr_value))
3287                         {
3288                                 result = false; /* definitely FALSE */
3289                                 break;
3290                         }
3291                 }
3292         }
3293
3294         MemoryContextSwitchTo(oldContext);
3295
3296         return result;
3297 }
3298
3299 /*
3300  * Number of items in a tlist (including any resjunk items!)
3301  */
3302 int
3303 ExecTargetListLength(List *targetlist)
3304 {
3305         /* This used to be more complex, but fjoins are dead */
3306         return list_length(targetlist);
3307 }
3308
3309 /*
3310  * Number of items in a tlist, not including any resjunk items
3311  */
3312 int
3313 ExecCleanTargetListLength(List *targetlist)
3314 {
3315         int                     len = 0;
3316         ListCell   *tl;
3317
3318         foreach(tl, targetlist)
3319         {
3320                 TargetEntry *curTle = (TargetEntry *) lfirst(tl);
3321
3322                 Assert(IsA(curTle, TargetEntry));
3323                 if (!curTle->resdom->resjunk)
3324                         len++;
3325         }
3326         return len;
3327 }
3328
3329 /* ----------------------------------------------------------------
3330  *              ExecTargetList
3331  *
3332  *              Evaluates a targetlist with respect to the given
3333  *              expression context and returns a tuple.
3334  *
3335  * The caller must pass workspace for the values and nulls arrays
3336  * as well as the itemIsDone array.  This convention saves palloc'ing
3337  * workspace on each call, and some callers may find it useful to examine
3338  * the values array directly.
3339  *
3340  * As with ExecEvalExpr, the caller should pass isDone = NULL if not
3341  * prepared to deal with sets of result tuples.  Otherwise, a return
3342  * of *isDone = ExprMultipleResult signifies a set element, and a return
3343  * of *isDone = ExprEndResult signifies end of the set of tuple.
3344  * ----------------------------------------------------------------
3345  */
3346 static HeapTuple
3347 ExecTargetList(List *targetlist,
3348                            TupleDesc targettype,
3349                            ExprContext *econtext,
3350                            Datum *values,
3351                            char *nulls,
3352                            ExprDoneCond *itemIsDone,
3353                            ExprDoneCond *isDone)
3354 {
3355         MemoryContext oldContext;
3356         ListCell   *tl;
3357         bool            isNull;
3358         bool            haveDoneSets;
3359
3360         /*
3361          * debugging stuff
3362          */
3363         EV_printf("ExecTargetList: tl is ");
3364         EV_nodeDisplay(targetlist);
3365         EV_printf("\n");
3366
3367         /*
3368          * Run in short-lived per-tuple context while computing expressions.
3369          */
3370         oldContext = MemoryContextSwitchTo(econtext->ecxt_per_tuple_memory);
3371
3372         /*
3373          * There used to be some klugy and demonstrably broken code here that
3374          * special-cased the situation where targetlist == NIL.  Now we just
3375          * fall through and return an empty-but-valid tuple.
3376          */
3377
3378         /*
3379          * evaluate all the expressions in the target list
3380          */
3381         if (isDone)
3382                 *isDone = ExprSingleResult;             /* until proven otherwise */
3383
3384         haveDoneSets = false;           /* any exhausted set exprs in tlist? */
3385
3386         foreach(tl, targetlist)
3387         {
3388                 GenericExprState *gstate = (GenericExprState *) lfirst(tl);
3389                 TargetEntry *tle = (TargetEntry *) gstate->xprstate.expr;
3390                 AttrNumber      resind = tle->resdom->resno - 1;
3391
3392                 values[resind] = ExecEvalExpr(gstate->arg,
3393                                                                           econtext,
3394                                                                           &isNull,
3395                                                                           &itemIsDone[resind]);
3396                 nulls[resind] = isNull ? 'n' : ' ';
3397
3398                 if (itemIsDone[resind] != ExprSingleResult)
3399                 {
3400                         /* We have a set-valued expression in the tlist */
3401                         if (isDone == NULL)
3402                                 ereport(ERROR,
3403                                                 (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
3404                                                  errmsg("set-valued function called in context that cannot accept a set")));
3405                         if (itemIsDone[resind] == ExprMultipleResult)
3406                         {
3407                                 /* we have undone sets in the tlist, set flag */
3408                                 *isDone = ExprMultipleResult;
3409                         }
3410                         else
3411                         {
3412                                 /* we have done sets in the tlist, set flag for that */
3413                                 haveDoneSets = true;
3414                         }
3415                 }
3416         }
3417
3418         if (haveDoneSets)
3419         {
3420                 /*
3421                  * note: can't get here unless we verified isDone != NULL
3422                  */
3423                 if (*isDone == ExprSingleResult)
3424                 {
3425                         /*
3426                          * all sets are done, so report that tlist expansion is
3427                          * complete.
3428                          */
3429                         *isDone = ExprEndResult;
3430                         MemoryContextSwitchTo(oldContext);
3431                         return NULL;
3432                 }
3433                 else
3434                 {
3435                         /*
3436                          * We have some done and some undone sets.      Restart the done
3437                          * ones so that we can deliver a tuple (if possible).
3438                          */
3439                         foreach(tl, targetlist)
3440                         {
3441                                 GenericExprState *gstate = (GenericExprState *) lfirst(tl);
3442                                 TargetEntry *tle = (TargetEntry *) gstate->xprstate.expr;
3443                                 AttrNumber      resind = tle->resdom->resno - 1;
3444
3445                                 if (itemIsDone[resind] == ExprEndResult)
3446                                 {
3447                                         values[resind] = ExecEvalExpr(gstate->arg,
3448                                                                                                   econtext,
3449                                                                                                   &isNull,
3450                                                                                                   &itemIsDone[resind]);
3451                                         nulls[resind] = isNull ? 'n' : ' ';
3452
3453                                         if (itemIsDone[resind] == ExprEndResult)
3454                                         {
3455                                                 /*
3456                                                  * Oh dear, this item is returning an empty set.
3457                                                  * Guess we can't make a tuple after all.
3458                                                  */
3459                                                 *isDone = ExprEndResult;
3460                                                 break;
3461                                         }
3462                                 }
3463                         }
3464
3465                         /*
3466                          * If we cannot make a tuple because some sets are empty, we
3467                          * still have to cycle the nonempty sets to completion, else
3468                          * resources will not be released from subplans etc.
3469                          *
3470                          * XXX is that still necessary?
3471                          */
3472                         if (*isDone == ExprEndResult)
3473                         {
3474                                 foreach(tl, targetlist)
3475                                 {
3476                                         GenericExprState *gstate = (GenericExprState *) lfirst(tl);
3477                                         TargetEntry *tle = (TargetEntry *) gstate->xprstate.expr;
3478                                         AttrNumber      resind = tle->resdom->resno - 1;
3479
3480                                         while (itemIsDone[resind] == ExprMultipleResult)
3481                                         {
3482                                                 (void) ExecEvalExpr(gstate->arg,
3483                                                                                         econtext,
3484                                                                                         &isNull,
3485                                                                                         &itemIsDone[resind]);
3486                                         }
3487                                 }
3488
3489                                 MemoryContextSwitchTo(oldContext);
3490                                 return NULL;
3491                         }
3492                 }
3493         }
3494
3495         /*
3496          * form the new result tuple (in the caller's memory context!)
3497          */
3498         MemoryContextSwitchTo(oldContext);
3499
3500         return heap_formtuple(targettype, values, nulls);
3501 }
3502
3503 /* ----------------------------------------------------------------
3504  *              ExecProject
3505  *
3506  *              projects a tuple based on projection info and stores
3507  *              it in the specified tuple table slot.
3508  *
3509  *              Note: someday soon the executor can be extended to eliminate
3510  *                        redundant projections by storing pointers to datums
3511  *                        in the tuple table and then passing these around when
3512  *                        possible.  this should make things much quicker.
3513  *                        -cim 6/3/91
3514  * ----------------------------------------------------------------
3515  */
3516 TupleTableSlot *
3517 ExecProject(ProjectionInfo *projInfo, ExprDoneCond *isDone)
3518 {
3519         TupleTableSlot *slot;
3520         TupleDesc       tupType;
3521         HeapTuple       newTuple;
3522
3523         /*
3524          * sanity checks
3525          */
3526         if (projInfo == NULL)
3527                 return NULL;
3528
3529         /*
3530          * get the projection info we want
3531          */
3532         slot = projInfo->pi_slot;
3533         tupType = slot->ttc_tupleDescriptor;
3534
3535         /*
3536          * form a new result tuple (if possible --- result can be NULL)
3537          */
3538         newTuple = ExecTargetList(projInfo->pi_targetlist,
3539                                                           tupType,
3540                                                           projInfo->pi_exprContext,
3541                                                           projInfo->pi_tupValues,
3542                                                           projInfo->pi_tupNulls,
3543                                                           projInfo->pi_itemIsDone,
3544                                                           isDone);
3545
3546         /*
3547          * store the tuple in the projection slot and return the slot.
3548          */
3549         return ExecStoreTuple(newTuple,                 /* tuple to store */
3550                                                   slot,                         /* slot to store in */
3551                                                   InvalidBuffer,        /* tuple has no buffer */
3552                                                   true);
3553 }