PostgreSQL Source Code  git master
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros
pl_comp.c
Go to the documentation of this file.
1 /*-------------------------------------------------------------------------
2  *
3  * pl_comp.c - Compiler part of the PL/pgSQL
4  * procedural language
5  *
6  * Portions Copyright (c) 1996-2017, PostgreSQL Global Development Group
7  * Portions Copyright (c) 1994, Regents of the University of California
8  *
9  *
10  * IDENTIFICATION
11  * src/pl/plpgsql/src/pl_comp.c
12  *
13  *-------------------------------------------------------------------------
14  */
15 
16 #include "postgres.h"
17 
18 #include <ctype.h>
19 
20 #include "access/htup_details.h"
21 #include "catalog/namespace.h"
22 #include "catalog/pg_proc.h"
23 #include "catalog/pg_proc_fn.h"
24 #include "catalog/pg_type.h"
25 #include "funcapi.h"
26 #include "nodes/makefuncs.h"
27 #include "parser/parse_type.h"
28 #include "utils/builtins.h"
29 #include "utils/guc.h"
30 #include "utils/lsyscache.h"
31 #include "utils/memutils.h"
32 #include "utils/regproc.h"
33 #include "utils/rel.h"
34 #include "utils/syscache.h"
35 
36 #include "plpgsql.h"
37 
38 
39 /* ----------
40  * Our own local and global variables
41  * ----------
42  */
44 
45 static int datums_alloc;
48 static int datums_last;
49 
51 bool plpgsql_DumpExecTree = false;
52 bool plpgsql_check_syntax = false;
53 
55 
56 /* A context appropriate for short-term allocs during compilation */
58 
59 /* ----------
60  * Hash table for compiled functions
61  * ----------
62  */
63 static HTAB *plpgsql_HashTable = NULL;
64 
65 typedef struct plpgsql_hashent
66 {
68  PLpgSQL_function *function;
70 
71 #define FUNCS_PER_USER 128 /* initial table size */
72 
73 /* ----------
74  * Lookup table for EXCEPTION condition names
75  * ----------
76  */
77 typedef struct
78 {
79  const char *label;
82 
84 #include "plerrcodes.h" /* pgrminclude ignore */
85  {NULL, 0}
86 };
87 
88 
89 /* ----------
90  * static prototypes
91  * ----------
92  */
94  HeapTuple procTup,
95  PLpgSQL_function *function,
96  PLpgSQL_func_hashkey *hashkey,
97  bool forValidator);
98 static void plpgsql_compile_error_callback(void *arg);
99 static void add_parameter_name(PLpgSQL_nsitem_type itemtype, int itemno, const char *name);
100 static void add_dummy_return(PLpgSQL_function *function);
101 static Node *plpgsql_pre_column_ref(ParseState *pstate, ColumnRef *cref);
102 static Node *plpgsql_post_column_ref(ParseState *pstate, ColumnRef *cref, Node *var);
103 static Node *plpgsql_param_ref(ParseState *pstate, ParamRef *pref);
104 static Node *resolve_column_ref(ParseState *pstate, PLpgSQL_expr *expr,
105  ColumnRef *cref, bool error_if_no_field);
106 static Node *make_datum_param(PLpgSQL_expr *expr, int dno, int location);
107 static PLpgSQL_row *build_row_from_class(Oid classOid);
108 static PLpgSQL_row *build_row_from_vars(PLpgSQL_variable **vars, int numvars);
109 static PLpgSQL_type *build_datatype(HeapTuple typeTup, int32 typmod, Oid collation);
110 static void plpgsql_start_datums(void);
111 static void plpgsql_finish_datums(PLpgSQL_function *function);
112 static void compute_function_hashkey(FunctionCallInfo fcinfo,
113  Form_pg_proc procStruct,
114  PLpgSQL_func_hashkey *hashkey,
115  bool forValidator);
116 static void plpgsql_resolve_polymorphic_argtypes(int numargs,
117  Oid *argtypes, char *argmodes,
118  Node *call_expr, bool forValidator,
119  const char *proname);
121 static void plpgsql_HashTableInsert(PLpgSQL_function *function,
122  PLpgSQL_func_hashkey *func_key);
123 static void plpgsql_HashTableDelete(PLpgSQL_function *function);
124 static void delete_function(PLpgSQL_function *func);
125 
126 /* ----------
127  * plpgsql_compile Make an execution tree for a PL/pgSQL function.
128  *
129  * If forValidator is true, we're only compiling for validation purposes,
130  * and so some checks are skipped.
131  *
132  * Note: it's important for this to fall through quickly if the function
133  * has already been compiled.
134  * ----------
135  */
137 plpgsql_compile(FunctionCallInfo fcinfo, bool forValidator)
138 {
139  Oid funcOid = fcinfo->flinfo->fn_oid;
140  HeapTuple procTup;
141  Form_pg_proc procStruct;
142  PLpgSQL_function *function;
143  PLpgSQL_func_hashkey hashkey;
144  bool function_valid = false;
145  bool hashkey_valid = false;
146 
147  /*
148  * Lookup the pg_proc tuple by Oid; we'll need it in any case
149  */
150  procTup = SearchSysCache1(PROCOID, ObjectIdGetDatum(funcOid));
151  if (!HeapTupleIsValid(procTup))
152  elog(ERROR, "cache lookup failed for function %u", funcOid);
153  procStruct = (Form_pg_proc) GETSTRUCT(procTup);
154 
155  /*
156  * See if there's already a cache entry for the current FmgrInfo. If not,
157  * try to find one in the hash table.
158  */
159  function = (PLpgSQL_function *) fcinfo->flinfo->fn_extra;
160 
161 recheck:
162  if (!function)
163  {
164  /* Compute hashkey using function signature and actual arg types */
165  compute_function_hashkey(fcinfo, procStruct, &hashkey, forValidator);
166  hashkey_valid = true;
167 
168  /* And do the lookup */
169  function = plpgsql_HashTableLookup(&hashkey);
170  }
171 
172  if (function)
173  {
174  /* We have a compiled function, but is it still valid? */
175  if (function->fn_xmin == HeapTupleHeaderGetRawXmin(procTup->t_data) &&
176  ItemPointerEquals(&function->fn_tid, &procTup->t_self))
177  function_valid = true;
178  else
179  {
180  /*
181  * Nope, so remove it from hashtable and try to drop associated
182  * storage (if not done already).
183  */
184  delete_function(function);
185 
186  /*
187  * If the function isn't in active use then we can overwrite the
188  * func struct with new data, allowing any other existing fn_extra
189  * pointers to make use of the new definition on their next use.
190  * If it is in use then just leave it alone and make a new one.
191  * (The active invocations will run to completion using the
192  * previous definition, and then the cache entry will just be
193  * leaked; doesn't seem worth adding code to clean it up, given
194  * what a corner case this is.)
195  *
196  * If we found the function struct via fn_extra then it's possible
197  * a replacement has already been made, so go back and recheck the
198  * hashtable.
199  */
200  if (function->use_count != 0)
201  {
202  function = NULL;
203  if (!hashkey_valid)
204  goto recheck;
205  }
206  }
207  }
208 
209  /*
210  * If the function wasn't found or was out-of-date, we have to compile it
211  */
212  if (!function_valid)
213  {
214  /*
215  * Calculate hashkey if we didn't already; we'll need it to store the
216  * completed function.
217  */
218  if (!hashkey_valid)
219  compute_function_hashkey(fcinfo, procStruct, &hashkey,
220  forValidator);
221 
222  /*
223  * Do the hard part.
224  */
225  function = do_compile(fcinfo, procTup, function,
226  &hashkey, forValidator);
227  }
228 
229  ReleaseSysCache(procTup);
230 
231  /*
232  * Save pointer in FmgrInfo to avoid search on subsequent calls
233  */
234  fcinfo->flinfo->fn_extra = (void *) function;
235 
236  /*
237  * Finally return the compiled function
238  */
239  return function;
240 }
241 
242 /*
243  * This is the slow part of plpgsql_compile().
244  *
245  * The passed-in "function" pointer is either NULL or an already-allocated
246  * function struct to overwrite.
247  *
248  * While compiling a function, the CurrentMemoryContext is the
249  * per-function memory context of the function we are compiling. That
250  * means a palloc() will allocate storage with the same lifetime as
251  * the function itself.
252  *
253  * Because palloc()'d storage will not be immediately freed, temporary
254  * allocations should either be performed in a short-lived memory
255  * context or explicitly pfree'd. Since not all backend functions are
256  * careful about pfree'ing their allocations, it is also wise to
257  * switch into a short-term context before calling into the
258  * backend. An appropriate context for performing short-term
259  * allocations is the plpgsql_compile_tmp_cxt.
260  *
261  * NB: this code is not re-entrant. We assume that nothing we do here could
262  * result in the invocation of another plpgsql function.
263  */
264 static PLpgSQL_function *
266  HeapTuple procTup,
267  PLpgSQL_function *function,
268  PLpgSQL_func_hashkey *hashkey,
269  bool forValidator)
270 {
271  Form_pg_proc procStruct = (Form_pg_proc) GETSTRUCT(procTup);
272  bool is_dml_trigger = CALLED_AS_TRIGGER(fcinfo);
273  bool is_event_trigger = CALLED_AS_EVENT_TRIGGER(fcinfo);
274  Datum prosrcdatum;
275  bool isnull;
276  char *proc_source;
277  HeapTuple typeTup;
278  Form_pg_type typeStruct;
279  PLpgSQL_variable *var;
280  PLpgSQL_rec *rec;
281  int i;
282  ErrorContextCallback plerrcontext;
283  int parse_rc;
284  Oid rettypeid;
285  int numargs;
286  int num_in_args = 0;
287  int num_out_args = 0;
288  Oid *argtypes;
289  char **argnames;
290  char *argmodes;
291  int *in_arg_varnos = NULL;
292  PLpgSQL_variable **out_arg_variables;
293  MemoryContext func_cxt;
294 
295  /*
296  * Setup the scanner input and error info. We assume that this function
297  * cannot be invoked recursively, so there's no need to save and restore
298  * the static variables used here.
299  */
300  prosrcdatum = SysCacheGetAttr(PROCOID, procTup,
301  Anum_pg_proc_prosrc, &isnull);
302  if (isnull)
303  elog(ERROR, "null prosrc");
304  proc_source = TextDatumGetCString(prosrcdatum);
305  plpgsql_scanner_init(proc_source);
306 
307  plpgsql_error_funcname = pstrdup(NameStr(procStruct->proname));
308 
309  /*
310  * Setup error traceback support for ereport()
311  */
313  plerrcontext.arg = forValidator ? proc_source : NULL;
314  plerrcontext.previous = error_context_stack;
315  error_context_stack = &plerrcontext;
316 
317  /*
318  * Do extra syntax checks when validating the function definition. We skip
319  * this when actually compiling functions for execution, for performance
320  * reasons.
321  */
322  plpgsql_check_syntax = forValidator;
323 
324  /*
325  * Create the new function struct, if not done already. The function
326  * structs are never thrown away, so keep them in TopMemoryContext.
327  */
328  if (function == NULL)
329  {
330  function = (PLpgSQL_function *)
332  }
333  else
334  {
335  /* re-using a previously existing struct, so clear it out */
336  memset(function, 0, sizeof(PLpgSQL_function));
337  }
338  plpgsql_curr_compile = function;
339 
340  /*
341  * All the permanent output of compilation (e.g. parse tree) is kept in a
342  * per-function memory context, so it can be reclaimed easily.
343  */
345  "PL/pgSQL function context",
347  plpgsql_compile_tmp_cxt = MemoryContextSwitchTo(func_cxt);
348 
349  function->fn_signature = format_procedure(fcinfo->flinfo->fn_oid);
350  function->fn_oid = fcinfo->flinfo->fn_oid;
351  function->fn_xmin = HeapTupleHeaderGetRawXmin(procTup->t_data);
352  function->fn_tid = procTup->t_self;
353  function->fn_input_collation = fcinfo->fncollation;
354  function->fn_cxt = func_cxt;
355  function->out_param_varno = -1; /* set up for no OUT param */
356  function->resolve_option = plpgsql_variable_conflict;
357  function->print_strict_params = plpgsql_print_strict_params;
358  /* only promote extra warnings and errors at CREATE FUNCTION time */
359  function->extra_warnings = forValidator ? plpgsql_extra_warnings : 0;
360  function->extra_errors = forValidator ? plpgsql_extra_errors : 0;
361 
362  if (is_dml_trigger)
363  function->fn_is_trigger = PLPGSQL_DML_TRIGGER;
364  else if (is_event_trigger)
365  function->fn_is_trigger = PLPGSQL_EVENT_TRIGGER;
366  else
367  function->fn_is_trigger = PLPGSQL_NOT_TRIGGER;
368 
369  /*
370  * Initialize the compiler, particularly the namespace stack. The
371  * outermost namespace contains function parameters and other special
372  * variables (such as FOUND), and is named after the function itself.
373  */
374  plpgsql_ns_init();
375  plpgsql_ns_push(NameStr(procStruct->proname), PLPGSQL_LABEL_BLOCK);
376  plpgsql_DumpExecTree = false;
378 
379  switch (function->fn_is_trigger)
380  {
381  case PLPGSQL_NOT_TRIGGER:
382 
383  /*
384  * Fetch info about the procedure's parameters. Allocations aren't
385  * needed permanently, so make them in tmp cxt.
386  *
387  * We also need to resolve any polymorphic input or output
388  * argument types. In validation mode we won't be able to, so we
389  * arbitrarily assume we are dealing with integers.
390  */
391  MemoryContextSwitchTo(plpgsql_compile_tmp_cxt);
392 
393  numargs = get_func_arg_info(procTup,
394  &argtypes, &argnames, &argmodes);
395 
396  plpgsql_resolve_polymorphic_argtypes(numargs, argtypes, argmodes,
397  fcinfo->flinfo->fn_expr,
398  forValidator,
400 
401  in_arg_varnos = (int *) palloc(numargs * sizeof(int));
402  out_arg_variables = (PLpgSQL_variable **) palloc(numargs * sizeof(PLpgSQL_variable *));
403 
404  MemoryContextSwitchTo(func_cxt);
405 
406  /*
407  * Create the variables for the procedure's parameters.
408  */
409  for (i = 0; i < numargs; i++)
410  {
411  char buf[32];
412  Oid argtypeid = argtypes[i];
413  char argmode = argmodes ? argmodes[i] : PROARGMODE_IN;
414  PLpgSQL_type *argdtype;
415  PLpgSQL_variable *argvariable;
416  PLpgSQL_nsitem_type argitemtype;
417 
418  /* Create $n name for variable */
419  snprintf(buf, sizeof(buf), "$%d", i + 1);
420 
421  /* Create datatype info */
422  argdtype = plpgsql_build_datatype(argtypeid,
423  -1,
424  function->fn_input_collation);
425 
426  /* Disallow pseudotype argument */
427  /* (note we already replaced polymorphic types) */
428  /* (build_variable would do this, but wrong message) */
429  if (argdtype->ttype != PLPGSQL_TTYPE_SCALAR &&
430  argdtype->ttype != PLPGSQL_TTYPE_ROW)
431  ereport(ERROR,
432  (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
433  errmsg("PL/pgSQL functions cannot accept type %s",
434  format_type_be(argtypeid))));
435 
436  /*
437  * Build variable and add to datum list. If there's a name
438  * for the argument, use that as refname, else use $n name.
439  */
440  argvariable = plpgsql_build_variable((argnames &&
441  argnames[i][0] != '\0') ?
442  argnames[i] : buf,
443  0, argdtype, false);
444 
445  if (argvariable->dtype == PLPGSQL_DTYPE_VAR)
446  {
447  argitemtype = PLPGSQL_NSTYPE_VAR;
448  }
449  else
450  {
451  Assert(argvariable->dtype == PLPGSQL_DTYPE_ROW);
452  argitemtype = PLPGSQL_NSTYPE_ROW;
453  }
454 
455  /* Remember arguments in appropriate arrays */
456  if (argmode == PROARGMODE_IN ||
457  argmode == PROARGMODE_INOUT ||
458  argmode == PROARGMODE_VARIADIC)
459  in_arg_varnos[num_in_args++] = argvariable->dno;
460  if (argmode == PROARGMODE_OUT ||
461  argmode == PROARGMODE_INOUT ||
462  argmode == PROARGMODE_TABLE)
463  out_arg_variables[num_out_args++] = argvariable;
464 
465  /* Add to namespace under the $n name */
466  add_parameter_name(argitemtype, argvariable->dno, buf);
467 
468  /* If there's a name for the argument, make an alias */
469  if (argnames && argnames[i][0] != '\0')
470  add_parameter_name(argitemtype, argvariable->dno,
471  argnames[i]);
472  }
473 
474  /*
475  * If there's just one OUT parameter, out_param_varno points
476  * directly to it. If there's more than one, build a row that
477  * holds all of them.
478  */
479  if (num_out_args == 1)
480  function->out_param_varno = out_arg_variables[0]->dno;
481  else if (num_out_args > 1)
482  {
483  PLpgSQL_row *row = build_row_from_vars(out_arg_variables,
484  num_out_args);
485 
487  function->out_param_varno = row->dno;
488  }
489 
490  /*
491  * Check for a polymorphic returntype. If found, use the actual
492  * returntype type from the caller's FuncExpr node, if we have
493  * one. (In validation mode we arbitrarily assume we are dealing
494  * with integers.)
495  *
496  * Note: errcode is FEATURE_NOT_SUPPORTED because it should always
497  * work; if it doesn't we're in some context that fails to make
498  * the info available.
499  */
500  rettypeid = procStruct->prorettype;
501  if (IsPolymorphicType(rettypeid))
502  {
503  if (forValidator)
504  {
505  if (rettypeid == ANYARRAYOID)
506  rettypeid = INT4ARRAYOID;
507  else if (rettypeid == ANYRANGEOID)
508  rettypeid = INT4RANGEOID;
509  else /* ANYELEMENT or ANYNONARRAY */
510  rettypeid = INT4OID;
511  /* XXX what could we use for ANYENUM? */
512  }
513  else
514  {
515  rettypeid = get_fn_expr_rettype(fcinfo->flinfo);
516  if (!OidIsValid(rettypeid))
517  ereport(ERROR,
518  (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
519  errmsg("could not determine actual return type "
520  "for polymorphic function \"%s\"",
522  }
523  }
524 
525  /*
526  * Normal function has a defined returntype
527  */
528  function->fn_rettype = rettypeid;
529  function->fn_retset = procStruct->proretset;
530 
531  /*
532  * Lookup the function's return type
533  */
534  typeTup = SearchSysCache1(TYPEOID, ObjectIdGetDatum(rettypeid));
535  if (!HeapTupleIsValid(typeTup))
536  elog(ERROR, "cache lookup failed for type %u", rettypeid);
537  typeStruct = (Form_pg_type) GETSTRUCT(typeTup);
538 
539  /* Disallow pseudotype result, except VOID or RECORD */
540  /* (note we already replaced polymorphic types) */
541  if (typeStruct->typtype == TYPTYPE_PSEUDO)
542  {
543  if (rettypeid == VOIDOID ||
544  rettypeid == RECORDOID)
545  /* okay */ ;
546  else if (rettypeid == TRIGGEROID || rettypeid == EVTTRIGGEROID)
547  ereport(ERROR,
548  (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
549  errmsg("trigger functions can only be called as triggers")));
550  else
551  ereport(ERROR,
552  (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
553  errmsg("PL/pgSQL functions cannot return type %s",
554  format_type_be(rettypeid))));
555  }
556 
557  if (typeStruct->typrelid != InvalidOid ||
558  rettypeid == RECORDOID)
559  function->fn_retistuple = true;
560  else
561  {
562  function->fn_retbyval = typeStruct->typbyval;
563  function->fn_rettyplen = typeStruct->typlen;
564 
565  /*
566  * install $0 reference, but only for polymorphic return
567  * types, and not when the return is specified through an
568  * output parameter.
569  */
570  if (IsPolymorphicType(procStruct->prorettype) &&
571  num_out_args == 0)
572  {
573  (void) plpgsql_build_variable("$0", 0,
574  build_datatype(typeTup,
575  -1,
576  function->fn_input_collation),
577  true);
578  }
579  }
580  ReleaseSysCache(typeTup);
581  break;
582 
583  case PLPGSQL_DML_TRIGGER:
584  /* Trigger procedure's return type is unknown yet */
585  function->fn_rettype = InvalidOid;
586  function->fn_retbyval = false;
587  function->fn_retistuple = true;
588  function->fn_retset = false;
589 
590  /* shouldn't be any declared arguments */
591  if (procStruct->pronargs != 0)
592  ereport(ERROR,
593  (errcode(ERRCODE_INVALID_FUNCTION_DEFINITION),
594  errmsg("trigger functions cannot have declared arguments"),
595  errhint("The arguments of the trigger can be accessed through TG_NARGS and TG_ARGV instead.")));
596 
597  /* Add the record for referencing NEW ROW */
598  rec = plpgsql_build_record("new", 0, true);
599  function->new_varno = rec->dno;
600 
601  /* Add the record for referencing OLD ROW */
602  rec = plpgsql_build_record("old", 0, true);
603  function->old_varno = rec->dno;
604 
605  /* Add the variable tg_name */
606  var = plpgsql_build_variable("tg_name", 0,
608  -1,
609  InvalidOid),
610  true);
611  function->tg_name_varno = var->dno;
612 
613  /* Add the variable tg_when */
614  var = plpgsql_build_variable("tg_when", 0,
616  -1,
617  function->fn_input_collation),
618  true);
619  function->tg_when_varno = var->dno;
620 
621  /* Add the variable tg_level */
622  var = plpgsql_build_variable("tg_level", 0,
624  -1,
625  function->fn_input_collation),
626  true);
627  function->tg_level_varno = var->dno;
628 
629  /* Add the variable tg_op */
630  var = plpgsql_build_variable("tg_op", 0,
632  -1,
633  function->fn_input_collation),
634  true);
635  function->tg_op_varno = var->dno;
636 
637  /* Add the variable tg_relid */
638  var = plpgsql_build_variable("tg_relid", 0,
640  -1,
641  InvalidOid),
642  true);
643  function->tg_relid_varno = var->dno;
644 
645  /* Add the variable tg_relname */
646  var = plpgsql_build_variable("tg_relname", 0,
648  -1,
649  InvalidOid),
650  true);
651  function->tg_relname_varno = var->dno;
652 
653  /* tg_table_name is now preferred to tg_relname */
654  var = plpgsql_build_variable("tg_table_name", 0,
656  -1,
657  InvalidOid),
658  true);
659  function->tg_table_name_varno = var->dno;
660 
661  /* add the variable tg_table_schema */
662  var = plpgsql_build_variable("tg_table_schema", 0,
664  -1,
665  InvalidOid),
666  true);
667  function->tg_table_schema_varno = var->dno;
668 
669  /* Add the variable tg_nargs */
670  var = plpgsql_build_variable("tg_nargs", 0,
672  -1,
673  InvalidOid),
674  true);
675  function->tg_nargs_varno = var->dno;
676 
677  /* Add the variable tg_argv */
678  var = plpgsql_build_variable("tg_argv", 0,
680  -1,
681  function->fn_input_collation),
682  true);
683  function->tg_argv_varno = var->dno;
684 
685  break;
686 
688  function->fn_rettype = VOIDOID;
689  function->fn_retbyval = false;
690  function->fn_retistuple = true;
691  function->fn_retset = false;
692 
693  /* shouldn't be any declared arguments */
694  if (procStruct->pronargs != 0)
695  ereport(ERROR,
696  (errcode(ERRCODE_INVALID_FUNCTION_DEFINITION),
697  errmsg("event trigger functions cannot have declared arguments")));
698 
699  /* Add the variable tg_event */
700  var = plpgsql_build_variable("tg_event", 0,
702  -1,
703  function->fn_input_collation),
704  true);
705  function->tg_event_varno = var->dno;
706 
707  /* Add the variable tg_tag */
708  var = plpgsql_build_variable("tg_tag", 0,
710  -1,
711  function->fn_input_collation),
712  true);
713  function->tg_tag_varno = var->dno;
714 
715  break;
716 
717  default:
718  elog(ERROR, "unrecognized function typecode: %d",
719  (int) function->fn_is_trigger);
720  break;
721  }
722 
723  /* Remember if function is STABLE/IMMUTABLE */
724  function->fn_readonly = (procStruct->provolatile != PROVOLATILE_VOLATILE);
725 
726  /*
727  * Create the magic FOUND variable.
728  */
729  var = plpgsql_build_variable("found", 0,
731  -1,
732  InvalidOid),
733  true);
734  function->found_varno = var->dno;
735 
736  /*
737  * Now parse the function's text
738  */
739  parse_rc = plpgsql_yyparse();
740  if (parse_rc != 0)
741  elog(ERROR, "plpgsql parser returned %d", parse_rc);
742  function->action = plpgsql_parse_result;
743 
745  pfree(proc_source);
746 
747  /*
748  * If it has OUT parameters or returns VOID or returns a set, we allow
749  * control to fall off the end without an explicit RETURN statement. The
750  * easiest way to implement this is to add a RETURN statement to the end
751  * of the statement list during parsing.
752  */
753  if (num_out_args > 0 || function->fn_rettype == VOIDOID ||
754  function->fn_retset)
755  add_dummy_return(function);
756 
757  /*
758  * Complete the function's info
759  */
760  function->fn_nargs = procStruct->pronargs;
761  for (i = 0; i < function->fn_nargs; i++)
762  function->fn_argvarnos[i] = in_arg_varnos[i];
763 
764  plpgsql_finish_datums(function);
765 
766  /* Debug dump for completed functions */
768  plpgsql_dumptree(function);
769 
770  /*
771  * add it to the hash table
772  */
773  plpgsql_HashTableInsert(function, hashkey);
774 
775  /*
776  * Pop the error context stack
777  */
778  error_context_stack = plerrcontext.previous;
779  plpgsql_error_funcname = NULL;
780 
781  plpgsql_check_syntax = false;
782 
783  MemoryContextSwitchTo(plpgsql_compile_tmp_cxt);
784  plpgsql_compile_tmp_cxt = NULL;
785  return function;
786 }
787 
788 /* ----------
789  * plpgsql_compile_inline Make an execution tree for an anonymous code block.
790  *
791  * Note: this is generally parallel to do_compile(); is it worth trying to
792  * merge the two?
793  *
794  * Note: we assume the block will be thrown away so there is no need to build
795  * persistent data structures.
796  * ----------
797  */
799 plpgsql_compile_inline(char *proc_source)
800 {
801  char *func_name = "inline_code_block";
802  PLpgSQL_function *function;
803  ErrorContextCallback plerrcontext;
804  PLpgSQL_variable *var;
805  int parse_rc;
806  MemoryContext func_cxt;
807 
808  /*
809  * Setup the scanner input and error info. We assume that this function
810  * cannot be invoked recursively, so there's no need to save and restore
811  * the static variables used here.
812  */
813  plpgsql_scanner_init(proc_source);
814 
815  plpgsql_error_funcname = func_name;
816 
817  /*
818  * Setup error traceback support for ereport()
819  */
821  plerrcontext.arg = proc_source;
822  plerrcontext.previous = error_context_stack;
823  error_context_stack = &plerrcontext;
824 
825  /* Do extra syntax checking if check_function_bodies is on */
827 
828  /* Function struct does not live past current statement */
829  function = (PLpgSQL_function *) palloc0(sizeof(PLpgSQL_function));
830 
831  plpgsql_curr_compile = function;
832 
833  /*
834  * All the rest of the compile-time storage (e.g. parse tree) is kept in
835  * its own memory context, so it can be reclaimed easily.
836  */
838  "PL/pgSQL inline code context",
840  plpgsql_compile_tmp_cxt = MemoryContextSwitchTo(func_cxt);
841 
842  function->fn_signature = pstrdup(func_name);
843  function->fn_is_trigger = PLPGSQL_NOT_TRIGGER;
844  function->fn_input_collation = InvalidOid;
845  function->fn_cxt = func_cxt;
846  function->out_param_varno = -1; /* set up for no OUT param */
847  function->resolve_option = plpgsql_variable_conflict;
848  function->print_strict_params = plpgsql_print_strict_params;
849 
850  /*
851  * don't do extra validation for inline code as we don't want to add spam
852  * at runtime
853  */
854  function->extra_warnings = 0;
855  function->extra_errors = 0;
856 
857  plpgsql_ns_init();
859  plpgsql_DumpExecTree = false;
861 
862  /* Set up as though in a function returning VOID */
863  function->fn_rettype = VOIDOID;
864  function->fn_retset = false;
865  function->fn_retistuple = false;
866  /* a bit of hardwired knowledge about type VOID here */
867  function->fn_retbyval = true;
868  function->fn_rettyplen = sizeof(int32);
869 
870  /*
871  * Remember if function is STABLE/IMMUTABLE. XXX would it be better to
872  * set this TRUE inside a read-only transaction? Not clear.
873  */
874  function->fn_readonly = false;
875 
876  /*
877  * Create the magic FOUND variable.
878  */
879  var = plpgsql_build_variable("found", 0,
881  -1,
882  InvalidOid),
883  true);
884  function->found_varno = var->dno;
885 
886  /*
887  * Now parse the function's text
888  */
889  parse_rc = plpgsql_yyparse();
890  if (parse_rc != 0)
891  elog(ERROR, "plpgsql parser returned %d", parse_rc);
892  function->action = plpgsql_parse_result;
893 
895 
896  /*
897  * If it returns VOID (always true at the moment), we allow control to
898  * fall off the end without an explicit RETURN statement.
899  */
900  if (function->fn_rettype == VOIDOID)
901  add_dummy_return(function);
902 
903  /*
904  * Complete the function's info
905  */
906  function->fn_nargs = 0;
907 
908  plpgsql_finish_datums(function);
909 
910  /*
911  * Pop the error context stack
912  */
913  error_context_stack = plerrcontext.previous;
914  plpgsql_error_funcname = NULL;
915 
916  plpgsql_check_syntax = false;
917 
918  MemoryContextSwitchTo(plpgsql_compile_tmp_cxt);
919  plpgsql_compile_tmp_cxt = NULL;
920  return function;
921 }
922 
923 
924 /*
925  * error context callback to let us supply a call-stack traceback.
926  * If we are validating or executing an anonymous code block, the function
927  * source text is passed as an argument.
928  */
929 static void
931 {
932  if (arg)
933  {
934  /*
935  * Try to convert syntax error position to reference text of original
936  * CREATE FUNCTION or DO command.
937  */
938  if (function_parse_error_transpose((const char *) arg))
939  return;
940 
941  /*
942  * Done if a syntax error position was reported; otherwise we have to
943  * fall back to a "near line N" report.
944  */
945  }
946 
948  errcontext("compilation of PL/pgSQL function \"%s\" near line %d",
950 }
951 
952 
953 /*
954  * Add a name for a function parameter to the function's namespace
955  */
956 static void
957 add_parameter_name(PLpgSQL_nsitem_type itemtype, int itemno, const char *name)
958 {
959  /*
960  * Before adding the name, check for duplicates. We need this even though
961  * functioncmds.c has a similar check, because that code explicitly
962  * doesn't complain about conflicting IN and OUT parameter names. In
963  * plpgsql, such names are in the same namespace, so there is no way to
964  * disambiguate.
965  */
966  if (plpgsql_ns_lookup(plpgsql_ns_top(), true,
967  name, NULL, NULL,
968  NULL) != NULL)
969  ereport(ERROR,
970  (errcode(ERRCODE_INVALID_FUNCTION_DEFINITION),
971  errmsg("parameter name \"%s\" used more than once",
972  name)));
973 
974  /* OK, add the name */
975  plpgsql_ns_additem(itemtype, itemno, name);
976 }
977 
978 /*
979  * Add a dummy RETURN statement to the given function's body
980  */
981 static void
983 {
984  /*
985  * If the outer block has an EXCEPTION clause, we need to make a new outer
986  * block, since the added RETURN shouldn't act like it is inside the
987  * EXCEPTION clause.
988  */
989  if (function->action->exceptions != NULL)
990  {
991  PLpgSQL_stmt_block *new;
992 
993  new = palloc0(sizeof(PLpgSQL_stmt_block));
994  new->cmd_type = PLPGSQL_STMT_BLOCK;
995  new->body = list_make1(function->action);
996 
997  function->action = new;
998  }
999  if (function->action->body == NIL ||
1000  ((PLpgSQL_stmt *) llast(function->action->body))->cmd_type != PLPGSQL_STMT_RETURN)
1001  {
1002  PLpgSQL_stmt_return *new;
1003 
1004  new = palloc0(sizeof(PLpgSQL_stmt_return));
1005  new->cmd_type = PLPGSQL_STMT_RETURN;
1006  new->expr = NULL;
1007  new->retvarno = function->out_param_varno;
1008 
1009  function->action->body = lappend(function->action->body, new);
1010  }
1011 }
1012 
1013 
1014 /*
1015  * plpgsql_parser_setup set up parser hooks for dynamic parameters
1016  *
1017  * Note: this routine, and the hook functions it prepares for, are logically
1018  * part of plpgsql parsing. But they actually run during function execution,
1019  * when we are ready to evaluate a SQL query or expression that has not
1020  * previously been parsed and planned.
1021  */
1022 void
1024 {
1028  /* no need to use p_coerce_param_hook */
1029  pstate->p_ref_hook_state = (void *) expr;
1030 }
1031 
1032 /*
1033  * plpgsql_pre_column_ref parser callback before parsing a ColumnRef
1034  */
1035 static Node *
1037 {
1038  PLpgSQL_expr *expr = (PLpgSQL_expr *) pstate->p_ref_hook_state;
1039 
1041  return resolve_column_ref(pstate, expr, cref, false);
1042  else
1043  return NULL;
1044 }
1045 
1046 /*
1047  * plpgsql_post_column_ref parser callback after parsing a ColumnRef
1048  */
1049 static Node *
1051 {
1052  PLpgSQL_expr *expr = (PLpgSQL_expr *) pstate->p_ref_hook_state;
1053  Node *myvar;
1054 
1056  return NULL; /* we already found there's no match */
1057 
1058  if (expr->func->resolve_option == PLPGSQL_RESOLVE_COLUMN && var != NULL)
1059  return NULL; /* there's a table column, prefer that */
1060 
1061  /*
1062  * If we find a record/row variable but can't match a field name, throw
1063  * error if there was no core resolution for the ColumnRef either. In
1064  * that situation, the reference is inevitably going to fail, and
1065  * complaining about the record/row variable is likely to be more on-point
1066  * than the core parser's error message. (It's too bad we don't have
1067  * access to transformColumnRef's internal crerr state here, as in case of
1068  * a conflict with a table name this could still be less than the most
1069  * helpful error message possible.)
1070  */
1071  myvar = resolve_column_ref(pstate, expr, cref, (var == NULL));
1072 
1073  if (myvar != NULL && var != NULL)
1074  {
1075  /*
1076  * We could leave it to the core parser to throw this error, but we
1077  * can add a more useful detail message than the core could.
1078  */
1079  ereport(ERROR,
1080  (errcode(ERRCODE_AMBIGUOUS_COLUMN),
1081  errmsg("column reference \"%s\" is ambiguous",
1082  NameListToString(cref->fields)),
1083  errdetail("It could refer to either a PL/pgSQL variable or a table column."),
1084  parser_errposition(pstate, cref->location)));
1085  }
1086 
1087  return myvar;
1088 }
1089 
1090 /*
1091  * plpgsql_param_ref parser callback for ParamRefs ($n symbols)
1092  */
1093 static Node *
1095 {
1096  PLpgSQL_expr *expr = (PLpgSQL_expr *) pstate->p_ref_hook_state;
1097  char pname[32];
1098  PLpgSQL_nsitem *nse;
1099 
1100  snprintf(pname, sizeof(pname), "$%d", pref->number);
1101 
1102  nse = plpgsql_ns_lookup(expr->ns, false,
1103  pname, NULL, NULL,
1104  NULL);
1105 
1106  if (nse == NULL)
1107  return NULL; /* name not known to plpgsql */
1108 
1109  return make_datum_param(expr, nse->itemno, pref->location);
1110 }
1111 
1112 /*
1113  * resolve_column_ref attempt to resolve a ColumnRef as a plpgsql var
1114  *
1115  * Returns the translated node structure, or NULL if name not found
1116  *
1117  * error_if_no_field tells whether to throw error or quietly return NULL if
1118  * we are able to match a record/row name but don't find a field name match.
1119  */
1120 static Node *
1122  ColumnRef *cref, bool error_if_no_field)
1123 {
1124  PLpgSQL_execstate *estate;
1125  PLpgSQL_nsitem *nse;
1126  const char *name1;
1127  const char *name2 = NULL;
1128  const char *name3 = NULL;
1129  const char *colname = NULL;
1130  int nnames;
1131  int nnames_scalar = 0;
1132  int nnames_wholerow = 0;
1133  int nnames_field = 0;
1134 
1135  /*
1136  * We use the function's current estate to resolve parameter data types.
1137  * This is really pretty bogus because there is no provision for updating
1138  * plans when those types change ...
1139  */
1140  estate = expr->func->cur_estate;
1141 
1142  /*----------
1143  * The allowed syntaxes are:
1144  *
1145  * A Scalar variable reference, or whole-row record reference.
1146  * A.B Qualified scalar or whole-row reference, or field reference.
1147  * A.B.C Qualified record field reference.
1148  * A.* Whole-row record reference.
1149  * A.B.* Qualified whole-row record reference.
1150  *----------
1151  */
1152  switch (list_length(cref->fields))
1153  {
1154  case 1:
1155  {
1156  Node *field1 = (Node *) linitial(cref->fields);
1157 
1158  Assert(IsA(field1, String));
1159  name1 = strVal(field1);
1160  nnames_scalar = 1;
1161  nnames_wholerow = 1;
1162  break;
1163  }
1164  case 2:
1165  {
1166  Node *field1 = (Node *) linitial(cref->fields);
1167  Node *field2 = (Node *) lsecond(cref->fields);
1168 
1169  Assert(IsA(field1, String));
1170  name1 = strVal(field1);
1171 
1172  /* Whole-row reference? */
1173  if (IsA(field2, A_Star))
1174  {
1175  /* Set name2 to prevent matches to scalar variables */
1176  name2 = "*";
1177  nnames_wholerow = 1;
1178  break;
1179  }
1180 
1181  Assert(IsA(field2, String));
1182  name2 = strVal(field2);
1183  colname = name2;
1184  nnames_scalar = 2;
1185  nnames_wholerow = 2;
1186  nnames_field = 1;
1187  break;
1188  }
1189  case 3:
1190  {
1191  Node *field1 = (Node *) linitial(cref->fields);
1192  Node *field2 = (Node *) lsecond(cref->fields);
1193  Node *field3 = (Node *) lthird(cref->fields);
1194 
1195  Assert(IsA(field1, String));
1196  name1 = strVal(field1);
1197  Assert(IsA(field2, String));
1198  name2 = strVal(field2);
1199 
1200  /* Whole-row reference? */
1201  if (IsA(field3, A_Star))
1202  {
1203  /* Set name3 to prevent matches to scalar variables */
1204  name3 = "*";
1205  nnames_wholerow = 2;
1206  break;
1207  }
1208 
1209  Assert(IsA(field3, String));
1210  name3 = strVal(field3);
1211  colname = name3;
1212  nnames_field = 2;
1213  break;
1214  }
1215  default:
1216  /* too many names, ignore */
1217  return NULL;
1218  }
1219 
1220  nse = plpgsql_ns_lookup(expr->ns, false,
1221  name1, name2, name3,
1222  &nnames);
1223 
1224  if (nse == NULL)
1225  return NULL; /* name not known to plpgsql */
1226 
1227  switch (nse->itemtype)
1228  {
1229  case PLPGSQL_NSTYPE_VAR:
1230  if (nnames == nnames_scalar)
1231  return make_datum_param(expr, nse->itemno, cref->location);
1232  break;
1233  case PLPGSQL_NSTYPE_REC:
1234  if (nnames == nnames_wholerow)
1235  return make_datum_param(expr, nse->itemno, cref->location);
1236  if (nnames == nnames_field)
1237  {
1238  /* colname could be a field in this record */
1239  int i;
1240 
1241  /* search for a datum referencing this field */
1242  for (i = 0; i < estate->ndatums; i++)
1243  {
1244  PLpgSQL_recfield *fld = (PLpgSQL_recfield *) estate->datums[i];
1245 
1246  if (fld->dtype == PLPGSQL_DTYPE_RECFIELD &&
1247  fld->recparentno == nse->itemno &&
1248  strcmp(fld->fieldname, colname) == 0)
1249  {
1250  return make_datum_param(expr, i, cref->location);
1251  }
1252  }
1253 
1254  /*
1255  * We should not get here, because a RECFIELD datum should
1256  * have been built at parse time for every possible qualified
1257  * reference to fields of this record. But if we do, handle
1258  * it like field-not-found: throw error or return NULL.
1259  */
1260  if (error_if_no_field)
1261  ereport(ERROR,
1262  (errcode(ERRCODE_UNDEFINED_COLUMN),
1263  errmsg("record \"%s\" has no field \"%s\"",
1264  (nnames_field == 1) ? name1 : name2,
1265  colname),
1266  parser_errposition(pstate, cref->location)));
1267  }
1268  break;
1269  case PLPGSQL_NSTYPE_ROW:
1270  if (nnames == nnames_wholerow)
1271  return make_datum_param(expr, nse->itemno, cref->location);
1272  if (nnames == nnames_field)
1273  {
1274  /* colname could be a field in this row */
1275  PLpgSQL_row *row = (PLpgSQL_row *) estate->datums[nse->itemno];
1276  int i;
1277 
1278  for (i = 0; i < row->nfields; i++)
1279  {
1280  if (row->fieldnames[i] &&
1281  strcmp(row->fieldnames[i], colname) == 0)
1282  {
1283  return make_datum_param(expr, row->varnos[i],
1284  cref->location);
1285  }
1286  }
1287  /* Not found, so throw error or return NULL */
1288  if (error_if_no_field)
1289  ereport(ERROR,
1290  (errcode(ERRCODE_UNDEFINED_COLUMN),
1291  errmsg("record \"%s\" has no field \"%s\"",
1292  (nnames_field == 1) ? name1 : name2,
1293  colname),
1294  parser_errposition(pstate, cref->location)));
1295  }
1296  break;
1297  default:
1298  elog(ERROR, "unrecognized plpgsql itemtype: %d", nse->itemtype);
1299  }
1300 
1301  /* Name format doesn't match the plpgsql variable type */
1302  return NULL;
1303 }
1304 
1305 /*
1306  * Helper for columnref parsing: build a Param referencing a plpgsql datum,
1307  * and make sure that that datum is listed in the expression's paramnos.
1308  */
1309 static Node *
1310 make_datum_param(PLpgSQL_expr *expr, int dno, int location)
1311 {
1312  PLpgSQL_execstate *estate;
1313  PLpgSQL_datum *datum;
1314  Param *param;
1315  MemoryContext oldcontext;
1316 
1317  /* see comment in resolve_column_ref */
1318  estate = expr->func->cur_estate;
1319  Assert(dno >= 0 && dno < estate->ndatums);
1320  datum = estate->datums[dno];
1321 
1322  /*
1323  * Bitmapset must be allocated in function's permanent memory context
1324  */
1325  oldcontext = MemoryContextSwitchTo(expr->func->fn_cxt);
1326  expr->paramnos = bms_add_member(expr->paramnos, dno);
1327  MemoryContextSwitchTo(oldcontext);
1328 
1329  param = makeNode(Param);
1330  param->paramkind = PARAM_EXTERN;
1331  param->paramid = dno + 1;
1333  datum,
1334  &param->paramtype,
1335  &param->paramtypmod,
1336  &param->paramcollid);
1337  param->location = location;
1338 
1339  return (Node *) param;
1340 }
1341 
1342 
1343 /* ----------
1344  * plpgsql_parse_word The scanner calls this to postparse
1345  * any single word that is not a reserved keyword.
1346  *
1347  * word1 is the downcased/dequoted identifier; it must be palloc'd in the
1348  * function's long-term memory context.
1349  *
1350  * yytxt is the original token text; we need this to check for quoting,
1351  * so that later checks for unreserved keywords work properly.
1352  *
1353  * If recognized as a variable, fill in *wdatum and return TRUE;
1354  * if not recognized, fill in *word and return FALSE.
1355  * (Note: those two pointers actually point to members of the same union,
1356  * but for notational reasons we pass them separately.)
1357  * ----------
1358  */
1359 bool
1360 plpgsql_parse_word(char *word1, const char *yytxt,
1361  PLwdatum *wdatum, PLword *word)
1362 {
1363  PLpgSQL_nsitem *ns;
1364 
1365  /*
1366  * We should do nothing in DECLARE sections. In SQL expressions, there's
1367  * no need to do anything either --- lookup will happen when the
1368  * expression is compiled.
1369  */
1371  {
1372  /*
1373  * Do a lookup in the current namespace stack
1374  */
1375  ns = plpgsql_ns_lookup(plpgsql_ns_top(), false,
1376  word1, NULL, NULL,
1377  NULL);
1378 
1379  if (ns != NULL)
1380  {
1381  switch (ns->itemtype)
1382  {
1383  case PLPGSQL_NSTYPE_VAR:
1384  case PLPGSQL_NSTYPE_ROW:
1385  case PLPGSQL_NSTYPE_REC:
1386  wdatum->datum = plpgsql_Datums[ns->itemno];
1387  wdatum->ident = word1;
1388  wdatum->quoted = (yytxt[0] == '"');
1389  wdatum->idents = NIL;
1390  return true;
1391 
1392  default:
1393  /* plpgsql_ns_lookup should never return anything else */
1394  elog(ERROR, "unrecognized plpgsql itemtype: %d",
1395  ns->itemtype);
1396  }
1397  }
1398  }
1399 
1400  /*
1401  * Nothing found - up to now it's a word without any special meaning for
1402  * us.
1403  */
1404  word->ident = word1;
1405  word->quoted = (yytxt[0] == '"');
1406  return false;
1407 }
1408 
1409 
1410 /* ----------
1411  * plpgsql_parse_dblword Same lookup for two words
1412  * separated by a dot.
1413  * ----------
1414  */
1415 bool
1416 plpgsql_parse_dblword(char *word1, char *word2,
1417  PLwdatum *wdatum, PLcword *cword)
1418 {
1419  PLpgSQL_nsitem *ns;
1420  List *idents;
1421  int nnames;
1422 
1423  idents = list_make2(makeString(word1),
1424  makeString(word2));
1425 
1426  /*
1427  * We should do nothing in DECLARE sections. In SQL expressions, we
1428  * really only need to make sure that RECFIELD datums are created when
1429  * needed.
1430  */
1432  {
1433  /*
1434  * Do a lookup in the current namespace stack
1435  */
1436  ns = plpgsql_ns_lookup(plpgsql_ns_top(), false,
1437  word1, word2, NULL,
1438  &nnames);
1439  if (ns != NULL)
1440  {
1441  switch (ns->itemtype)
1442  {
1443  case PLPGSQL_NSTYPE_VAR:
1444  /* Block-qualified reference to scalar variable. */
1445  wdatum->datum = plpgsql_Datums[ns->itemno];
1446  wdatum->ident = NULL;
1447  wdatum->quoted = false; /* not used */
1448  wdatum->idents = idents;
1449  return true;
1450 
1451  case PLPGSQL_NSTYPE_REC:
1452  if (nnames == 1)
1453  {
1454  /*
1455  * First word is a record name, so second word could
1456  * be a field in this record. We build a RECFIELD
1457  * datum whether it is or not --- any error will be
1458  * detected later.
1459  */
1460  PLpgSQL_recfield *new;
1461 
1462  new = palloc(sizeof(PLpgSQL_recfield));
1463  new->dtype = PLPGSQL_DTYPE_RECFIELD;
1464  new->fieldname = pstrdup(word2);
1465  new->recparentno = ns->itemno;
1466 
1468 
1469  wdatum->datum = (PLpgSQL_datum *) new;
1470  }
1471  else
1472  {
1473  /* Block-qualified reference to record variable. */
1474  wdatum->datum = plpgsql_Datums[ns->itemno];
1475  }
1476  wdatum->ident = NULL;
1477  wdatum->quoted = false; /* not used */
1478  wdatum->idents = idents;
1479  return true;
1480 
1481  case PLPGSQL_NSTYPE_ROW:
1482  if (nnames == 1)
1483  {
1484  /*
1485  * First word is a row name, so second word could be a
1486  * field in this row. Again, no error now if it
1487  * isn't.
1488  */
1489  PLpgSQL_row *row;
1490  int i;
1491 
1492  row = (PLpgSQL_row *) (plpgsql_Datums[ns->itemno]);
1493  for (i = 0; i < row->nfields; i++)
1494  {
1495  if (row->fieldnames[i] &&
1496  strcmp(row->fieldnames[i], word2) == 0)
1497  {
1498  wdatum->datum = plpgsql_Datums[row->varnos[i]];
1499  wdatum->ident = NULL;
1500  wdatum->quoted = false; /* not used */
1501  wdatum->idents = idents;
1502  return true;
1503  }
1504  }
1505  /* fall through to return CWORD */
1506  }
1507  else
1508  {
1509  /* Block-qualified reference to row variable. */
1510  wdatum->datum = plpgsql_Datums[ns->itemno];
1511  wdatum->ident = NULL;
1512  wdatum->quoted = false; /* not used */
1513  wdatum->idents = idents;
1514  return true;
1515  }
1516  break;
1517 
1518  default:
1519  break;
1520  }
1521  }
1522  }
1523 
1524  /* Nothing found */
1525  cword->idents = idents;
1526  return false;
1527 }
1528 
1529 
1530 /* ----------
1531  * plpgsql_parse_tripword Same lookup for three words
1532  * separated by dots.
1533  * ----------
1534  */
1535 bool
1536 plpgsql_parse_tripword(char *word1, char *word2, char *word3,
1537  PLwdatum *wdatum, PLcword *cword)
1538 {
1539  PLpgSQL_nsitem *ns;
1540  List *idents;
1541  int nnames;
1542 
1543  idents = list_make3(makeString(word1),
1544  makeString(word2),
1545  makeString(word3));
1546 
1547  /*
1548  * We should do nothing in DECLARE sections. In SQL expressions, we
1549  * really only need to make sure that RECFIELD datums are created when
1550  * needed.
1551  */
1553  {
1554  /*
1555  * Do a lookup in the current namespace stack. Must find a qualified
1556  * reference, else ignore.
1557  */
1558  ns = plpgsql_ns_lookup(plpgsql_ns_top(), false,
1559  word1, word2, word3,
1560  &nnames);
1561  if (ns != NULL && nnames == 2)
1562  {
1563  switch (ns->itemtype)
1564  {
1565  case PLPGSQL_NSTYPE_REC:
1566  {
1567  /*
1568  * words 1/2 are a record name, so third word could be
1569  * a field in this record.
1570  */
1571  PLpgSQL_recfield *new;
1572 
1573  new = palloc(sizeof(PLpgSQL_recfield));
1574  new->dtype = PLPGSQL_DTYPE_RECFIELD;
1575  new->fieldname = pstrdup(word3);
1576  new->recparentno = ns->itemno;
1577 
1579 
1580  wdatum->datum = (PLpgSQL_datum *) new;
1581  wdatum->ident = NULL;
1582  wdatum->quoted = false; /* not used */
1583  wdatum->idents = idents;
1584  return true;
1585  }
1586 
1587  case PLPGSQL_NSTYPE_ROW:
1588  {
1589  /*
1590  * words 1/2 are a row name, so third word could be a
1591  * field in this row.
1592  */
1593  PLpgSQL_row *row;
1594  int i;
1595 
1596  row = (PLpgSQL_row *) (plpgsql_Datums[ns->itemno]);
1597  for (i = 0; i < row->nfields; i++)
1598  {
1599  if (row->fieldnames[i] &&
1600  strcmp(row->fieldnames[i], word3) == 0)
1601  {
1602  wdatum->datum = plpgsql_Datums[row->varnos[i]];
1603  wdatum->ident = NULL;
1604  wdatum->quoted = false; /* not used */
1605  wdatum->idents = idents;
1606  return true;
1607  }
1608  }
1609  /* fall through to return CWORD */
1610  break;
1611  }
1612 
1613  default:
1614  break;
1615  }
1616  }
1617  }
1618 
1619  /* Nothing found */
1620  cword->idents = idents;
1621  return false;
1622 }
1623 
1624 
1625 /* ----------
1626  * plpgsql_parse_wordtype The scanner found word%TYPE. word can be
1627  * a variable name or a basetype.
1628  *
1629  * Returns datatype struct, or NULL if no match found for word.
1630  * ----------
1631  */
1632 PLpgSQL_type *
1634 {
1635  PLpgSQL_type *dtype;
1636  PLpgSQL_nsitem *nse;
1637  HeapTuple typeTup;
1638 
1639  /*
1640  * Do a lookup in the current namespace stack
1641  */
1642  nse = plpgsql_ns_lookup(plpgsql_ns_top(), false,
1643  ident, NULL, NULL,
1644  NULL);
1645 
1646  if (nse != NULL)
1647  {
1648  switch (nse->itemtype)
1649  {
1650  case PLPGSQL_NSTYPE_VAR:
1651  return ((PLpgSQL_var *) (plpgsql_Datums[nse->itemno]))->datatype;
1652 
1653  /* XXX perhaps allow REC/ROW here? */
1654 
1655  default:
1656  return NULL;
1657  }
1658  }
1659 
1660  /*
1661  * Word wasn't found in the namespace stack. Try to find a data type with
1662  * that name, but ignore shell types and complex types.
1663  */
1664  typeTup = LookupTypeName(NULL, makeTypeName(ident), NULL, false);
1665  if (typeTup)
1666  {
1667  Form_pg_type typeStruct = (Form_pg_type) GETSTRUCT(typeTup);
1668 
1669  if (!typeStruct->typisdefined ||
1670  typeStruct->typrelid != InvalidOid)
1671  {
1672  ReleaseSysCache(typeTup);
1673  return NULL;
1674  }
1675 
1676  dtype = build_datatype(typeTup, -1,
1677  plpgsql_curr_compile->fn_input_collation);
1678 
1679  ReleaseSysCache(typeTup);
1680  return dtype;
1681  }
1682 
1683  /*
1684  * Nothing found - up to now it's a word without any special meaning for
1685  * us.
1686  */
1687  return NULL;
1688 }
1689 
1690 
1691 /* ----------
1692  * plpgsql_parse_cwordtype Same lookup for compositeword%TYPE
1693  * ----------
1694  */
1695 PLpgSQL_type *
1697 {
1698  PLpgSQL_type *dtype = NULL;
1699  PLpgSQL_nsitem *nse;
1700  const char *fldname;
1701  Oid classOid;
1702  HeapTuple classtup = NULL;
1703  HeapTuple attrtup = NULL;
1704  HeapTuple typetup = NULL;
1705  Form_pg_class classStruct;
1706  Form_pg_attribute attrStruct;
1707  MemoryContext oldCxt;
1708 
1709  /* Avoid memory leaks in the long-term function context */
1710  oldCxt = MemoryContextSwitchTo(plpgsql_compile_tmp_cxt);
1711 
1712  if (list_length(idents) == 2)
1713  {
1714  /*
1715  * Do a lookup in the current namespace stack. We don't need to check
1716  * number of names matched, because we will only consider scalar
1717  * variables.
1718  */
1719  nse = plpgsql_ns_lookup(plpgsql_ns_top(), false,
1720  strVal(linitial(idents)),
1721  strVal(lsecond(idents)),
1722  NULL,
1723  NULL);
1724 
1725  if (nse != NULL && nse->itemtype == PLPGSQL_NSTYPE_VAR)
1726  {
1727  dtype = ((PLpgSQL_var *) (plpgsql_Datums[nse->itemno]))->datatype;
1728  goto done;
1729  }
1730 
1731  /*
1732  * First word could also be a table name
1733  */
1734  classOid = RelnameGetRelid(strVal(linitial(idents)));
1735  if (!OidIsValid(classOid))
1736  goto done;
1737  fldname = strVal(lsecond(idents));
1738  }
1739  else if (list_length(idents) == 3)
1740  {
1741  RangeVar *relvar;
1742 
1743  relvar = makeRangeVar(strVal(linitial(idents)),
1744  strVal(lsecond(idents)),
1745  -1);
1746  /* Can't lock relation - we might not have privileges. */
1747  classOid = RangeVarGetRelid(relvar, NoLock, true);
1748  if (!OidIsValid(classOid))
1749  goto done;
1750  fldname = strVal(lthird(idents));
1751  }
1752  else
1753  goto done;
1754 
1755  classtup = SearchSysCache1(RELOID, ObjectIdGetDatum(classOid));
1756  if (!HeapTupleIsValid(classtup))
1757  goto done;
1758  classStruct = (Form_pg_class) GETSTRUCT(classtup);
1759 
1760  /*
1761  * It must be a relation, sequence, view, materialized view, composite
1762  * type, or foreign table
1763  */
1764  if (classStruct->relkind != RELKIND_RELATION &&
1765  classStruct->relkind != RELKIND_SEQUENCE &&
1766  classStruct->relkind != RELKIND_VIEW &&
1767  classStruct->relkind != RELKIND_MATVIEW &&
1768  classStruct->relkind != RELKIND_COMPOSITE_TYPE &&
1769  classStruct->relkind != RELKIND_FOREIGN_TABLE &&
1770  classStruct->relkind != RELKIND_PARTITIONED_TABLE)
1771  goto done;
1772 
1773  /*
1774  * Fetch the named table field and its type
1775  */
1776  attrtup = SearchSysCacheAttName(classOid, fldname);
1777  if (!HeapTupleIsValid(attrtup))
1778  goto done;
1779  attrStruct = (Form_pg_attribute) GETSTRUCT(attrtup);
1780 
1781  typetup = SearchSysCache1(TYPEOID,
1782  ObjectIdGetDatum(attrStruct->atttypid));
1783  if (!HeapTupleIsValid(typetup))
1784  elog(ERROR, "cache lookup failed for type %u", attrStruct->atttypid);
1785 
1786  /*
1787  * Found that - build a compiler type struct in the caller's cxt and
1788  * return it
1789  */
1790  MemoryContextSwitchTo(oldCxt);
1791  dtype = build_datatype(typetup,
1792  attrStruct->atttypmod,
1793  attrStruct->attcollation);
1794  MemoryContextSwitchTo(plpgsql_compile_tmp_cxt);
1795 
1796 done:
1797  if (HeapTupleIsValid(classtup))
1798  ReleaseSysCache(classtup);
1799  if (HeapTupleIsValid(attrtup))
1800  ReleaseSysCache(attrtup);
1801  if (HeapTupleIsValid(typetup))
1802  ReleaseSysCache(typetup);
1803 
1804  MemoryContextSwitchTo(oldCxt);
1805  return dtype;
1806 }
1807 
1808 /* ----------
1809  * plpgsql_parse_wordrowtype Scanner found word%ROWTYPE.
1810  * So word must be a table name.
1811  * ----------
1812  */
1813 PLpgSQL_type *
1815 {
1816  Oid classOid;
1817 
1818  /* Lookup the relation */
1819  classOid = RelnameGetRelid(ident);
1820  if (!OidIsValid(classOid))
1821  ereport(ERROR,
1823  errmsg("relation \"%s\" does not exist", ident)));
1824 
1825  /* Build and return the row type struct */
1826  return plpgsql_build_datatype(get_rel_type_id(classOid), -1, InvalidOid);
1827 }
1828 
1829 /* ----------
1830  * plpgsql_parse_cwordrowtype Scanner found compositeword%ROWTYPE.
1831  * So word must be a namespace qualified table name.
1832  * ----------
1833  */
1834 PLpgSQL_type *
1836 {
1837  Oid classOid;
1838  RangeVar *relvar;
1839  MemoryContext oldCxt;
1840 
1841  if (list_length(idents) != 2)
1842  return NULL;
1843 
1844  /* Avoid memory leaks in long-term function context */
1845  oldCxt = MemoryContextSwitchTo(plpgsql_compile_tmp_cxt);
1846 
1847  /* Look up relation name. Can't lock it - we might not have privileges. */
1848  relvar = makeRangeVar(strVal(linitial(idents)),
1849  strVal(lsecond(idents)),
1850  -1);
1851  classOid = RangeVarGetRelid(relvar, NoLock, false);
1852 
1853  MemoryContextSwitchTo(oldCxt);
1854 
1855  /* Build and return the row type struct */
1856  return plpgsql_build_datatype(get_rel_type_id(classOid), -1, InvalidOid);
1857 }
1858 
1859 /*
1860  * plpgsql_build_variable - build a datum-array entry of a given
1861  * datatype
1862  *
1863  * The returned struct may be a PLpgSQL_var, PLpgSQL_row, or
1864  * PLpgSQL_rec depending on the given datatype, and is allocated via
1865  * palloc. The struct is automatically added to the current datum
1866  * array, and optionally to the current namespace.
1867  */
1869 plpgsql_build_variable(const char *refname, int lineno, PLpgSQL_type *dtype,
1870  bool add2namespace)
1871 {
1873 
1874  switch (dtype->ttype)
1875  {
1876  case PLPGSQL_TTYPE_SCALAR:
1877  {
1878  /* Ordinary scalar datatype */
1879  PLpgSQL_var *var;
1880 
1881  var = palloc0(sizeof(PLpgSQL_var));
1882  var->dtype = PLPGSQL_DTYPE_VAR;
1883  var->refname = pstrdup(refname);
1884  var->lineno = lineno;
1885  var->datatype = dtype;
1886  /* other fields might be filled by caller */
1887 
1888  /* preset to NULL */
1889  var->value = 0;
1890  var->isnull = true;
1891  var->freeval = false;
1892 
1894  if (add2namespace)
1896  var->dno,
1897  refname);
1898  result = (PLpgSQL_variable *) var;
1899  break;
1900  }
1901  case PLPGSQL_TTYPE_ROW:
1902  {
1903  /* Composite type -- build a row variable */
1904  PLpgSQL_row *row;
1905 
1906  row = build_row_from_class(dtype->typrelid);
1907 
1908  row->dtype = PLPGSQL_DTYPE_ROW;
1909  row->refname = pstrdup(refname);
1910  row->lineno = lineno;
1911 
1913  if (add2namespace)
1915  row->dno,
1916  refname);
1917  result = (PLpgSQL_variable *) row;
1918  break;
1919  }
1920  case PLPGSQL_TTYPE_REC:
1921  {
1922  /* "record" type -- build a record variable */
1923  PLpgSQL_rec *rec;
1924 
1925  rec = plpgsql_build_record(refname, lineno, add2namespace);
1926  result = (PLpgSQL_variable *) rec;
1927  break;
1928  }
1929  case PLPGSQL_TTYPE_PSEUDO:
1930  ereport(ERROR,
1931  (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
1932  errmsg("variable \"%s\" has pseudo-type %s",
1933  refname, format_type_be(dtype->typoid))));
1934  result = NULL; /* keep compiler quiet */
1935  break;
1936  default:
1937  elog(ERROR, "unrecognized ttype: %d", dtype->ttype);
1938  result = NULL; /* keep compiler quiet */
1939  break;
1940  }
1941 
1942  return result;
1943 }
1944 
1945 /*
1946  * Build empty named record variable, and optionally add it to namespace
1947  */
1948 PLpgSQL_rec *
1949 plpgsql_build_record(const char *refname, int lineno, bool add2namespace)
1950 {
1951  PLpgSQL_rec *rec;
1952 
1953  rec = palloc0(sizeof(PLpgSQL_rec));
1954  rec->dtype = PLPGSQL_DTYPE_REC;
1955  rec->refname = pstrdup(refname);
1956  rec->lineno = lineno;
1957  rec->tup = NULL;
1958  rec->tupdesc = NULL;
1959  rec->freetup = false;
1960  rec->freetupdesc = false;
1962  if (add2namespace)
1964 
1965  return rec;
1966 }
1967 
1968 /*
1969  * Build a row-variable data structure given the pg_class OID.
1970  */
1971 static PLpgSQL_row *
1973 {
1974  PLpgSQL_row *row;
1975  Relation rel;
1976  Form_pg_class classStruct;
1977  const char *relname;
1978  int i;
1979 
1980  /*
1981  * Open the relation to get info.
1982  */
1983  rel = relation_open(classOid, AccessShareLock);
1984  classStruct = RelationGetForm(rel);
1985  relname = RelationGetRelationName(rel);
1986 
1987  /*
1988  * Accept relation, sequence, view, materialized view, composite type, or
1989  * foreign table.
1990  */
1991  if (classStruct->relkind != RELKIND_RELATION &&
1992  classStruct->relkind != RELKIND_SEQUENCE &&
1993  classStruct->relkind != RELKIND_VIEW &&
1994  classStruct->relkind != RELKIND_MATVIEW &&
1995  classStruct->relkind != RELKIND_COMPOSITE_TYPE &&
1996  classStruct->relkind != RELKIND_FOREIGN_TABLE &&
1997  classStruct->relkind != RELKIND_PARTITIONED_TABLE)
1998  ereport(ERROR,
1999  (errcode(ERRCODE_WRONG_OBJECT_TYPE),
2000  errmsg("relation \"%s\" is not a table", relname)));
2001 
2002  /*
2003  * Create a row datum entry and all the required variables that it will
2004  * point to.
2005  */
2006  row = palloc0(sizeof(PLpgSQL_row));
2007  row->dtype = PLPGSQL_DTYPE_ROW;
2009  row->nfields = classStruct->relnatts;
2010  row->fieldnames = palloc(sizeof(char *) * row->nfields);
2011  row->varnos = palloc(sizeof(int) * row->nfields);
2012 
2013  for (i = 0; i < row->nfields; i++)
2014  {
2015  Form_pg_attribute attrStruct;
2016 
2017  /*
2018  * Get the attribute and check for dropped column
2019  */
2020  attrStruct = TupleDescAttr(row->rowtupdesc, i);
2021 
2022  if (!attrStruct->attisdropped)
2023  {
2024  char *attname;
2025  char refname[(NAMEDATALEN * 2) + 100];
2026  PLpgSQL_variable *var;
2027 
2028  attname = NameStr(attrStruct->attname);
2029  snprintf(refname, sizeof(refname), "%s.%s", relname, attname);
2030 
2031  /*
2032  * Create the internal variable for the field
2033  *
2034  * We know if the table definitions contain a default value or if
2035  * the field is declared in the table as NOT NULL. But it's
2036  * possible to create a table field as NOT NULL without a default
2037  * value and that would lead to problems later when initializing
2038  * the variables due to entering a block at execution time. Thus
2039  * we ignore this information for now.
2040  */
2041  var = plpgsql_build_variable(refname, 0,
2042  plpgsql_build_datatype(attrStruct->atttypid,
2043  attrStruct->atttypmod,
2044  attrStruct->attcollation),
2045  false);
2046 
2047  /* Add the variable to the row */
2048  row->fieldnames[i] = attname;
2049  row->varnos[i] = var->dno;
2050  }
2051  else
2052  {
2053  /* Leave a hole in the row structure for the dropped col */
2054  row->fieldnames[i] = NULL;
2055  row->varnos[i] = -1;
2056  }
2057  }
2058 
2060 
2061  return row;
2062 }
2063 
2064 /*
2065  * Build a row-variable data structure given the component variables.
2066  */
2067 static PLpgSQL_row *
2069 {
2070  PLpgSQL_row *row;
2071  int i;
2072 
2073  row = palloc0(sizeof(PLpgSQL_row));
2074  row->dtype = PLPGSQL_DTYPE_ROW;
2075  row->rowtupdesc = CreateTemplateTupleDesc(numvars, false);
2076  row->nfields = numvars;
2077  row->fieldnames = palloc(numvars * sizeof(char *));
2078  row->varnos = palloc(numvars * sizeof(int));
2079 
2080  for (i = 0; i < numvars; i++)
2081  {
2082  PLpgSQL_variable *var = vars[i];
2083  Oid typoid = RECORDOID;
2084  int32 typmod = -1;
2085  Oid typcoll = InvalidOid;
2086 
2087  switch (var->dtype)
2088  {
2089  case PLPGSQL_DTYPE_VAR:
2090  typoid = ((PLpgSQL_var *) var)->datatype->typoid;
2091  typmod = ((PLpgSQL_var *) var)->datatype->atttypmod;
2092  typcoll = ((PLpgSQL_var *) var)->datatype->collation;
2093  break;
2094 
2095  case PLPGSQL_DTYPE_REC:
2096  break;
2097 
2098  case PLPGSQL_DTYPE_ROW:
2099  if (((PLpgSQL_row *) var)->rowtupdesc)
2100  {
2101  typoid = ((PLpgSQL_row *) var)->rowtupdesc->tdtypeid;
2102  typmod = ((PLpgSQL_row *) var)->rowtupdesc->tdtypmod;
2103  /* composite types have no collation */
2104  }
2105  break;
2106 
2107  default:
2108  elog(ERROR, "unrecognized dtype: %d", var->dtype);
2109  }
2110 
2111  row->fieldnames[i] = var->refname;
2112  row->varnos[i] = var->dno;
2113 
2114  TupleDescInitEntry(row->rowtupdesc, i + 1,
2115  var->refname,
2116  typoid, typmod,
2117  0);
2118  TupleDescInitEntryCollation(row->rowtupdesc, i + 1, typcoll);
2119  }
2120 
2121  return row;
2122 }
2123 
2124 /*
2125  * plpgsql_build_datatype
2126  * Build PLpgSQL_type struct given type OID, typmod, and collation.
2127  *
2128  * If collation is not InvalidOid then it overrides the type's default
2129  * collation. But collation is ignored if the datatype is non-collatable.
2130  */
2131 PLpgSQL_type *
2132 plpgsql_build_datatype(Oid typeOid, int32 typmod, Oid collation)
2133 {
2134  HeapTuple typeTup;
2135  PLpgSQL_type *typ;
2136 
2137  typeTup = SearchSysCache1(TYPEOID, ObjectIdGetDatum(typeOid));
2138  if (!HeapTupleIsValid(typeTup))
2139  elog(ERROR, "cache lookup failed for type %u", typeOid);
2140 
2141  typ = build_datatype(typeTup, typmod, collation);
2142 
2143  ReleaseSysCache(typeTup);
2144 
2145  return typ;
2146 }
2147 
2148 /*
2149  * Utility subroutine to make a PLpgSQL_type struct given a pg_type entry
2150  */
2151 static PLpgSQL_type *
2152 build_datatype(HeapTuple typeTup, int32 typmod, Oid collation)
2153 {
2154  Form_pg_type typeStruct = (Form_pg_type) GETSTRUCT(typeTup);
2155  PLpgSQL_type *typ;
2156 
2157  if (!typeStruct->typisdefined)
2158  ereport(ERROR,
2159  (errcode(ERRCODE_UNDEFINED_OBJECT),
2160  errmsg("type \"%s\" is only a shell",
2161  NameStr(typeStruct->typname))));
2162 
2163  typ = (PLpgSQL_type *) palloc(sizeof(PLpgSQL_type));
2164 
2165  typ->typname = pstrdup(NameStr(typeStruct->typname));
2166  typ->typoid = HeapTupleGetOid(typeTup);
2167  switch (typeStruct->typtype)
2168  {
2169  case TYPTYPE_BASE:
2170  case TYPTYPE_DOMAIN:
2171  case TYPTYPE_ENUM:
2172  case TYPTYPE_RANGE:
2173  typ->ttype = PLPGSQL_TTYPE_SCALAR;
2174  break;
2175  case TYPTYPE_COMPOSITE:
2176  Assert(OidIsValid(typeStruct->typrelid));
2177  typ->ttype = PLPGSQL_TTYPE_ROW;
2178  break;
2179  case TYPTYPE_PSEUDO:
2180  if (typ->typoid == RECORDOID)
2181  typ->ttype = PLPGSQL_TTYPE_REC;
2182  else
2183  typ->ttype = PLPGSQL_TTYPE_PSEUDO;
2184  break;
2185  default:
2186  elog(ERROR, "unrecognized typtype: %d",
2187  (int) typeStruct->typtype);
2188  break;
2189  }
2190  typ->typlen = typeStruct->typlen;
2191  typ->typbyval = typeStruct->typbyval;
2192  typ->typtype = typeStruct->typtype;
2193  typ->typrelid = typeStruct->typrelid;
2194  typ->collation = typeStruct->typcollation;
2195  if (OidIsValid(collation) && OidIsValid(typ->collation))
2196  typ->collation = collation;
2197  /* Detect if type is true array, or domain thereof */
2198  /* NB: this is only used to decide whether to apply expand_array */
2199  if (typeStruct->typtype == TYPTYPE_BASE)
2200  {
2201  /*
2202  * This test should include what get_element_type() checks. We also
2203  * disallow non-toastable array types (i.e. oidvector and int2vector).
2204  */
2205  typ->typisarray = (typeStruct->typlen == -1 &&
2206  OidIsValid(typeStruct->typelem) &&
2207  typeStruct->typstorage != 'p');
2208  }
2209  else if (typeStruct->typtype == TYPTYPE_DOMAIN)
2210  {
2211  /* we can short-circuit looking up base types if it's not varlena */
2212  typ->typisarray = (typeStruct->typlen == -1 &&
2213  typeStruct->typstorage != 'p' &&
2214  OidIsValid(get_base_element_type(typeStruct->typbasetype)));
2215  }
2216  else
2217  typ->typisarray = false;
2218  typ->atttypmod = typmod;
2219 
2220  return typ;
2221 }
2222 
2223 /*
2224  * plpgsql_recognize_err_condition
2225  * Check condition name and translate it to SQLSTATE.
2226  *
2227  * Note: there are some cases where the same condition name has multiple
2228  * entries in the table. We arbitrarily return the first match.
2229  */
2230 int
2231 plpgsql_recognize_err_condition(const char *condname, bool allow_sqlstate)
2232 {
2233  int i;
2234 
2235  if (allow_sqlstate)
2236  {
2237  if (strlen(condname) == 5 &&
2238  strspn(condname, "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ") == 5)
2239  return MAKE_SQLSTATE(condname[0],
2240  condname[1],
2241  condname[2],
2242  condname[3],
2243  condname[4]);
2244  }
2245 
2246  for (i = 0; exception_label_map[i].label != NULL; i++)
2247  {
2248  if (strcmp(condname, exception_label_map[i].label) == 0)
2249  return exception_label_map[i].sqlerrstate;
2250  }
2251 
2252  ereport(ERROR,
2253  (errcode(ERRCODE_UNDEFINED_OBJECT),
2254  errmsg("unrecognized exception condition \"%s\"",
2255  condname)));
2256  return 0; /* keep compiler quiet */
2257 }
2258 
2259 /*
2260  * plpgsql_parse_err_condition
2261  * Generate PLpgSQL_condition entry(s) for an exception condition name
2262  *
2263  * This has to be able to return a list because there are some duplicate
2264  * names in the table of error code names.
2265  */
2268 {
2269  int i;
2270  PLpgSQL_condition *new;
2271  PLpgSQL_condition *prev;
2272 
2273  /*
2274  * XXX Eventually we will want to look for user-defined exception names
2275  * here.
2276  */
2277 
2278  /*
2279  * OTHERS is represented as code 0 (which would map to '00000', but we
2280  * have no need to represent that as an exception condition).
2281  */
2282  if (strcmp(condname, "others") == 0)
2283  {
2284  new = palloc(sizeof(PLpgSQL_condition));
2285  new->sqlerrstate = 0;
2286  new->condname = condname;
2287  new->next = NULL;
2288  return new;
2289  }
2290 
2291  prev = NULL;
2292  for (i = 0; exception_label_map[i].label != NULL; i++)
2293  {
2294  if (strcmp(condname, exception_label_map[i].label) == 0)
2295  {
2296  new = palloc(sizeof(PLpgSQL_condition));
2297  new->sqlerrstate = exception_label_map[i].sqlerrstate;
2298  new->condname = condname;
2299  new->next = prev;
2300  prev = new;
2301  }
2302  }
2303 
2304  if (!prev)
2305  ereport(ERROR,
2306  (errcode(ERRCODE_UNDEFINED_OBJECT),
2307  errmsg("unrecognized exception condition \"%s\"",
2308  condname)));
2309 
2310  return prev;
2311 }
2312 
2313 /* ----------
2314  * plpgsql_start_datums Initialize datum list at compile startup.
2315  * ----------
2316  */
2317 static void
2319 {
2320  datums_alloc = 128;
2321  plpgsql_nDatums = 0;
2322  /* This is short-lived, so needn't allocate in function's cxt */
2323  plpgsql_Datums = MemoryContextAlloc(plpgsql_compile_tmp_cxt,
2324  sizeof(PLpgSQL_datum *) * datums_alloc);
2325  /* datums_last tracks what's been seen by plpgsql_add_initdatums() */
2326  datums_last = 0;
2327 }
2328 
2329 /* ----------
2330  * plpgsql_adddatum Add a variable, record or row
2331  * to the compiler's datum list.
2332  * ----------
2333  */
2334 void
2336 {
2338  {
2339  datums_alloc *= 2;
2340  plpgsql_Datums = repalloc(plpgsql_Datums, sizeof(PLpgSQL_datum *) * datums_alloc);
2341  }
2342 
2343  new->dno = plpgsql_nDatums;
2344  plpgsql_Datums[plpgsql_nDatums++] = new;
2345 }
2346 
2347 /* ----------
2348  * plpgsql_finish_datums Copy completed datum info into function struct.
2349  *
2350  * This is also responsible for building resettable_datums, a bitmapset
2351  * of the dnos of all ROW, REC, and RECFIELD datums in the function.
2352  * ----------
2353  */
2354 static void
2356 {
2357  Bitmapset *resettable_datums = NULL;
2358  int i;
2359 
2360  function->ndatums = plpgsql_nDatums;
2361  function->datums = palloc(sizeof(PLpgSQL_datum *) * plpgsql_nDatums);
2362  for (i = 0; i < plpgsql_nDatums; i++)
2363  {
2364  function->datums[i] = plpgsql_Datums[i];
2365  switch (function->datums[i]->dtype)
2366  {
2367  case PLPGSQL_DTYPE_ROW:
2368  case PLPGSQL_DTYPE_REC:
2370  resettable_datums = bms_add_member(resettable_datums, i);
2371  break;
2372 
2373  default:
2374  break;
2375  }
2376  }
2377  function->resettable_datums = resettable_datums;
2378 }
2379 
2380 
2381 /* ----------
2382  * plpgsql_add_initdatums Make an array of the datum numbers of
2383  * all the simple VAR datums created since the last call
2384  * to this function.
2385  *
2386  * If varnos is NULL, we just forget any datum entries created since the
2387  * last call.
2388  *
2389  * This is used around a DECLARE section to create a list of the VARs
2390  * that have to be initialized at block entry. Note that VARs can also
2391  * be created elsewhere than DECLARE, eg by a FOR-loop, but it is then
2392  * the responsibility of special-purpose code to initialize them.
2393  * ----------
2394  */
2395 int
2397 {
2398  int i;
2399  int n = 0;
2400 
2401  for (i = datums_last; i < plpgsql_nDatums; i++)
2402  {
2403  switch (plpgsql_Datums[i]->dtype)
2404  {
2405  case PLPGSQL_DTYPE_VAR:
2406  n++;
2407  break;
2408 
2409  default:
2410  break;
2411  }
2412  }
2413 
2414  if (varnos != NULL)
2415  {
2416  if (n > 0)
2417  {
2418  *varnos = (int *) palloc(sizeof(int) * n);
2419 
2420  n = 0;
2421  for (i = datums_last; i < plpgsql_nDatums; i++)
2422  {
2423  switch (plpgsql_Datums[i]->dtype)
2424  {
2425  case PLPGSQL_DTYPE_VAR:
2426  (*varnos)[n++] = plpgsql_Datums[i]->dno;
2427 
2428  default:
2429  break;
2430  }
2431  }
2432  }
2433  else
2434  *varnos = NULL;
2435  }
2436 
2438  return n;
2439 }
2440 
2441 
2442 /*
2443  * Compute the hashkey for a given function invocation
2444  *
2445  * The hashkey is returned into the caller-provided storage at *hashkey.
2446  */
2447 static void
2449  Form_pg_proc procStruct,
2450  PLpgSQL_func_hashkey *hashkey,
2451  bool forValidator)
2452 {
2453  /* Make sure any unused bytes of the struct are zero */
2454  MemSet(hashkey, 0, sizeof(PLpgSQL_func_hashkey));
2455 
2456  /* get function OID */
2457  hashkey->funcOid = fcinfo->flinfo->fn_oid;
2458 
2459  /* get call context */
2460  hashkey->isTrigger = CALLED_AS_TRIGGER(fcinfo);
2461 
2462  /*
2463  * if trigger, get its OID. In validation mode we do not know what
2464  * relation or transition table names are intended to be used, so we leave
2465  * trigOid zero; the hash entry built in this case will never really be
2466  * used.
2467  */
2468  if (hashkey->isTrigger && !forValidator)
2469  {
2470  TriggerData *trigdata = (TriggerData *) fcinfo->context;
2471 
2472  hashkey->trigOid = trigdata->tg_trigger->tgoid;
2473  }
2474 
2475  /* get input collation, if known */
2476  hashkey->inputCollation = fcinfo->fncollation;
2477 
2478  if (procStruct->pronargs > 0)
2479  {
2480  /* get the argument types */
2481  memcpy(hashkey->argtypes, procStruct->proargtypes.values,
2482  procStruct->pronargs * sizeof(Oid));
2483 
2484  /* resolve any polymorphic argument types */
2485  plpgsql_resolve_polymorphic_argtypes(procStruct->pronargs,
2486  hashkey->argtypes,
2487  NULL,
2488  fcinfo->flinfo->fn_expr,
2489  forValidator,
2490  NameStr(procStruct->proname));
2491  }
2492 }
2493 
2494 /*
2495  * This is the same as the standard resolve_polymorphic_argtypes() function,
2496  * but with a special case for validation: assume that polymorphic arguments
2497  * are integer, integer-array or integer-range. Also, we go ahead and report
2498  * the error if we can't resolve the types.
2499  */
2500 static void
2502  Oid *argtypes, char *argmodes,
2503  Node *call_expr, bool forValidator,
2504  const char *proname)
2505 {
2506  int i;
2507 
2508  if (!forValidator)
2509  {
2510  /* normal case, pass to standard routine */
2511  if (!resolve_polymorphic_argtypes(numargs, argtypes, argmodes,
2512  call_expr))
2513  ereport(ERROR,
2514  (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
2515  errmsg("could not determine actual argument "
2516  "type for polymorphic function \"%s\"",
2517  proname)));
2518  }
2519  else
2520  {
2521  /* special validation case */
2522  for (i = 0; i < numargs; i++)
2523  {
2524  switch (argtypes[i])
2525  {
2526  case ANYELEMENTOID:
2527  case ANYNONARRAYOID:
2528  case ANYENUMOID: /* XXX dubious */
2529  argtypes[i] = INT4OID;
2530  break;
2531  case ANYARRAYOID:
2532  argtypes[i] = INT4ARRAYOID;
2533  break;
2534  case ANYRANGEOID:
2535  argtypes[i] = INT4RANGEOID;
2536  break;
2537  default:
2538  break;
2539  }
2540  }
2541  }
2542 }
2543 
2544 /*
2545  * delete_function - clean up as much as possible of a stale function cache
2546  *
2547  * We can't release the PLpgSQL_function struct itself, because of the
2548  * possibility that there are fn_extra pointers to it. We can release
2549  * the subsidiary storage, but only if there are no active evaluations
2550  * in progress. Otherwise we'll just leak that storage. Since the
2551  * case would only occur if a pg_proc update is detected during a nested
2552  * recursive call on the function, a leak seems acceptable.
2553  *
2554  * Note that this can be called more than once if there are multiple fn_extra
2555  * pointers to the same function cache. Hence be careful not to do things
2556  * twice.
2557  */
2558 static void
2560 {
2561  /* remove function from hash table (might be done already) */
2563 
2564  /* release the function's storage if safe and not done already */
2565  if (func->use_count == 0)
2567 }
2568 
2569 /* exported so we can call it from plpgsql_init() */
2570 void
2572 {
2573  HASHCTL ctl;
2574 
2575  /* don't allow double-initialization */
2576  Assert(plpgsql_HashTable == NULL);
2577 
2578  memset(&ctl, 0, sizeof(ctl));
2579  ctl.keysize = sizeof(PLpgSQL_func_hashkey);
2580  ctl.entrysize = sizeof(plpgsql_HashEnt);
2581  plpgsql_HashTable = hash_create("PLpgSQL function cache",
2583  &ctl,
2584  HASH_ELEM | HASH_BLOBS);
2585 }
2586 
2587 static PLpgSQL_function *
2589 {
2590  plpgsql_HashEnt *hentry;
2591 
2592  hentry = (plpgsql_HashEnt *) hash_search(plpgsql_HashTable,
2593  (void *) func_key,
2594  HASH_FIND,
2595  NULL);
2596  if (hentry)
2597  return hentry->function;
2598  else
2599  return NULL;
2600 }
2601 
2602 static void
2604  PLpgSQL_func_hashkey *func_key)
2605 {
2606  plpgsql_HashEnt *hentry;
2607  bool found;
2608 
2609  hentry = (plpgsql_HashEnt *) hash_search(plpgsql_HashTable,
2610  (void *) func_key,
2611  HASH_ENTER,
2612  &found);
2613  if (found)
2614  elog(WARNING, "trying to insert a function that already exists");
2615 
2616  hentry->function = function;
2617  /* prepare back link from function to hashtable key */
2618  function->fn_hashkey = &hentry->key;
2619 }
2620 
2621 static void
2623 {
2624  plpgsql_HashEnt *hentry;
2625 
2626  /* do nothing if not in table */
2627  if (function->fn_hashkey == NULL)
2628  return;
2629 
2630  hentry = (plpgsql_HashEnt *) hash_search(plpgsql_HashTable,
2631  (void *) function->fn_hashkey,
2632  HASH_REMOVE,
2633  NULL);
2634  if (hentry == NULL)
2635  elog(WARNING, "trying to delete function that does not exist");
2636 
2637  /* remove back link, which no longer points to allocated storage */
2638  function->fn_hashkey = NULL;
2639 }
#define list_make2(x1, x2)
Definition: pg_list.h:140
Value * makeString(char *str)
Definition: value.c:53
bool resolve_polymorphic_argtypes(int numargs, Oid *argtypes, char *argmodes, Node *call_expr)
Definition: funcapi.c:599
Type LookupTypeName(ParseState *pstate, const TypeName *typeName, int32 *typmod_p, bool missing_ok)
Definition: parse_type.c:57
PLpgSQL_function * plpgsql_compile_inline(char *proc_source)
Definition: pl_comp.c:799
#define list_make3(x1, x2, x3)
Definition: pg_list.h:141
int plpgsql_nDatums
Definition: pl_comp.c:46
int plpgsql_yyparse(void)
#define ANYNONARRAYOID
Definition: pg_type.h:704
PLpgSQL_datum_type dtype
Definition: plpgsql.h:302
#define NIL
Definition: pg_list.h:69
TupleDesc tupdesc
Definition: plpgsql.h:308
#define FUNCS_PER_USER
Definition: pl_comp.c:71
int plpgsql_latest_lineno(void)
Definition: pl_scanner.c:688
#define TYPTYPE_DOMAIN
Definition: pg_type.h:722
void plpgsql_free_function_memory(PLpgSQL_function *func)
Definition: pl_funcs.c:695
Oid argtypes[FUNC_MAX_ARGS]
Definition: plpgsql.h:802
#define CALLED_AS_EVENT_TRIGGER(fcinfo)
Definition: event_trigger.h:40
TupleDesc CreateTupleDescCopy(TupleDesc tupdesc)
Definition: tupdesc.c:102
#define IsA(nodeptr, _type_)
Definition: nodes.h:560
PLpgSQL_datum ** plpgsql_Datums
Definition: pl_comp.c:47
PLpgSQL_func_hashkey * fn_hashkey
Definition: plpgsql.h:826
PLpgSQL_type * plpgsql_parse_wordrowtype(char *ident)
Definition: pl_comp.c:1814
char * refname
Definition: plpgsql.h:281
#define NAMEOID
Definition: pg_type.h:300
int errhint(const char *fmt,...)
Definition: elog.c:987
static PLpgSQL_function * do_compile(FunctionCallInfo fcinfo, HeapTuple procTup, PLpgSQL_function *function, PLpgSQL_func_hashkey *hashkey, bool forValidator)
Definition: pl_comp.c:265
PLpgSQL_nsitem * plpgsql_ns_top(void)
Definition: pl_funcs.c:83
const char * label
Definition: pl_comp.c:79
bool plpgsql_parse_dblword(char *word1, char *word2, PLwdatum *wdatum, PLcword *cword)
Definition: pl_comp.c:1416
#define GETSTRUCT(TUP)
Definition: htup_details.h:656
PLpgSQL_type * plpgsql_build_datatype(Oid typeOid, int32 typmod, Oid collation)
Definition: pl_comp.c:2132
#define ERRCODE_UNDEFINED_TABLE
Definition: pgbench.c:61
static void compute_function_hashkey(FunctionCallInfo fcinfo, Form_pg_proc procStruct, PLpgSQL_func_hashkey *hashkey, bool forValidator)
Definition: pl_comp.c:2448
PLpgSQL_func_hashkey key
Definition: pl_comp.c:67
char * refname
Definition: plpgsql.h:258
#define HASH_ELEM
Definition: hsearch.h:87
static PLpgSQL_row * build_row_from_class(Oid classOid)
Definition: pl_comp.c:1972
#define TYPTYPE_BASE
Definition: pg_type.h:720
#define RelationGetDescr(relation)
Definition: rel.h:428
PLpgSQL_datum_type dtype
Definition: plpgsql.h:256
#define TYPTYPE_COMPOSITE
Definition: pg_type.h:721
Oid RelnameGetRelid(const char *relname)
Definition: namespace.c:654
#define OIDOID
Definition: pg_type.h:328
#define TEXTOID
Definition: pg_type.h:324
fmNodePtr context
Definition: fmgr.h:80
#define MAKE_SQLSTATE(ch1, ch2, ch3, ch4, ch5)
Definition: elog.h:62
static Node * plpgsql_pre_column_ref(ParseState *pstate, ColumnRef *cref)
Definition: pl_comp.c:1036
#define RangeVarGetRelid(relation, lockmode, missing_ok)
Definition: namespace.h:53
#define TupleDescAttr(tupdesc, i)
Definition: tupdesc.h:84
PLpgSQL_nsitem * plpgsql_ns_lookup(PLpgSQL_nsitem *ns_cur, bool localmode, const char *name1, const char *name2, const char *name3, int *names_used)
Definition: pl_funcs.c:132
#define RelationGetForm(relation)
Definition: rel.h:410
char * pstrdup(const char *in)
Definition: mcxt.c:1076
#define ANYELEMENTOID
Definition: pg_type.h:702
PLpgSQL_type * datatype
Definition: plpgsql.h:261
bool freetup
Definition: plpgsql.h:309
Oid tgoid
Definition: reltrigger.h:25
#define llast(l)
Definition: pg_list.h:131
int get_func_arg_info(HeapTuple procTup, Oid **p_argtypes, char ***p_argnames, char **p_argmodes)
Definition: funcapi.c:793
#define RELKIND_MATVIEW
Definition: pg_class.h:165
void plpgsql_ns_additem(PLpgSQL_nsitem_type itemtype, int itemno, const char *name)
Definition: pl_funcs.c:94
static MemoryContext MemoryContextSwitchTo(MemoryContext context)
Definition: palloc.h:109
#define Anum_pg_proc_prosrc
Definition: pg_proc.h:115
#define AccessShareLock
Definition: lockdefs.h:36
void plpgsql_HashTableInit(void)
Definition: pl_comp.c:2571
PLpgSQL_type_type ttype
Definition: plpgsql.h:180
#define INT4OID
Definition: pg_type.h:316
Size entrysize
Definition: hsearch.h:73
ParamKind paramkind
Definition: primnodes.h:244
Definition: nodes.h:509
PLpgSQL_rec * plpgsql_build_record(const char *refname, int lineno, bool add2namespace)
Definition: pl_comp.c:1949
int plpgsql_recognize_err_condition(const char *condname, bool allow_sqlstate)
Definition: pl_comp.c:2231
int plpgsql_extra_errors
Definition: pl_handler.c:55
PLpgSQL_type * plpgsql_parse_wordtype(char *ident)
Definition: pl_comp.c:1633
#define strVal(v)
Definition: value.h:54
int errcode(int sqlerrcode)
Definition: elog.c:575
void relation_close(Relation relation, LOCKMODE lockmode)
Definition: heapam.c:1266
#define MemSet(start, val, len)
Definition: c.h:846
char * format_type_be(Oid type_oid)
Definition: format_type.c:94
return result
Definition: formatting.c:1633
int snprintf(char *str, size_t count, const char *fmt,...) pg_attribute_printf(3
void * hash_search(HTAB *hashp, const void *keyPtr, HASHACTION action, bool *foundPtr)
Definition: dynahash.c:902
FormData_pg_type * Form_pg_type
Definition: pg_type.h:233
bool check_function_bodies
Definition: guc.c:447
#define PROARGMODE_VARIADIC
Definition: pg_proc.h:5570
void plpgsql_dumptree(PLpgSQL_function *func)
Definition: pl_funcs.c:1543
char * ident
Definition: plpgsql.h:989
unsigned int Oid
Definition: postgres_ext.h:31
struct ErrorContextCallback * previous
Definition: elog.h:238
#define OidIsValid(objectId)
Definition: c.h:532
char * refname
Definition: plpgsql.h:304
static void plpgsql_resolve_polymorphic_argtypes(int numargs, Oid *argtypes, char *argmodes, Node *call_expr, bool forValidator, const char *proname)
Definition: pl_comp.c:2501
static void plpgsql_HashTableInsert(PLpgSQL_function *function, PLpgSQL_func_hashkey *func_key)
Definition: pl_comp.c:2603
#define lsecond(l)
Definition: pg_list.h:116
static void plpgsql_start_datums(void)
Definition: pl_comp.c:2318
#define RELKIND_COMPOSITE_TYPE
Definition: pg_class.h:166
#define PROARGMODE_INOUT
Definition: pg_proc.h:5569
#define SearchSysCache1(cacheId, key1)
Definition: syscache.h:159
#define PROARGMODE_OUT
Definition: pg_proc.h:5568
PostParseColumnRefHook p_post_columnref_hook
Definition: parse_node.h:211
signed int int32
Definition: c.h:246
PLpgSQL_datum ** datums
Definition: plpgsql.h:908
PLpgSQL_resolve_option resolve_option
Definition: plpgsql.h:857
int location
Definition: parsenodes.h:235
HeapTupleHeader t_data
Definition: htup.h:67
static HTAB * plpgsql_HashTable
Definition: pl_comp.c:63
ErrorContextCallback * error_context_stack
Definition: elog.c:88
static void delete_function(PLpgSQL_function *func)
Definition: pl_comp.c:2559
#define list_make1(x1)
Definition: pg_list.h:139
#define NAMEDATALEN
struct plpgsql_hashent plpgsql_HashEnt
void plpgsql_scanner_finish(void)
Definition: pl_scanner.c:729
FmgrInfo * flinfo
Definition: fmgr.h:79
Definition: dynahash.c:208
Bitmapset * paramnos
Definition: plpgsql.h:225
static PLpgSQL_function * plpgsql_HashTableLookup(PLpgSQL_func_hashkey *func_key)
Definition: pl_comp.c:2588
void pfree(void *pointer)
Definition: mcxt.c:949
#define linitial(l)
Definition: pg_list.h:111
#define VOIDOID
Definition: pg_type.h:690
#define TEXTARRAYOID
Definition: pg_type.h:470
PLpgSQL_function * plpgsql_compile(FunctionCallInfo fcinfo, bool forValidator)
Definition: pl_comp.c:137
bool plpgsql_check_syntax
Definition: pl_comp.c:52
#define ObjectIdGetDatum(X)
Definition: postgres.h:513
#define ERROR
Definition: elog.h:43
char * plpgsql_error_funcname
Definition: pl_comp.c:50
#define IsPolymorphicType(typid)
Definition: pg_type.h:745
char ** fieldnames
Definition: plpgsql.h:293
struct PLpgSQL_execstate * cur_estate
Definition: plpgsql.h:874
Oid paramcollid
Definition: primnodes.h:248
struct PLpgSQL_func_hashkey PLpgSQL_func_hashkey
bool plpgsql_DumpExecTree
Definition: pl_comp.c:51
int location
Definition: primnodes.h:249
PLpgSQL_type * plpgsql_parse_cwordtype(List *idents)
Definition: pl_comp.c:1696
#define ANYRANGEOID
Definition: pg_type.h:714
unsigned long use_count
Definition: plpgsql.h:875
static void add_parameter_name(PLpgSQL_nsitem_type itemtype, int itemno, const char *name)
Definition: pl_comp.c:957
#define TRIGGEROID
Definition: pg_type.h:692
#define PROARGMODE_TABLE
Definition: pg_proc.h:5571
ItemPointerData t_self
Definition: htup.h:65
void TupleDescInitEntryCollation(TupleDesc desc, AttrNumber attributeNumber, Oid collationid)
Definition: tupdesc.c:664
int plpgsql_extra_warnings
Definition: pl_handler.c:54
List * idents
Definition: plpgsql.h:995
#define ALLOCSET_DEFAULT_SIZES
Definition: memutils.h:165
#define INT4RANGEOID
Definition: pg_type.h:648
struct PLpgSQL_nsitem * ns
Definition: plpgsql.h:232
void plpgsql_parser_setup(struct ParseState *pstate, PLpgSQL_expr *expr)
Definition: pl_comp.c:1023
#define NoLock
Definition: lockdefs.h:34
static void add_dummy_return(PLpgSQL_function *function)
Definition: pl_comp.c:982
ParseParamRefHook p_paramref_hook
Definition: parse_node.h:212
static char * buf
Definition: pg_test_fsync.c:67
#define ANYENUMOID
Definition: pg_type.h:706
int errdetail(const char *fmt,...)
Definition: elog.c:873
static Node * plpgsql_param_ref(ParseState *pstate, ParamRef *pref)
Definition: pl_comp.c:1094
static int datums_alloc
Definition: pl_comp.c:45
#define RelationGetRelationName(relation)
Definition: rel.h:436
FormData_pg_attribute * Form_pg_attribute
Definition: pg_attribute.h:187
#define RECORDOID
Definition: pg_type.h:680
#define RELKIND_FOREIGN_TABLE
Definition: pg_class.h:167
MemoryContext CurrentMemoryContext
Definition: mcxt.c:37
MemoryContext fn_cxt
Definition: plpgsql.h:827
void plpgsql_ns_init(void)
Definition: pl_funcs.c:45
PLpgSQL_function * function
Definition: pl_comp.c:68
List * idents
Definition: plpgsql.h:1003
void TupleDescInitEntry(TupleDesc desc, AttrNumber attributeNumber, const char *attributeName, Oid oidtypeid, int32 typmod, int attdim)
Definition: tupdesc.c:505
#define ereport(elevel, rest)
Definition: elog.h:122
#define PROARGMODE_IN
Definition: pg_proc.h:5567
bool freeval
Definition: plpgsql.h:271
bool plpgsql_parse_word(char *word1, const char *yytxt, PLwdatum *wdatum, PLword *word)
Definition: pl_comp.c:1360
MemoryContext TopMemoryContext
Definition: mcxt.c:43
Oid typrelid
Definition: plpgsql.h:184
int * varnos
Definition: plpgsql.h:294
void plpgsql_exec_get_datum_type_info(PLpgSQL_execstate *estate, PLpgSQL_datum *datum, Oid *typeid, int32 *typmod, Oid *collation)
Definition: pl_exec.c:5026
#define PROVOLATILE_VOLATILE
Definition: pg_proc.h:5551
Oid fn_input_collation
Definition: plpgsql.h:825
List * lappend(List *list, void *datum)
Definition: list.c:128
bool typbyval
Definition: plpgsql.h:182
#define TYPTYPE_RANGE
Definition: pg_type.h:725
#define WARNING
Definition: elog.h:40
Oid collation
Definition: plpgsql.h:185
char * NameListToString(List *names)
Definition: namespace.c:3063
#define HASH_BLOBS
Definition: hsearch.h:88
#define RELKIND_PARTITIONED_TABLE
Definition: pg_class.h:168
#define TextDatumGetCString(d)
Definition: builtins.h:92
#define ANYARRAYOID
Definition: pg_type.h:688
bool typisarray
Definition: plpgsql.h:186
MemoryContext AllocSetContextCreate(MemoryContext parent, const char *name, Size minContextSize, Size initBlockSize, Size maxBlockSize)
Definition: aset.c:322
void * palloc0(Size size)
Definition: mcxt.c:877
static void plpgsql_HashTableDelete(PLpgSQL_function *function)
Definition: pl_comp.c:2622
HTAB * hash_create(const char *tabname, long nelem, HASHCTL *info, int flags)
Definition: dynahash.c:316
uintptr_t Datum
Definition: postgres.h:372
IdentifierLookup plpgsql_IdentifierLookup
Definition: pl_scanner.c:29
Oid get_fn_expr_rettype(FmgrInfo *flinfo)
Definition: fmgr.c:1887
void ReleaseSysCache(HeapTuple tuple)
Definition: syscache.c:1117
bool quoted
Definition: plpgsql.h:990
Datum SysCacheGetAttr(int cacheId, HeapTuple tup, AttrNumber attributeNumber, bool *isNull)
Definition: syscache.c:1325
static char * label
Definition: pg_basebackup.c:81
PLpgSQL_datum_type dtype
Definition: plpgsql.h:318
Oid get_rel_type_id(Oid relid)
Definition: lsyscache.c:1777
int number
Definition: parsenodes.h:244
Size keysize
Definition: hsearch.h:72
Trigger * tg_trigger
Definition: trigger.h:37
FormData_pg_proc * Form_pg_proc
Definition: pg_proc.h:83
void * MemoryContextAllocZero(MemoryContext context, Size size)
Definition: mcxt.c:741
Datum value
Definition: plpgsql.h:269
#define InvalidOid
Definition: postgres_ext.h:36
struct PLpgSQL_function * func
Definition: plpgsql.h:229
TypeName * makeTypeName(char *typnam)
Definition: makefuncs.c:441
Oid fn_oid
Definition: fmgr.h:59
bool plpgsql_print_strict_params
Definition: pl_handler.c:48
char * format_procedure(Oid procedure_oid)
Definition: regproc.c:323
int32 paramtypmod
Definition: primnodes.h:247
static void plpgsql_compile_error_callback(void *arg)
Definition: pl_comp.c:930
int location
Definition: parsenodes.h:245
int plpgsql_variable_conflict
Definition: pl_handler.c:46
#define makeNode(_type_)
Definition: nodes.h:557
#define HeapTupleIsValid(tuple)
Definition: htup.h:77
#define EVTTRIGGEROID
Definition: pg_type.h:694
#define CALLED_AS_TRIGGER(fcinfo)
Definition: trigger.h:25
PLpgSQL_type * plpgsql_parse_cwordrowtype(List *idents)
Definition: pl_comp.c:1835
#define Assert(condition)
Definition: c.h:664
int nfields
Definition: plpgsql.h:292
int lineno
Definition: plpgsql.h:259
void * p_ref_hook_state
Definition: parse_node.h:214
fmNodePtr fn_expr
Definition: fmgr.h:66
int paramid
Definition: primnodes.h:245
static Node * resolve_column_ref(ParseState *pstate, PLpgSQL_expr *expr, ColumnRef *cref, bool error_if_no_field)
Definition: pl_comp.c:1121
bool function_parse_error_transpose(const char *prosrc)
Definition: pg_proc.c:984
PLpgSQL_datum * datum
Definition: plpgsql.h:1000
void plpgsql_ns_push(const char *label, PLpgSQL_label_type label_type)
Definition: pl_funcs.c:56
static int list_length(const List *l)
Definition: pg_list.h:89
int parser_errposition(ParseState *pstate, int location)
Definition: parse_node.c:111
char * typname
Definition: plpgsql.h:178
PLpgSQL_stmt_block * plpgsql_parse_result
Definition: pl_comp.c:43
PLpgSQL_variable * plpgsql_build_variable(const char *refname, int lineno, PLpgSQL_type *dtype, bool add2namespace)
Definition: pl_comp.c:1869
static const ExceptionLabelMap exception_label_map[]
Definition: pl_comp.c:83
char * refname
Definition: plpgsql.h:212
#define HeapTupleHeaderGetRawXmin(tup)
Definition: htup_details.h:302
bool freetupdesc
Definition: plpgsql.h:310
HeapTuple SearchSysCacheAttName(Oid relid, const char *attname)
Definition: syscache.c:1205
PLpgSQL_datum_type dtype
Definition: plpgsql.h:210
void * fn_extra
Definition: fmgr.h:64
Bitmapset * bms_add_member(Bitmapset *a, int x)
Definition: bitmapset.c:698
#define BOOLOID
Definition: pg_type.h:288
TupleDesc CreateTemplateTupleDesc(int natts, bool hasoid)
Definition: tupdesc.c:43
bool ItemPointerEquals(ItemPointer pointer1, ItemPointer pointer2)
Definition: itemptr.c:29
void * repalloc(void *pointer, Size size)
Definition: mcxt.c:962
const char * name
Definition: encode.c:521
on_exit_nicely_callback function
#define TYPTYPE_PSEUDO
Definition: pg_type.h:724
static void word(struct vars *, int, struct state *, struct state *)
Definition: regcomp.c:1243
char typtype
Definition: plpgsql.h:183
int plpgsql_add_initdatums(int **varnos)
Definition: pl_comp.c:2396
void plpgsql_scanner_init(const char *str)
Definition: pl_scanner.c:702
FormData_pg_class * Form_pg_class
Definition: pg_class.h:95
Oid get_base_element_type(Oid typid)
Definition: lsyscache.c:2557
void(* callback)(void *arg)
Definition: elog.h:239
bool quoted
Definition: plpgsql.h:1002
static PLpgSQL_type * build_datatype(HeapTuple typeTup, int32 typmod, Oid collation)
Definition: pl_comp.c:2152
char * ident
Definition: plpgsql.h:1001
void * palloc(Size size)
Definition: mcxt.c:848
int errmsg(const char *fmt,...)
Definition: elog.c:797
static void plpgsql_finish_datums(PLpgSQL_function *function)
Definition: pl_comp.c:2355
int32 atttypmod
Definition: plpgsql.h:187
void * MemoryContextAlloc(MemoryContext context, Size size)
Definition: mcxt.c:706
HeapTuple tup
Definition: plpgsql.h:307
#define RELKIND_VIEW
Definition: pg_class.h:164
PLpgSQL_nsitem_type itemtype
Definition: plpgsql.h:351
bool plpgsql_parse_tripword(char *word1, char *word2, char *word3, PLwdatum *wdatum, PLcword *cword)
Definition: pl_comp.c:1536
void plpgsql_adddatum(PLpgSQL_datum *new)
Definition: pl_comp.c:2335
int i
TupleDesc rowtupdesc
Definition: plpgsql.h:285
MemoryContext plpgsql_compile_tmp_cxt
Definition: pl_comp.c:57
#define errcontext
Definition: elog.h:164
#define NameStr(name)
Definition: c.h:493
#define TYPTYPE_ENUM
Definition: pg_type.h:723
void * arg
static int datums_last
Definition: pl_comp.c:48
Relation relation_open(Oid relationId, LOCKMODE lockmode)
Definition: heapam.c:1120
#define lthird(l)
Definition: pg_list.h:121
#define elog
Definition: elog.h:219
PreParseColumnRefHook p_pre_columnref_hook
Definition: parse_node.h:210
int16 typlen
Definition: plpgsql.h:181
#define HeapTupleGetOid(tuple)
Definition: htup_details.h:695
#define INT4ARRAYOID
Definition: pg_type.h:467
PLpgSQL_condition * plpgsql_parse_err_condition(char *condname)
Definition: pl_comp.c:2267
static PLpgSQL_row * build_row_from_vars(PLpgSQL_variable **vars, int numvars)
Definition: pl_comp.c:2068
#define RELKIND_RELATION
Definition: pg_class.h:160
Definition: regcomp.c:224
#define RELKIND_SEQUENCE
Definition: pg_class.h:162
Definition: pg_list.h:45
static Node * plpgsql_post_column_ref(ParseState *pstate, ColumnRef *cref, Node *var)
Definition: pl_comp.c:1050
char * fieldname
Definition: plpgsql.h:320
int lineno
Definition: plpgsql.h:305
Oid paramtype
Definition: primnodes.h:246
RangeVar * makeRangeVar(char *schemaname, char *relname, int location)
Definition: makefuncs.c:419
PLpgSQL_datum_type dtype
Definition: plpgsql.h:279
List * fields
Definition: parsenodes.h:234
PLpgSQL_function * plpgsql_curr_compile
Definition: pl_comp.c:54
PLpgSQL_nsitem_type
Definition: plpgsql.h:38
static Node * make_datum_param(PLpgSQL_expr *expr, int dno, int location)
Definition: pl_comp.c:1310
int lineno
Definition: plpgsql.h:282
bool isnull
Definition: plpgsql.h:270
Oid typoid
Definition: plpgsql.h:179