]> granicus.if.org Git - postgresql/blob - src/backend/utils/fmgr/fmgr.c
Add use of asprintf()
[postgresql] / src / backend / utils / fmgr / fmgr.c
1 /*-------------------------------------------------------------------------
2  *
3  * fmgr.c
4  *        The Postgres function manager.
5  *
6  * Portions Copyright (c) 1996-2013, PostgreSQL Global Development Group
7  * Portions Copyright (c) 1994, Regents of the University of California
8  *
9  *
10  * IDENTIFICATION
11  *        src/backend/utils/fmgr/fmgr.c
12  *
13  *-------------------------------------------------------------------------
14  */
15
16 #include "postgres.h"
17
18 #include "access/tuptoaster.h"
19 #include "catalog/pg_language.h"
20 #include "catalog/pg_proc.h"
21 #include "executor/functions.h"
22 #include "executor/spi.h"
23 #include "lib/stringinfo.h"
24 #include "miscadmin.h"
25 #include "nodes/nodeFuncs.h"
26 #include "pgstat.h"
27 #include "utils/builtins.h"
28 #include "utils/fmgrtab.h"
29 #include "utils/guc.h"
30 #include "utils/lsyscache.h"
31 #include "utils/syscache.h"
32
33 /*
34  * Hooks for function calls
35  */
36 PGDLLIMPORT needs_fmgr_hook_type needs_fmgr_hook = NULL;
37 PGDLLIMPORT fmgr_hook_type fmgr_hook = NULL;
38
39 /*
40  * Declaration for old-style function pointer type.  This is now used only
41  * in fmgr_oldstyle() and is no longer exported.
42  *
43  * The m68k SVR4 ABI defines that pointers are returned in %a0 instead of
44  * %d0. So if a function pointer is declared to return a pointer, the
45  * compiler may look only into %a0, but if the called function was declared
46  * to return an integer type, it puts its value only into %d0. So the
47  * caller doesn't pick up the correct return value. The solution is to
48  * declare the function pointer to return int, so the compiler picks up the
49  * return value from %d0. (Functions returning pointers put their value
50  * *additionally* into %d0 for compatibility.) The price is that there are
51  * some warnings about int->pointer conversions ... which we can suppress
52  * with suitably ugly casts in fmgr_oldstyle().
53  */
54 #if (defined(__mc68000__) || (defined(__m68k__))) && defined(__ELF__)
55 typedef int32 (*func_ptr) ();
56 #else
57 typedef char *(*func_ptr) ();
58 #endif
59
60 /*
61  * For an oldstyle function, fn_extra points to a record like this:
62  */
63 typedef struct
64 {
65         func_ptr        func;                   /* Address of the oldstyle function */
66         bool            arg_toastable[FUNC_MAX_ARGS];   /* is n'th arg of a toastable
67                                                                                                  * datatype? */
68 } Oldstyle_fnextra;
69
70 /*
71  * Hashtable for fast lookup of external C functions
72  */
73 typedef struct
74 {
75         /* fn_oid is the hash key and so must be first! */
76         Oid                     fn_oid;                 /* OID of an external C function */
77         TransactionId fn_xmin;          /* for checking up-to-dateness */
78         ItemPointerData fn_tid;
79         PGFunction      user_fn;                /* the function's address */
80         const Pg_finfo_record *inforec;         /* address of its info record */
81 } CFuncHashTabEntry;
82
83 static HTAB *CFuncHash = NULL;
84
85
86 static void fmgr_info_cxt_security(Oid functionId, FmgrInfo *finfo, MemoryContext mcxt,
87                                            bool ignore_security);
88 static void fmgr_info_C_lang(Oid functionId, FmgrInfo *finfo, HeapTuple procedureTuple);
89 static void fmgr_info_other_lang(Oid functionId, FmgrInfo *finfo, HeapTuple procedureTuple);
90 static CFuncHashTabEntry *lookup_C_func(HeapTuple procedureTuple);
91 static void record_C_func(HeapTuple procedureTuple,
92                           PGFunction user_fn, const Pg_finfo_record *inforec);
93 static Datum fmgr_oldstyle(PG_FUNCTION_ARGS);
94 static Datum fmgr_security_definer(PG_FUNCTION_ARGS);
95
96
97 /*
98  * Lookup routines for builtin-function table.  We can search by either Oid
99  * or name, but search by Oid is much faster.
100  */
101
102 static const FmgrBuiltin *
103 fmgr_isbuiltin(Oid id)
104 {
105         int                     low = 0;
106         int                     high = fmgr_nbuiltins - 1;
107
108         /*
109          * Loop invariant: low is the first index that could contain target entry,
110          * and high is the last index that could contain it.
111          */
112         while (low <= high)
113         {
114                 int                     i = (high + low) / 2;
115                 const FmgrBuiltin *ptr = &fmgr_builtins[i];
116
117                 if (id == ptr->foid)
118                         return ptr;
119                 else if (id > ptr->foid)
120                         low = i + 1;
121                 else
122                         high = i - 1;
123         }
124         return NULL;
125 }
126
127 /*
128  * Lookup a builtin by name.  Note there can be more than one entry in
129  * the array with the same name, but they should all point to the same
130  * routine.
131  */
132 static const FmgrBuiltin *
133 fmgr_lookupByName(const char *name)
134 {
135         int                     i;
136
137         for (i = 0; i < fmgr_nbuiltins; i++)
138         {
139                 if (strcmp(name, fmgr_builtins[i].funcName) == 0)
140                         return fmgr_builtins + i;
141         }
142         return NULL;
143 }
144
145 /*
146  * This routine fills a FmgrInfo struct, given the OID
147  * of the function to be called.
148  *
149  * The caller's CurrentMemoryContext is used as the fn_mcxt of the info
150  * struct; this means that any subsidiary data attached to the info struct
151  * (either by fmgr_info itself, or later on by a function call handler)
152  * will be allocated in that context.  The caller must ensure that this
153  * context is at least as long-lived as the info struct itself.  This is
154  * not a problem in typical cases where the info struct is on the stack or
155  * in freshly-palloc'd space.  However, if one intends to store an info
156  * struct in a long-lived table, it's better to use fmgr_info_cxt.
157  */
158 void
159 fmgr_info(Oid functionId, FmgrInfo *finfo)
160 {
161         fmgr_info_cxt_security(functionId, finfo, CurrentMemoryContext, false);
162 }
163
164 /*
165  * Fill a FmgrInfo struct, specifying a memory context in which its
166  * subsidiary data should go.
167  */
168 void
169 fmgr_info_cxt(Oid functionId, FmgrInfo *finfo, MemoryContext mcxt)
170 {
171         fmgr_info_cxt_security(functionId, finfo, mcxt, false);
172 }
173
174 /*
175  * This one does the actual work.  ignore_security is ordinarily false
176  * but is set to true when we need to avoid recursion.
177  */
178 static void
179 fmgr_info_cxt_security(Oid functionId, FmgrInfo *finfo, MemoryContext mcxt,
180                                            bool ignore_security)
181 {
182         const FmgrBuiltin *fbp;
183         HeapTuple       procedureTuple;
184         Form_pg_proc procedureStruct;
185         Datum           prosrcdatum;
186         bool            isnull;
187         char       *prosrc;
188
189         /*
190          * fn_oid *must* be filled in last.  Some code assumes that if fn_oid is
191          * valid, the whole struct is valid.  Some FmgrInfo struct's do survive
192          * elogs.
193          */
194         finfo->fn_oid = InvalidOid;
195         finfo->fn_extra = NULL;
196         finfo->fn_mcxt = mcxt;
197         finfo->fn_expr = NULL;          /* caller may set this later */
198
199         if ((fbp = fmgr_isbuiltin(functionId)) != NULL)
200         {
201                 /*
202                  * Fast path for builtin functions: don't bother consulting pg_proc
203                  */
204                 finfo->fn_nargs = fbp->nargs;
205                 finfo->fn_strict = fbp->strict;
206                 finfo->fn_retset = fbp->retset;
207                 finfo->fn_stats = TRACK_FUNC_ALL;               /* ie, never track */
208                 finfo->fn_addr = fbp->func;
209                 finfo->fn_oid = functionId;
210                 return;
211         }
212
213         /* Otherwise we need the pg_proc entry */
214         procedureTuple = SearchSysCache1(PROCOID, ObjectIdGetDatum(functionId));
215         if (!HeapTupleIsValid(procedureTuple))
216                 elog(ERROR, "cache lookup failed for function %u", functionId);
217         procedureStruct = (Form_pg_proc) GETSTRUCT(procedureTuple);
218
219         finfo->fn_nargs = procedureStruct->pronargs;
220         finfo->fn_strict = procedureStruct->proisstrict;
221         finfo->fn_retset = procedureStruct->proretset;
222
223         /*
224          * If it has prosecdef set, non-null proconfig, or if a plugin wants to
225          * hook function entry/exit, use fmgr_security_definer call handler ---
226          * unless we are being called again by fmgr_security_definer or
227          * fmgr_info_other_lang.
228          *
229          * When using fmgr_security_definer, function stats tracking is always
230          * disabled at the outer level, and instead we set the flag properly in
231          * fmgr_security_definer's private flinfo and implement the tracking
232          * inside fmgr_security_definer.  This loses the ability to charge the
233          * overhead of fmgr_security_definer to the function, but gains the
234          * ability to set the track_functions GUC as a local GUC parameter of an
235          * interesting function and have the right things happen.
236          */
237         if (!ignore_security &&
238                 (procedureStruct->prosecdef ||
239                  !heap_attisnull(procedureTuple, Anum_pg_proc_proconfig) ||
240                  FmgrHookIsNeeded(functionId)))
241         {
242                 finfo->fn_addr = fmgr_security_definer;
243                 finfo->fn_stats = TRACK_FUNC_ALL;               /* ie, never track */
244                 finfo->fn_oid = functionId;
245                 ReleaseSysCache(procedureTuple);
246                 return;
247         }
248
249         switch (procedureStruct->prolang)
250         {
251                 case INTERNALlanguageId:
252
253                         /*
254                          * For an ordinary builtin function, we should never get here
255                          * because the isbuiltin() search above will have succeeded.
256                          * However, if the user has done a CREATE FUNCTION to create an
257                          * alias for a builtin function, we can end up here.  In that case
258                          * we have to look up the function by name.  The name of the
259                          * internal function is stored in prosrc (it doesn't have to be
260                          * the same as the name of the alias!)
261                          */
262                         prosrcdatum = SysCacheGetAttr(PROCOID, procedureTuple,
263                                                                                   Anum_pg_proc_prosrc, &isnull);
264                         if (isnull)
265                                 elog(ERROR, "null prosrc");
266                         prosrc = TextDatumGetCString(prosrcdatum);
267                         fbp = fmgr_lookupByName(prosrc);
268                         if (fbp == NULL)
269                                 ereport(ERROR,
270                                                 (errcode(ERRCODE_UNDEFINED_FUNCTION),
271                                                  errmsg("internal function \"%s\" is not in internal lookup table",
272                                                                 prosrc)));
273                         pfree(prosrc);
274                         /* Should we check that nargs, strict, retset match the table? */
275                         finfo->fn_addr = fbp->func;
276                         /* note this policy is also assumed in fast path above */
277                         finfo->fn_stats = TRACK_FUNC_ALL;       /* ie, never track */
278                         break;
279
280                 case ClanguageId:
281                         fmgr_info_C_lang(functionId, finfo, procedureTuple);
282                         finfo->fn_stats = TRACK_FUNC_PL;        /* ie, track if ALL */
283                         break;
284
285                 case SQLlanguageId:
286                         finfo->fn_addr = fmgr_sql;
287                         finfo->fn_stats = TRACK_FUNC_PL;        /* ie, track if ALL */
288                         break;
289
290                 default:
291                         fmgr_info_other_lang(functionId, finfo, procedureTuple);
292                         finfo->fn_stats = TRACK_FUNC_OFF;       /* ie, track if not OFF */
293                         break;
294         }
295
296         finfo->fn_oid = functionId;
297         ReleaseSysCache(procedureTuple);
298 }
299
300 /*
301  * Special fmgr_info processing for C-language functions.  Note that
302  * finfo->fn_oid is not valid yet.
303  */
304 static void
305 fmgr_info_C_lang(Oid functionId, FmgrInfo *finfo, HeapTuple procedureTuple)
306 {
307         Form_pg_proc procedureStruct = (Form_pg_proc) GETSTRUCT(procedureTuple);
308         CFuncHashTabEntry *hashentry;
309         PGFunction      user_fn;
310         const Pg_finfo_record *inforec;
311         Oldstyle_fnextra *fnextra;
312         bool            isnull;
313         int                     i;
314
315         /*
316          * See if we have the function address cached already
317          */
318         hashentry = lookup_C_func(procedureTuple);
319         if (hashentry)
320         {
321                 user_fn = hashentry->user_fn;
322                 inforec = hashentry->inforec;
323         }
324         else
325         {
326                 Datum           prosrcattr,
327                                         probinattr;
328                 char       *prosrcstring,
329                                    *probinstring;
330                 void       *libraryhandle;
331
332                 /*
333                  * Get prosrc and probin strings (link symbol and library filename).
334                  * While in general these columns might be null, that's not allowed
335                  * for C-language functions.
336                  */
337                 prosrcattr = SysCacheGetAttr(PROCOID, procedureTuple,
338                                                                          Anum_pg_proc_prosrc, &isnull);
339                 if (isnull)
340                         elog(ERROR, "null prosrc for C function %u", functionId);
341                 prosrcstring = TextDatumGetCString(prosrcattr);
342
343                 probinattr = SysCacheGetAttr(PROCOID, procedureTuple,
344                                                                          Anum_pg_proc_probin, &isnull);
345                 if (isnull)
346                         elog(ERROR, "null probin for C function %u", functionId);
347                 probinstring = TextDatumGetCString(probinattr);
348
349                 /* Look up the function itself */
350                 user_fn = load_external_function(probinstring, prosrcstring, true,
351                                                                                  &libraryhandle);
352
353                 /* Get the function information record (real or default) */
354                 inforec = fetch_finfo_record(libraryhandle, prosrcstring);
355
356                 /* Cache the addresses for later calls */
357                 record_C_func(procedureTuple, user_fn, inforec);
358
359                 pfree(prosrcstring);
360                 pfree(probinstring);
361         }
362
363         switch (inforec->api_version)
364         {
365                 case 0:
366                         /* Old style: need to use a handler */
367                         finfo->fn_addr = fmgr_oldstyle;
368                         fnextra = (Oldstyle_fnextra *)
369                                 MemoryContextAllocZero(finfo->fn_mcxt,
370                                                                            sizeof(Oldstyle_fnextra));
371                         finfo->fn_extra = (void *) fnextra;
372                         fnextra->func = (func_ptr) user_fn;
373                         for (i = 0; i < procedureStruct->pronargs; i++)
374                         {
375                                 fnextra->arg_toastable[i] =
376                                         TypeIsToastable(procedureStruct->proargtypes.values[i]);
377                         }
378                         break;
379                 case 1:
380                         /* New style: call directly */
381                         finfo->fn_addr = user_fn;
382                         break;
383                 default:
384                         /* Shouldn't get here if fetch_finfo_record did its job */
385                         elog(ERROR, "unrecognized function API version: %d",
386                                  inforec->api_version);
387                         break;
388         }
389 }
390
391 /*
392  * Special fmgr_info processing for other-language functions.  Note
393  * that finfo->fn_oid is not valid yet.
394  */
395 static void
396 fmgr_info_other_lang(Oid functionId, FmgrInfo *finfo, HeapTuple procedureTuple)
397 {
398         Form_pg_proc procedureStruct = (Form_pg_proc) GETSTRUCT(procedureTuple);
399         Oid                     language = procedureStruct->prolang;
400         HeapTuple       languageTuple;
401         Form_pg_language languageStruct;
402         FmgrInfo        plfinfo;
403
404         languageTuple = SearchSysCache1(LANGOID, ObjectIdGetDatum(language));
405         if (!HeapTupleIsValid(languageTuple))
406                 elog(ERROR, "cache lookup failed for language %u", language);
407         languageStruct = (Form_pg_language) GETSTRUCT(languageTuple);
408
409         /*
410          * Look up the language's call handler function, ignoring any attributes
411          * that would normally cause insertion of fmgr_security_definer.  We need
412          * to get back a bare pointer to the actual C-language function.
413          */
414         fmgr_info_cxt_security(languageStruct->lanplcallfoid, &plfinfo,
415                                                    CurrentMemoryContext, true);
416         finfo->fn_addr = plfinfo.fn_addr;
417
418         /*
419          * If lookup of the PL handler function produced nonnull fn_extra,
420          * complain --- it must be an oldstyle function! We no longer support
421          * oldstyle PL handlers.
422          */
423         if (plfinfo.fn_extra != NULL)
424                 elog(ERROR, "language %u has old-style handler", language);
425
426         ReleaseSysCache(languageTuple);
427 }
428
429 /*
430  * Fetch and validate the information record for the given external function.
431  * The function is specified by a handle for the containing library
432  * (obtained from load_external_function) as well as the function name.
433  *
434  * If no info function exists for the given name, it is not an error.
435  * Instead we return a default info record for a version-0 function.
436  * We want to raise an error here only if the info function returns
437  * something bogus.
438  *
439  * This function is broken out of fmgr_info_C_lang so that fmgr_c_validator
440  * can validate the information record for a function not yet entered into
441  * pg_proc.
442  */
443 const Pg_finfo_record *
444 fetch_finfo_record(void *filehandle, char *funcname)
445 {
446         char       *infofuncname;
447         PGFInfoFunction infofunc;
448         const Pg_finfo_record *inforec;
449         static Pg_finfo_record default_inforec = {0};
450
451         infofuncname = psprintf("pg_finfo_%s", funcname);
452
453         /* Try to look up the info function */
454         infofunc = (PGFInfoFunction) lookup_external_function(filehandle,
455                                                                                                                   infofuncname);
456         if (infofunc == NULL)
457         {
458                 /* Not found --- assume version 0 */
459                 pfree(infofuncname);
460                 return &default_inforec;
461         }
462
463         /* Found, so call it */
464         inforec = (*infofunc) ();
465
466         /* Validate result as best we can */
467         if (inforec == NULL)
468                 elog(ERROR, "null result from info function \"%s\"", infofuncname);
469         switch (inforec->api_version)
470         {
471                 case 0:
472                 case 1:
473                         /* OK, no additional fields to validate */
474                         break;
475                 default:
476                         ereport(ERROR,
477                                         (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
478                                          errmsg("unrecognized API version %d reported by info function \"%s\"",
479                                                         inforec->api_version, infofuncname)));
480                         break;
481         }
482
483         pfree(infofuncname);
484         return inforec;
485 }
486
487
488 /*-------------------------------------------------------------------------
489  *              Routines for caching lookup information for external C functions.
490  *
491  * The routines in dfmgr.c are relatively slow, so we try to avoid running
492  * them more than once per external function per session.  We use a hash table
493  * with the function OID as the lookup key.
494  *-------------------------------------------------------------------------
495  */
496
497 /*
498  * lookup_C_func: try to find a C function in the hash table
499  *
500  * If an entry exists and is up to date, return it; else return NULL
501  */
502 static CFuncHashTabEntry *
503 lookup_C_func(HeapTuple procedureTuple)
504 {
505         Oid                     fn_oid = HeapTupleGetOid(procedureTuple);
506         CFuncHashTabEntry *entry;
507
508         if (CFuncHash == NULL)
509                 return NULL;                    /* no table yet */
510         entry = (CFuncHashTabEntry *)
511                 hash_search(CFuncHash,
512                                         &fn_oid,
513                                         HASH_FIND,
514                                         NULL);
515         if (entry == NULL)
516                 return NULL;                    /* no such entry */
517         if (entry->fn_xmin == HeapTupleHeaderGetXmin(procedureTuple->t_data) &&
518                 ItemPointerEquals(&entry->fn_tid, &procedureTuple->t_self))
519                 return entry;                   /* OK */
520         return NULL;                            /* entry is out of date */
521 }
522
523 /*
524  * record_C_func: enter (or update) info about a C function in the hash table
525  */
526 static void
527 record_C_func(HeapTuple procedureTuple,
528                           PGFunction user_fn, const Pg_finfo_record *inforec)
529 {
530         Oid                     fn_oid = HeapTupleGetOid(procedureTuple);
531         CFuncHashTabEntry *entry;
532         bool            found;
533
534         /* Create the hash table if it doesn't exist yet */
535         if (CFuncHash == NULL)
536         {
537                 HASHCTL         hash_ctl;
538
539                 MemSet(&hash_ctl, 0, sizeof(hash_ctl));
540                 hash_ctl.keysize = sizeof(Oid);
541                 hash_ctl.entrysize = sizeof(CFuncHashTabEntry);
542                 hash_ctl.hash = oid_hash;
543                 CFuncHash = hash_create("CFuncHash",
544                                                                 100,
545                                                                 &hash_ctl,
546                                                                 HASH_ELEM | HASH_FUNCTION);
547         }
548
549         entry = (CFuncHashTabEntry *)
550                 hash_search(CFuncHash,
551                                         &fn_oid,
552                                         HASH_ENTER,
553                                         &found);
554         /* OID is already filled in */
555         entry->fn_xmin = HeapTupleHeaderGetXmin(procedureTuple->t_data);
556         entry->fn_tid = procedureTuple->t_self;
557         entry->user_fn = user_fn;
558         entry->inforec = inforec;
559 }
560
561 /*
562  * clear_external_function_hash: remove entries for a library being closed
563  *
564  * Presently we just zap the entire hash table, but later it might be worth
565  * the effort to remove only the entries associated with the given handle.
566  */
567 void
568 clear_external_function_hash(void *filehandle)
569 {
570         if (CFuncHash)
571                 hash_destroy(CFuncHash);
572         CFuncHash = NULL;
573 }
574
575
576 /*
577  * Copy an FmgrInfo struct
578  *
579  * This is inherently somewhat bogus since we can't reliably duplicate
580  * language-dependent subsidiary info.  We cheat by zeroing fn_extra,
581  * instead, meaning that subsidiary info will have to be recomputed.
582  */
583 void
584 fmgr_info_copy(FmgrInfo *dstinfo, FmgrInfo *srcinfo,
585                            MemoryContext destcxt)
586 {
587         memcpy(dstinfo, srcinfo, sizeof(FmgrInfo));
588         dstinfo->fn_mcxt = destcxt;
589         if (dstinfo->fn_addr == fmgr_oldstyle)
590         {
591                 /* For oldstyle functions we must copy fn_extra */
592                 Oldstyle_fnextra *fnextra;
593
594                 fnextra = (Oldstyle_fnextra *)
595                         MemoryContextAlloc(destcxt, sizeof(Oldstyle_fnextra));
596                 memcpy(fnextra, srcinfo->fn_extra, sizeof(Oldstyle_fnextra));
597                 dstinfo->fn_extra = (void *) fnextra;
598         }
599         else
600                 dstinfo->fn_extra = NULL;
601 }
602
603
604 /*
605  * Specialized lookup routine for fmgr_internal_validator: given the alleged
606  * name of an internal function, return the OID of the function.
607  * If the name is not recognized, return InvalidOid.
608  */
609 Oid
610 fmgr_internal_function(const char *proname)
611 {
612         const FmgrBuiltin *fbp = fmgr_lookupByName(proname);
613
614         if (fbp == NULL)
615                 return InvalidOid;
616         return fbp->foid;
617 }
618
619
620 /*
621  * Handler for old-style "C" language functions
622  */
623 static Datum
624 fmgr_oldstyle(PG_FUNCTION_ARGS)
625 {
626         Oldstyle_fnextra *fnextra;
627         int                     n_arguments = fcinfo->nargs;
628         int                     i;
629         bool            isnull;
630         func_ptr        user_fn;
631         char       *returnValue;
632
633         if (fcinfo->flinfo == NULL || fcinfo->flinfo->fn_extra == NULL)
634                 elog(ERROR, "fmgr_oldstyle received NULL pointer");
635         fnextra = (Oldstyle_fnextra *) fcinfo->flinfo->fn_extra;
636
637         /*
638          * Result is NULL if any argument is NULL, but we still call the function
639          * (peculiar, but that's the way it worked before, and after all this is a
640          * backwards-compatibility wrapper).  Note, however, that we'll never get
641          * here with NULL arguments if the function is marked strict.
642          *
643          * We also need to detoast any TOAST-ed inputs, since it's unlikely that
644          * an old-style function knows about TOASTing.
645          */
646         isnull = false;
647         for (i = 0; i < n_arguments; i++)
648         {
649                 if (PG_ARGISNULL(i))
650                         isnull = true;
651                 else if (fnextra->arg_toastable[i])
652                         fcinfo->arg[i] = PointerGetDatum(PG_DETOAST_DATUM(fcinfo->arg[i]));
653         }
654         fcinfo->isnull = isnull;
655
656         user_fn = fnextra->func;
657
658         switch (n_arguments)
659         {
660                 case 0:
661                         returnValue = (char *) (*user_fn) ();
662                         break;
663                 case 1:
664
665                         /*
666                          * nullvalue() used to use isNull to check if arg is NULL; perhaps
667                          * there are other functions still out there that also rely on
668                          * this undocumented hack?
669                          */
670                         returnValue = (char *) (*user_fn) (fcinfo->arg[0],
671                                                                                            &fcinfo->isnull);
672                         break;
673                 case 2:
674                         returnValue = (char *) (*user_fn) (fcinfo->arg[0],
675                                                                                            fcinfo->arg[1]);
676                         break;
677                 case 3:
678                         returnValue = (char *) (*user_fn) (fcinfo->arg[0],
679                                                                                            fcinfo->arg[1],
680                                                                                            fcinfo->arg[2]);
681                         break;
682                 case 4:
683                         returnValue = (char *) (*user_fn) (fcinfo->arg[0],
684                                                                                            fcinfo->arg[1],
685                                                                                            fcinfo->arg[2],
686                                                                                            fcinfo->arg[3]);
687                         break;
688                 case 5:
689                         returnValue = (char *) (*user_fn) (fcinfo->arg[0],
690                                                                                            fcinfo->arg[1],
691                                                                                            fcinfo->arg[2],
692                                                                                            fcinfo->arg[3],
693                                                                                            fcinfo->arg[4]);
694                         break;
695                 case 6:
696                         returnValue = (char *) (*user_fn) (fcinfo->arg[0],
697                                                                                            fcinfo->arg[1],
698                                                                                            fcinfo->arg[2],
699                                                                                            fcinfo->arg[3],
700                                                                                            fcinfo->arg[4],
701                                                                                            fcinfo->arg[5]);
702                         break;
703                 case 7:
704                         returnValue = (char *) (*user_fn) (fcinfo->arg[0],
705                                                                                            fcinfo->arg[1],
706                                                                                            fcinfo->arg[2],
707                                                                                            fcinfo->arg[3],
708                                                                                            fcinfo->arg[4],
709                                                                                            fcinfo->arg[5],
710                                                                                            fcinfo->arg[6]);
711                         break;
712                 case 8:
713                         returnValue = (char *) (*user_fn) (fcinfo->arg[0],
714                                                                                            fcinfo->arg[1],
715                                                                                            fcinfo->arg[2],
716                                                                                            fcinfo->arg[3],
717                                                                                            fcinfo->arg[4],
718                                                                                            fcinfo->arg[5],
719                                                                                            fcinfo->arg[6],
720                                                                                            fcinfo->arg[7]);
721                         break;
722                 case 9:
723                         returnValue = (char *) (*user_fn) (fcinfo->arg[0],
724                                                                                            fcinfo->arg[1],
725                                                                                            fcinfo->arg[2],
726                                                                                            fcinfo->arg[3],
727                                                                                            fcinfo->arg[4],
728                                                                                            fcinfo->arg[5],
729                                                                                            fcinfo->arg[6],
730                                                                                            fcinfo->arg[7],
731                                                                                            fcinfo->arg[8]);
732                         break;
733                 case 10:
734                         returnValue = (char *) (*user_fn) (fcinfo->arg[0],
735                                                                                            fcinfo->arg[1],
736                                                                                            fcinfo->arg[2],
737                                                                                            fcinfo->arg[3],
738                                                                                            fcinfo->arg[4],
739                                                                                            fcinfo->arg[5],
740                                                                                            fcinfo->arg[6],
741                                                                                            fcinfo->arg[7],
742                                                                                            fcinfo->arg[8],
743                                                                                            fcinfo->arg[9]);
744                         break;
745                 case 11:
746                         returnValue = (char *) (*user_fn) (fcinfo->arg[0],
747                                                                                            fcinfo->arg[1],
748                                                                                            fcinfo->arg[2],
749                                                                                            fcinfo->arg[3],
750                                                                                            fcinfo->arg[4],
751                                                                                            fcinfo->arg[5],
752                                                                                            fcinfo->arg[6],
753                                                                                            fcinfo->arg[7],
754                                                                                            fcinfo->arg[8],
755                                                                                            fcinfo->arg[9],
756                                                                                            fcinfo->arg[10]);
757                         break;
758                 case 12:
759                         returnValue = (char *) (*user_fn) (fcinfo->arg[0],
760                                                                                            fcinfo->arg[1],
761                                                                                            fcinfo->arg[2],
762                                                                                            fcinfo->arg[3],
763                                                                                            fcinfo->arg[4],
764                                                                                            fcinfo->arg[5],
765                                                                                            fcinfo->arg[6],
766                                                                                            fcinfo->arg[7],
767                                                                                            fcinfo->arg[8],
768                                                                                            fcinfo->arg[9],
769                                                                                            fcinfo->arg[10],
770                                                                                            fcinfo->arg[11]);
771                         break;
772                 case 13:
773                         returnValue = (char *) (*user_fn) (fcinfo->arg[0],
774                                                                                            fcinfo->arg[1],
775                                                                                            fcinfo->arg[2],
776                                                                                            fcinfo->arg[3],
777                                                                                            fcinfo->arg[4],
778                                                                                            fcinfo->arg[5],
779                                                                                            fcinfo->arg[6],
780                                                                                            fcinfo->arg[7],
781                                                                                            fcinfo->arg[8],
782                                                                                            fcinfo->arg[9],
783                                                                                            fcinfo->arg[10],
784                                                                                            fcinfo->arg[11],
785                                                                                            fcinfo->arg[12]);
786                         break;
787                 case 14:
788                         returnValue = (char *) (*user_fn) (fcinfo->arg[0],
789                                                                                            fcinfo->arg[1],
790                                                                                            fcinfo->arg[2],
791                                                                                            fcinfo->arg[3],
792                                                                                            fcinfo->arg[4],
793                                                                                            fcinfo->arg[5],
794                                                                                            fcinfo->arg[6],
795                                                                                            fcinfo->arg[7],
796                                                                                            fcinfo->arg[8],
797                                                                                            fcinfo->arg[9],
798                                                                                            fcinfo->arg[10],
799                                                                                            fcinfo->arg[11],
800                                                                                            fcinfo->arg[12],
801                                                                                            fcinfo->arg[13]);
802                         break;
803                 case 15:
804                         returnValue = (char *) (*user_fn) (fcinfo->arg[0],
805                                                                                            fcinfo->arg[1],
806                                                                                            fcinfo->arg[2],
807                                                                                            fcinfo->arg[3],
808                                                                                            fcinfo->arg[4],
809                                                                                            fcinfo->arg[5],
810                                                                                            fcinfo->arg[6],
811                                                                                            fcinfo->arg[7],
812                                                                                            fcinfo->arg[8],
813                                                                                            fcinfo->arg[9],
814                                                                                            fcinfo->arg[10],
815                                                                                            fcinfo->arg[11],
816                                                                                            fcinfo->arg[12],
817                                                                                            fcinfo->arg[13],
818                                                                                            fcinfo->arg[14]);
819                         break;
820                 case 16:
821                         returnValue = (char *) (*user_fn) (fcinfo->arg[0],
822                                                                                            fcinfo->arg[1],
823                                                                                            fcinfo->arg[2],
824                                                                                            fcinfo->arg[3],
825                                                                                            fcinfo->arg[4],
826                                                                                            fcinfo->arg[5],
827                                                                                            fcinfo->arg[6],
828                                                                                            fcinfo->arg[7],
829                                                                                            fcinfo->arg[8],
830                                                                                            fcinfo->arg[9],
831                                                                                            fcinfo->arg[10],
832                                                                                            fcinfo->arg[11],
833                                                                                            fcinfo->arg[12],
834                                                                                            fcinfo->arg[13],
835                                                                                            fcinfo->arg[14],
836                                                                                            fcinfo->arg[15]);
837                         break;
838                 default:
839
840                         /*
841                          * Increasing FUNC_MAX_ARGS doesn't automatically add cases to the
842                          * above code, so mention the actual value in this error not
843                          * FUNC_MAX_ARGS.  You could add cases to the above if you needed
844                          * to support old-style functions with many arguments, but making
845                          * 'em be new-style is probably a better idea.
846                          */
847                         ereport(ERROR,
848                                         (errcode(ERRCODE_TOO_MANY_ARGUMENTS),
849                          errmsg("function %u has too many arguments (%d, maximum is %d)",
850                                         fcinfo->flinfo->fn_oid, n_arguments, 16)));
851                         returnValue = NULL; /* keep compiler quiet */
852                         break;
853         }
854
855         return PointerGetDatum(returnValue);
856 }
857
858
859 /*
860  * Support for security-definer and proconfig-using functions.  We support
861  * both of these features using the same call handler, because they are
862  * often used together and it would be inefficient (as well as notationally
863  * messy) to have two levels of call handler involved.
864  */
865 struct fmgr_security_definer_cache
866 {
867         FmgrInfo        flinfo;                 /* lookup info for target function */
868         Oid                     userid;                 /* userid to set, or InvalidOid */
869         ArrayType  *proconfig;          /* GUC values to set, or NULL */
870         Datum           arg;                    /* passthrough argument for plugin modules */
871 };
872
873 /*
874  * Function handler for security-definer/proconfig/plugin-hooked functions.
875  * We extract the OID of the actual function and do a fmgr lookup again.
876  * Then we fetch the pg_proc row and copy the owner ID and proconfig fields.
877  * (All this info is cached for the duration of the current query.)
878  * To execute a call, we temporarily replace the flinfo with the cached
879  * and looked-up one, while keeping the outer fcinfo (which contains all
880  * the actual arguments, etc.) intact.  This is not re-entrant, but then
881  * the fcinfo itself can't be used re-entrantly anyway.
882  */
883 static Datum
884 fmgr_security_definer(PG_FUNCTION_ARGS)
885 {
886         Datum           result;
887         struct fmgr_security_definer_cache *volatile fcache;
888         FmgrInfo   *save_flinfo;
889         Oid                     save_userid;
890         int                     save_sec_context;
891         volatile int save_nestlevel;
892         PgStat_FunctionCallUsage fcusage;
893
894         if (!fcinfo->flinfo->fn_extra)
895         {
896                 HeapTuple       tuple;
897                 Form_pg_proc procedureStruct;
898                 Datum           datum;
899                 bool            isnull;
900                 MemoryContext oldcxt;
901
902                 fcache = MemoryContextAllocZero(fcinfo->flinfo->fn_mcxt,
903                                                                                 sizeof(*fcache));
904
905                 fmgr_info_cxt_security(fcinfo->flinfo->fn_oid, &fcache->flinfo,
906                                                            fcinfo->flinfo->fn_mcxt, true);
907                 fcache->flinfo.fn_expr = fcinfo->flinfo->fn_expr;
908
909                 tuple = SearchSysCache1(PROCOID,
910                                                                 ObjectIdGetDatum(fcinfo->flinfo->fn_oid));
911                 if (!HeapTupleIsValid(tuple))
912                         elog(ERROR, "cache lookup failed for function %u",
913                                  fcinfo->flinfo->fn_oid);
914                 procedureStruct = (Form_pg_proc) GETSTRUCT(tuple);
915
916                 if (procedureStruct->prosecdef)
917                         fcache->userid = procedureStruct->proowner;
918
919                 datum = SysCacheGetAttr(PROCOID, tuple, Anum_pg_proc_proconfig,
920                                                                 &isnull);
921                 if (!isnull)
922                 {
923                         oldcxt = MemoryContextSwitchTo(fcinfo->flinfo->fn_mcxt);
924                         fcache->proconfig = DatumGetArrayTypePCopy(datum);
925                         MemoryContextSwitchTo(oldcxt);
926                 }
927
928                 ReleaseSysCache(tuple);
929
930                 fcinfo->flinfo->fn_extra = fcache;
931         }
932         else
933                 fcache = fcinfo->flinfo->fn_extra;
934
935         /* GetUserIdAndSecContext is cheap enough that no harm in a wasted call */
936         GetUserIdAndSecContext(&save_userid, &save_sec_context);
937         if (fcache->proconfig)          /* Need a new GUC nesting level */
938                 save_nestlevel = NewGUCNestLevel();
939         else
940                 save_nestlevel = 0;             /* keep compiler quiet */
941
942         if (OidIsValid(fcache->userid))
943                 SetUserIdAndSecContext(fcache->userid,
944                                                         save_sec_context | SECURITY_LOCAL_USERID_CHANGE);
945
946         if (fcache->proconfig)
947         {
948                 ProcessGUCArray(fcache->proconfig,
949                                                 (superuser() ? PGC_SUSET : PGC_USERSET),
950                                                 PGC_S_SESSION,
951                                                 GUC_ACTION_SAVE);
952         }
953
954         /* function manager hook */
955         if (fmgr_hook)
956                 (*fmgr_hook) (FHET_START, &fcache->flinfo, &fcache->arg);
957
958         /*
959          * We don't need to restore GUC or userid settings on error, because the
960          * ensuing xact or subxact abort will do that.  The PG_TRY block is only
961          * needed to clean up the flinfo link.
962          */
963         save_flinfo = fcinfo->flinfo;
964
965         PG_TRY();
966         {
967                 fcinfo->flinfo = &fcache->flinfo;
968
969                 /* See notes in fmgr_info_cxt_security */
970                 pgstat_init_function_usage(fcinfo, &fcusage);
971
972                 result = FunctionCallInvoke(fcinfo);
973
974                 /*
975                  * We could be calling either a regular or a set-returning function,
976                  * so we have to test to see what finalize flag to use.
977                  */
978                 pgstat_end_function_usage(&fcusage,
979                                                                   (fcinfo->resultinfo == NULL ||
980                                                                    !IsA(fcinfo->resultinfo, ReturnSetInfo) ||
981                                                                    ((ReturnSetInfo *) fcinfo->resultinfo)->isDone != ExprMultipleResult));
982         }
983         PG_CATCH();
984         {
985                 fcinfo->flinfo = save_flinfo;
986                 if (fmgr_hook)
987                         (*fmgr_hook) (FHET_ABORT, &fcache->flinfo, &fcache->arg);
988                 PG_RE_THROW();
989         }
990         PG_END_TRY();
991
992         fcinfo->flinfo = save_flinfo;
993
994         if (fcache->proconfig)
995                 AtEOXact_GUC(true, save_nestlevel);
996         if (OidIsValid(fcache->userid))
997                 SetUserIdAndSecContext(save_userid, save_sec_context);
998         if (fmgr_hook)
999                 (*fmgr_hook) (FHET_END, &fcache->flinfo, &fcache->arg);
1000
1001         return result;
1002 }
1003
1004
1005 /*-------------------------------------------------------------------------
1006  *              Support routines for callers of fmgr-compatible functions
1007  *-------------------------------------------------------------------------
1008  */
1009
1010 /*
1011  * These are for invocation of a specifically named function with a
1012  * directly-computed parameter list.  Note that neither arguments nor result
1013  * are allowed to be NULL.      Also, the function cannot be one that needs to
1014  * look at FmgrInfo, since there won't be any.
1015  */
1016 Datum
1017 DirectFunctionCall1Coll(PGFunction func, Oid collation, Datum arg1)
1018 {
1019         FunctionCallInfoData fcinfo;
1020         Datum           result;
1021
1022         InitFunctionCallInfoData(fcinfo, NULL, 1, collation, NULL, NULL);
1023
1024         fcinfo.arg[0] = arg1;
1025         fcinfo.argnull[0] = false;
1026
1027         result = (*func) (&fcinfo);
1028
1029         /* Check for null result, since caller is clearly not expecting one */
1030         if (fcinfo.isnull)
1031                 elog(ERROR, "function %p returned NULL", (void *) func);
1032
1033         return result;
1034 }
1035
1036 Datum
1037 DirectFunctionCall2Coll(PGFunction func, Oid collation, Datum arg1, Datum arg2)
1038 {
1039         FunctionCallInfoData fcinfo;
1040         Datum           result;
1041
1042         InitFunctionCallInfoData(fcinfo, NULL, 2, collation, NULL, NULL);
1043
1044         fcinfo.arg[0] = arg1;
1045         fcinfo.arg[1] = arg2;
1046         fcinfo.argnull[0] = false;
1047         fcinfo.argnull[1] = false;
1048
1049         result = (*func) (&fcinfo);
1050
1051         /* Check for null result, since caller is clearly not expecting one */
1052         if (fcinfo.isnull)
1053                 elog(ERROR, "function %p returned NULL", (void *) func);
1054
1055         return result;
1056 }
1057
1058 Datum
1059 DirectFunctionCall3Coll(PGFunction func, Oid collation, Datum arg1, Datum arg2,
1060                                                 Datum arg3)
1061 {
1062         FunctionCallInfoData fcinfo;
1063         Datum           result;
1064
1065         InitFunctionCallInfoData(fcinfo, NULL, 3, collation, NULL, NULL);
1066
1067         fcinfo.arg[0] = arg1;
1068         fcinfo.arg[1] = arg2;
1069         fcinfo.arg[2] = arg3;
1070         fcinfo.argnull[0] = false;
1071         fcinfo.argnull[1] = false;
1072         fcinfo.argnull[2] = false;
1073
1074         result = (*func) (&fcinfo);
1075
1076         /* Check for null result, since caller is clearly not expecting one */
1077         if (fcinfo.isnull)
1078                 elog(ERROR, "function %p returned NULL", (void *) func);
1079
1080         return result;
1081 }
1082
1083 Datum
1084 DirectFunctionCall4Coll(PGFunction func, Oid collation, Datum arg1, Datum arg2,
1085                                                 Datum arg3, Datum arg4)
1086 {
1087         FunctionCallInfoData fcinfo;
1088         Datum           result;
1089
1090         InitFunctionCallInfoData(fcinfo, NULL, 4, collation, NULL, NULL);
1091
1092         fcinfo.arg[0] = arg1;
1093         fcinfo.arg[1] = arg2;
1094         fcinfo.arg[2] = arg3;
1095         fcinfo.arg[3] = arg4;
1096         fcinfo.argnull[0] = false;
1097         fcinfo.argnull[1] = false;
1098         fcinfo.argnull[2] = false;
1099         fcinfo.argnull[3] = false;
1100
1101         result = (*func) (&fcinfo);
1102
1103         /* Check for null result, since caller is clearly not expecting one */
1104         if (fcinfo.isnull)
1105                 elog(ERROR, "function %p returned NULL", (void *) func);
1106
1107         return result;
1108 }
1109
1110 Datum
1111 DirectFunctionCall5Coll(PGFunction func, Oid collation, Datum arg1, Datum arg2,
1112                                                 Datum arg3, Datum arg4, Datum arg5)
1113 {
1114         FunctionCallInfoData fcinfo;
1115         Datum           result;
1116
1117         InitFunctionCallInfoData(fcinfo, NULL, 5, collation, NULL, NULL);
1118
1119         fcinfo.arg[0] = arg1;
1120         fcinfo.arg[1] = arg2;
1121         fcinfo.arg[2] = arg3;
1122         fcinfo.arg[3] = arg4;
1123         fcinfo.arg[4] = arg5;
1124         fcinfo.argnull[0] = false;
1125         fcinfo.argnull[1] = false;
1126         fcinfo.argnull[2] = false;
1127         fcinfo.argnull[3] = false;
1128         fcinfo.argnull[4] = false;
1129
1130         result = (*func) (&fcinfo);
1131
1132         /* Check for null result, since caller is clearly not expecting one */
1133         if (fcinfo.isnull)
1134                 elog(ERROR, "function %p returned NULL", (void *) func);
1135
1136         return result;
1137 }
1138
1139 Datum
1140 DirectFunctionCall6Coll(PGFunction func, Oid collation, Datum arg1, Datum arg2,
1141                                                 Datum arg3, Datum arg4, Datum arg5,
1142                                                 Datum arg6)
1143 {
1144         FunctionCallInfoData fcinfo;
1145         Datum           result;
1146
1147         InitFunctionCallInfoData(fcinfo, NULL, 6, collation, NULL, NULL);
1148
1149         fcinfo.arg[0] = arg1;
1150         fcinfo.arg[1] = arg2;
1151         fcinfo.arg[2] = arg3;
1152         fcinfo.arg[3] = arg4;
1153         fcinfo.arg[4] = arg5;
1154         fcinfo.arg[5] = arg6;
1155         fcinfo.argnull[0] = false;
1156         fcinfo.argnull[1] = false;
1157         fcinfo.argnull[2] = false;
1158         fcinfo.argnull[3] = false;
1159         fcinfo.argnull[4] = false;
1160         fcinfo.argnull[5] = false;
1161
1162         result = (*func) (&fcinfo);
1163
1164         /* Check for null result, since caller is clearly not expecting one */
1165         if (fcinfo.isnull)
1166                 elog(ERROR, "function %p returned NULL", (void *) func);
1167
1168         return result;
1169 }
1170
1171 Datum
1172 DirectFunctionCall7Coll(PGFunction func, Oid collation, Datum arg1, Datum arg2,
1173                                                 Datum arg3, Datum arg4, Datum arg5,
1174                                                 Datum arg6, Datum arg7)
1175 {
1176         FunctionCallInfoData fcinfo;
1177         Datum           result;
1178
1179         InitFunctionCallInfoData(fcinfo, NULL, 7, collation, NULL, NULL);
1180
1181         fcinfo.arg[0] = arg1;
1182         fcinfo.arg[1] = arg2;
1183         fcinfo.arg[2] = arg3;
1184         fcinfo.arg[3] = arg4;
1185         fcinfo.arg[4] = arg5;
1186         fcinfo.arg[5] = arg6;
1187         fcinfo.arg[6] = arg7;
1188         fcinfo.argnull[0] = false;
1189         fcinfo.argnull[1] = false;
1190         fcinfo.argnull[2] = false;
1191         fcinfo.argnull[3] = false;
1192         fcinfo.argnull[4] = false;
1193         fcinfo.argnull[5] = false;
1194         fcinfo.argnull[6] = false;
1195
1196         result = (*func) (&fcinfo);
1197
1198         /* Check for null result, since caller is clearly not expecting one */
1199         if (fcinfo.isnull)
1200                 elog(ERROR, "function %p returned NULL", (void *) func);
1201
1202         return result;
1203 }
1204
1205 Datum
1206 DirectFunctionCall8Coll(PGFunction func, Oid collation, Datum arg1, Datum arg2,
1207                                                 Datum arg3, Datum arg4, Datum arg5,
1208                                                 Datum arg6, Datum arg7, Datum arg8)
1209 {
1210         FunctionCallInfoData fcinfo;
1211         Datum           result;
1212
1213         InitFunctionCallInfoData(fcinfo, NULL, 8, collation, NULL, NULL);
1214
1215         fcinfo.arg[0] = arg1;
1216         fcinfo.arg[1] = arg2;
1217         fcinfo.arg[2] = arg3;
1218         fcinfo.arg[3] = arg4;
1219         fcinfo.arg[4] = arg5;
1220         fcinfo.arg[5] = arg6;
1221         fcinfo.arg[6] = arg7;
1222         fcinfo.arg[7] = arg8;
1223         fcinfo.argnull[0] = false;
1224         fcinfo.argnull[1] = false;
1225         fcinfo.argnull[2] = false;
1226         fcinfo.argnull[3] = false;
1227         fcinfo.argnull[4] = false;
1228         fcinfo.argnull[5] = false;
1229         fcinfo.argnull[6] = false;
1230         fcinfo.argnull[7] = false;
1231
1232         result = (*func) (&fcinfo);
1233
1234         /* Check for null result, since caller is clearly not expecting one */
1235         if (fcinfo.isnull)
1236                 elog(ERROR, "function %p returned NULL", (void *) func);
1237
1238         return result;
1239 }
1240
1241 Datum
1242 DirectFunctionCall9Coll(PGFunction func, Oid collation, Datum arg1, Datum arg2,
1243                                                 Datum arg3, Datum arg4, Datum arg5,
1244                                                 Datum arg6, Datum arg7, Datum arg8,
1245                                                 Datum arg9)
1246 {
1247         FunctionCallInfoData fcinfo;
1248         Datum           result;
1249
1250         InitFunctionCallInfoData(fcinfo, NULL, 9, collation, NULL, NULL);
1251
1252         fcinfo.arg[0] = arg1;
1253         fcinfo.arg[1] = arg2;
1254         fcinfo.arg[2] = arg3;
1255         fcinfo.arg[3] = arg4;
1256         fcinfo.arg[4] = arg5;
1257         fcinfo.arg[5] = arg6;
1258         fcinfo.arg[6] = arg7;
1259         fcinfo.arg[7] = arg8;
1260         fcinfo.arg[8] = arg9;
1261         fcinfo.argnull[0] = false;
1262         fcinfo.argnull[1] = false;
1263         fcinfo.argnull[2] = false;
1264         fcinfo.argnull[3] = false;
1265         fcinfo.argnull[4] = false;
1266         fcinfo.argnull[5] = false;
1267         fcinfo.argnull[6] = false;
1268         fcinfo.argnull[7] = false;
1269         fcinfo.argnull[8] = false;
1270
1271         result = (*func) (&fcinfo);
1272
1273         /* Check for null result, since caller is clearly not expecting one */
1274         if (fcinfo.isnull)
1275                 elog(ERROR, "function %p returned NULL", (void *) func);
1276
1277         return result;
1278 }
1279
1280
1281 /*
1282  * These are for invocation of a previously-looked-up function with a
1283  * directly-computed parameter list.  Note that neither arguments nor result
1284  * are allowed to be NULL.
1285  */
1286 Datum
1287 FunctionCall1Coll(FmgrInfo *flinfo, Oid collation, Datum arg1)
1288 {
1289         FunctionCallInfoData fcinfo;
1290         Datum           result;
1291
1292         InitFunctionCallInfoData(fcinfo, flinfo, 1, collation, NULL, NULL);
1293
1294         fcinfo.arg[0] = arg1;
1295         fcinfo.argnull[0] = false;
1296
1297         result = FunctionCallInvoke(&fcinfo);
1298
1299         /* Check for null result, since caller is clearly not expecting one */
1300         if (fcinfo.isnull)
1301                 elog(ERROR, "function %u returned NULL", fcinfo.flinfo->fn_oid);
1302
1303         return result;
1304 }
1305
1306 Datum
1307 FunctionCall2Coll(FmgrInfo *flinfo, Oid collation, Datum arg1, Datum arg2)
1308 {
1309         /*
1310          * XXX if you change this routine, see also the inlined version in
1311          * utils/sort/tuplesort.c!
1312          */
1313         FunctionCallInfoData fcinfo;
1314         Datum           result;
1315
1316         InitFunctionCallInfoData(fcinfo, flinfo, 2, collation, NULL, NULL);
1317
1318         fcinfo.arg[0] = arg1;
1319         fcinfo.arg[1] = arg2;
1320         fcinfo.argnull[0] = false;
1321         fcinfo.argnull[1] = false;
1322
1323         result = FunctionCallInvoke(&fcinfo);
1324
1325         /* Check for null result, since caller is clearly not expecting one */
1326         if (fcinfo.isnull)
1327                 elog(ERROR, "function %u returned NULL", fcinfo.flinfo->fn_oid);
1328
1329         return result;
1330 }
1331
1332 Datum
1333 FunctionCall3Coll(FmgrInfo *flinfo, Oid collation, Datum arg1, Datum arg2,
1334                                   Datum arg3)
1335 {
1336         FunctionCallInfoData fcinfo;
1337         Datum           result;
1338
1339         InitFunctionCallInfoData(fcinfo, flinfo, 3, collation, NULL, NULL);
1340
1341         fcinfo.arg[0] = arg1;
1342         fcinfo.arg[1] = arg2;
1343         fcinfo.arg[2] = arg3;
1344         fcinfo.argnull[0] = false;
1345         fcinfo.argnull[1] = false;
1346         fcinfo.argnull[2] = false;
1347
1348         result = FunctionCallInvoke(&fcinfo);
1349
1350         /* Check for null result, since caller is clearly not expecting one */
1351         if (fcinfo.isnull)
1352                 elog(ERROR, "function %u returned NULL", fcinfo.flinfo->fn_oid);
1353
1354         return result;
1355 }
1356
1357 Datum
1358 FunctionCall4Coll(FmgrInfo *flinfo, Oid collation, Datum arg1, Datum arg2,
1359                                   Datum arg3, Datum arg4)
1360 {
1361         FunctionCallInfoData fcinfo;
1362         Datum           result;
1363
1364         InitFunctionCallInfoData(fcinfo, flinfo, 4, collation, NULL, NULL);
1365
1366         fcinfo.arg[0] = arg1;
1367         fcinfo.arg[1] = arg2;
1368         fcinfo.arg[2] = arg3;
1369         fcinfo.arg[3] = arg4;
1370         fcinfo.argnull[0] = false;
1371         fcinfo.argnull[1] = false;
1372         fcinfo.argnull[2] = false;
1373         fcinfo.argnull[3] = false;
1374
1375         result = FunctionCallInvoke(&fcinfo);
1376
1377         /* Check for null result, since caller is clearly not expecting one */
1378         if (fcinfo.isnull)
1379                 elog(ERROR, "function %u returned NULL", fcinfo.flinfo->fn_oid);
1380
1381         return result;
1382 }
1383
1384 Datum
1385 FunctionCall5Coll(FmgrInfo *flinfo, Oid collation, Datum arg1, Datum arg2,
1386                                   Datum arg3, Datum arg4, Datum arg5)
1387 {
1388         FunctionCallInfoData fcinfo;
1389         Datum           result;
1390
1391         InitFunctionCallInfoData(fcinfo, flinfo, 5, collation, NULL, NULL);
1392
1393         fcinfo.arg[0] = arg1;
1394         fcinfo.arg[1] = arg2;
1395         fcinfo.arg[2] = arg3;
1396         fcinfo.arg[3] = arg4;
1397         fcinfo.arg[4] = arg5;
1398         fcinfo.argnull[0] = false;
1399         fcinfo.argnull[1] = false;
1400         fcinfo.argnull[2] = false;
1401         fcinfo.argnull[3] = false;
1402         fcinfo.argnull[4] = false;
1403
1404         result = FunctionCallInvoke(&fcinfo);
1405
1406         /* Check for null result, since caller is clearly not expecting one */
1407         if (fcinfo.isnull)
1408                 elog(ERROR, "function %u returned NULL", fcinfo.flinfo->fn_oid);
1409
1410         return result;
1411 }
1412
1413 Datum
1414 FunctionCall6Coll(FmgrInfo *flinfo, Oid collation, Datum arg1, Datum arg2,
1415                                   Datum arg3, Datum arg4, Datum arg5,
1416                                   Datum arg6)
1417 {
1418         FunctionCallInfoData fcinfo;
1419         Datum           result;
1420
1421         InitFunctionCallInfoData(fcinfo, flinfo, 6, collation, NULL, NULL);
1422
1423         fcinfo.arg[0] = arg1;
1424         fcinfo.arg[1] = arg2;
1425         fcinfo.arg[2] = arg3;
1426         fcinfo.arg[3] = arg4;
1427         fcinfo.arg[4] = arg5;
1428         fcinfo.arg[5] = arg6;
1429         fcinfo.argnull[0] = false;
1430         fcinfo.argnull[1] = false;
1431         fcinfo.argnull[2] = false;
1432         fcinfo.argnull[3] = false;
1433         fcinfo.argnull[4] = false;
1434         fcinfo.argnull[5] = false;
1435
1436         result = FunctionCallInvoke(&fcinfo);
1437
1438         /* Check for null result, since caller is clearly not expecting one */
1439         if (fcinfo.isnull)
1440                 elog(ERROR, "function %u returned NULL", fcinfo.flinfo->fn_oid);
1441
1442         return result;
1443 }
1444
1445 Datum
1446 FunctionCall7Coll(FmgrInfo *flinfo, Oid collation, Datum arg1, Datum arg2,
1447                                   Datum arg3, Datum arg4, Datum arg5,
1448                                   Datum arg6, Datum arg7)
1449 {
1450         FunctionCallInfoData fcinfo;
1451         Datum           result;
1452
1453         InitFunctionCallInfoData(fcinfo, flinfo, 7, collation, NULL, NULL);
1454
1455         fcinfo.arg[0] = arg1;
1456         fcinfo.arg[1] = arg2;
1457         fcinfo.arg[2] = arg3;
1458         fcinfo.arg[3] = arg4;
1459         fcinfo.arg[4] = arg5;
1460         fcinfo.arg[5] = arg6;
1461         fcinfo.arg[6] = arg7;
1462         fcinfo.argnull[0] = false;
1463         fcinfo.argnull[1] = false;
1464         fcinfo.argnull[2] = false;
1465         fcinfo.argnull[3] = false;
1466         fcinfo.argnull[4] = false;
1467         fcinfo.argnull[5] = false;
1468         fcinfo.argnull[6] = false;
1469
1470         result = FunctionCallInvoke(&fcinfo);
1471
1472         /* Check for null result, since caller is clearly not expecting one */
1473         if (fcinfo.isnull)
1474                 elog(ERROR, "function %u returned NULL", fcinfo.flinfo->fn_oid);
1475
1476         return result;
1477 }
1478
1479 Datum
1480 FunctionCall8Coll(FmgrInfo *flinfo, Oid collation, Datum arg1, Datum arg2,
1481                                   Datum arg3, Datum arg4, Datum arg5,
1482                                   Datum arg6, Datum arg7, Datum arg8)
1483 {
1484         FunctionCallInfoData fcinfo;
1485         Datum           result;
1486
1487         InitFunctionCallInfoData(fcinfo, flinfo, 8, collation, NULL, NULL);
1488
1489         fcinfo.arg[0] = arg1;
1490         fcinfo.arg[1] = arg2;
1491         fcinfo.arg[2] = arg3;
1492         fcinfo.arg[3] = arg4;
1493         fcinfo.arg[4] = arg5;
1494         fcinfo.arg[5] = arg6;
1495         fcinfo.arg[6] = arg7;
1496         fcinfo.arg[7] = arg8;
1497         fcinfo.argnull[0] = false;
1498         fcinfo.argnull[1] = false;
1499         fcinfo.argnull[2] = false;
1500         fcinfo.argnull[3] = false;
1501         fcinfo.argnull[4] = false;
1502         fcinfo.argnull[5] = false;
1503         fcinfo.argnull[6] = false;
1504         fcinfo.argnull[7] = false;
1505
1506         result = FunctionCallInvoke(&fcinfo);
1507
1508         /* Check for null result, since caller is clearly not expecting one */
1509         if (fcinfo.isnull)
1510                 elog(ERROR, "function %u returned NULL", fcinfo.flinfo->fn_oid);
1511
1512         return result;
1513 }
1514
1515 Datum
1516 FunctionCall9Coll(FmgrInfo *flinfo, Oid collation, Datum arg1, Datum arg2,
1517                                   Datum arg3, Datum arg4, Datum arg5,
1518                                   Datum arg6, Datum arg7, Datum arg8,
1519                                   Datum arg9)
1520 {
1521         FunctionCallInfoData fcinfo;
1522         Datum           result;
1523
1524         InitFunctionCallInfoData(fcinfo, flinfo, 9, collation, NULL, NULL);
1525
1526         fcinfo.arg[0] = arg1;
1527         fcinfo.arg[1] = arg2;
1528         fcinfo.arg[2] = arg3;
1529         fcinfo.arg[3] = arg4;
1530         fcinfo.arg[4] = arg5;
1531         fcinfo.arg[5] = arg6;
1532         fcinfo.arg[6] = arg7;
1533         fcinfo.arg[7] = arg8;
1534         fcinfo.arg[8] = arg9;
1535         fcinfo.argnull[0] = false;
1536         fcinfo.argnull[1] = false;
1537         fcinfo.argnull[2] = false;
1538         fcinfo.argnull[3] = false;
1539         fcinfo.argnull[4] = false;
1540         fcinfo.argnull[5] = false;
1541         fcinfo.argnull[6] = false;
1542         fcinfo.argnull[7] = false;
1543         fcinfo.argnull[8] = false;
1544
1545         result = FunctionCallInvoke(&fcinfo);
1546
1547         /* Check for null result, since caller is clearly not expecting one */
1548         if (fcinfo.isnull)
1549                 elog(ERROR, "function %u returned NULL", fcinfo.flinfo->fn_oid);
1550
1551         return result;
1552 }
1553
1554
1555 /*
1556  * These are for invocation of a function identified by OID with a
1557  * directly-computed parameter list.  Note that neither arguments nor result
1558  * are allowed to be NULL.      These are essentially fmgr_info() followed
1559  * by FunctionCallN().  If the same function is to be invoked repeatedly,
1560  * do the fmgr_info() once and then use FunctionCallN().
1561  */
1562 Datum
1563 OidFunctionCall0Coll(Oid functionId, Oid collation)
1564 {
1565         FmgrInfo        flinfo;
1566         FunctionCallInfoData fcinfo;
1567         Datum           result;
1568
1569         fmgr_info(functionId, &flinfo);
1570
1571         InitFunctionCallInfoData(fcinfo, &flinfo, 0, collation, NULL, NULL);
1572
1573         result = FunctionCallInvoke(&fcinfo);
1574
1575         /* Check for null result, since caller is clearly not expecting one */
1576         if (fcinfo.isnull)
1577                 elog(ERROR, "function %u returned NULL", flinfo.fn_oid);
1578
1579         return result;
1580 }
1581
1582 Datum
1583 OidFunctionCall1Coll(Oid functionId, Oid collation, Datum arg1)
1584 {
1585         FmgrInfo        flinfo;
1586         FunctionCallInfoData fcinfo;
1587         Datum           result;
1588
1589         fmgr_info(functionId, &flinfo);
1590
1591         InitFunctionCallInfoData(fcinfo, &flinfo, 1, collation, NULL, NULL);
1592
1593         fcinfo.arg[0] = arg1;
1594         fcinfo.argnull[0] = false;
1595
1596         result = FunctionCallInvoke(&fcinfo);
1597
1598         /* Check for null result, since caller is clearly not expecting one */
1599         if (fcinfo.isnull)
1600                 elog(ERROR, "function %u returned NULL", flinfo.fn_oid);
1601
1602         return result;
1603 }
1604
1605 Datum
1606 OidFunctionCall2Coll(Oid functionId, Oid collation, Datum arg1, Datum arg2)
1607 {
1608         FmgrInfo        flinfo;
1609         FunctionCallInfoData fcinfo;
1610         Datum           result;
1611
1612         fmgr_info(functionId, &flinfo);
1613
1614         InitFunctionCallInfoData(fcinfo, &flinfo, 2, collation, NULL, NULL);
1615
1616         fcinfo.arg[0] = arg1;
1617         fcinfo.arg[1] = arg2;
1618         fcinfo.argnull[0] = false;
1619         fcinfo.argnull[1] = false;
1620
1621         result = FunctionCallInvoke(&fcinfo);
1622
1623         /* Check for null result, since caller is clearly not expecting one */
1624         if (fcinfo.isnull)
1625                 elog(ERROR, "function %u returned NULL", flinfo.fn_oid);
1626
1627         return result;
1628 }
1629
1630 Datum
1631 OidFunctionCall3Coll(Oid functionId, Oid collation, Datum arg1, Datum arg2,
1632                                          Datum arg3)
1633 {
1634         FmgrInfo        flinfo;
1635         FunctionCallInfoData fcinfo;
1636         Datum           result;
1637
1638         fmgr_info(functionId, &flinfo);
1639
1640         InitFunctionCallInfoData(fcinfo, &flinfo, 3, collation, NULL, NULL);
1641
1642         fcinfo.arg[0] = arg1;
1643         fcinfo.arg[1] = arg2;
1644         fcinfo.arg[2] = arg3;
1645         fcinfo.argnull[0] = false;
1646         fcinfo.argnull[1] = false;
1647         fcinfo.argnull[2] = false;
1648
1649         result = FunctionCallInvoke(&fcinfo);
1650
1651         /* Check for null result, since caller is clearly not expecting one */
1652         if (fcinfo.isnull)
1653                 elog(ERROR, "function %u returned NULL", flinfo.fn_oid);
1654
1655         return result;
1656 }
1657
1658 Datum
1659 OidFunctionCall4Coll(Oid functionId, Oid collation, Datum arg1, Datum arg2,
1660                                          Datum arg3, Datum arg4)
1661 {
1662         FmgrInfo        flinfo;
1663         FunctionCallInfoData fcinfo;
1664         Datum           result;
1665
1666         fmgr_info(functionId, &flinfo);
1667
1668         InitFunctionCallInfoData(fcinfo, &flinfo, 4, collation, NULL, NULL);
1669
1670         fcinfo.arg[0] = arg1;
1671         fcinfo.arg[1] = arg2;
1672         fcinfo.arg[2] = arg3;
1673         fcinfo.arg[3] = arg4;
1674         fcinfo.argnull[0] = false;
1675         fcinfo.argnull[1] = false;
1676         fcinfo.argnull[2] = false;
1677         fcinfo.argnull[3] = false;
1678
1679         result = FunctionCallInvoke(&fcinfo);
1680
1681         /* Check for null result, since caller is clearly not expecting one */
1682         if (fcinfo.isnull)
1683                 elog(ERROR, "function %u returned NULL", flinfo.fn_oid);
1684
1685         return result;
1686 }
1687
1688 Datum
1689 OidFunctionCall5Coll(Oid functionId, Oid collation, Datum arg1, Datum arg2,
1690                                          Datum arg3, Datum arg4, Datum arg5)
1691 {
1692         FmgrInfo        flinfo;
1693         FunctionCallInfoData fcinfo;
1694         Datum           result;
1695
1696         fmgr_info(functionId, &flinfo);
1697
1698         InitFunctionCallInfoData(fcinfo, &flinfo, 5, collation, NULL, NULL);
1699
1700         fcinfo.arg[0] = arg1;
1701         fcinfo.arg[1] = arg2;
1702         fcinfo.arg[2] = arg3;
1703         fcinfo.arg[3] = arg4;
1704         fcinfo.arg[4] = arg5;
1705         fcinfo.argnull[0] = false;
1706         fcinfo.argnull[1] = false;
1707         fcinfo.argnull[2] = false;
1708         fcinfo.argnull[3] = false;
1709         fcinfo.argnull[4] = false;
1710
1711         result = FunctionCallInvoke(&fcinfo);
1712
1713         /* Check for null result, since caller is clearly not expecting one */
1714         if (fcinfo.isnull)
1715                 elog(ERROR, "function %u returned NULL", flinfo.fn_oid);
1716
1717         return result;
1718 }
1719
1720 Datum
1721 OidFunctionCall6Coll(Oid functionId, Oid collation, Datum arg1, Datum arg2,
1722                                          Datum arg3, Datum arg4, Datum arg5,
1723                                          Datum arg6)
1724 {
1725         FmgrInfo        flinfo;
1726         FunctionCallInfoData fcinfo;
1727         Datum           result;
1728
1729         fmgr_info(functionId, &flinfo);
1730
1731         InitFunctionCallInfoData(fcinfo, &flinfo, 6, collation, NULL, NULL);
1732
1733         fcinfo.arg[0] = arg1;
1734         fcinfo.arg[1] = arg2;
1735         fcinfo.arg[2] = arg3;
1736         fcinfo.arg[3] = arg4;
1737         fcinfo.arg[4] = arg5;
1738         fcinfo.arg[5] = arg6;
1739         fcinfo.argnull[0] = false;
1740         fcinfo.argnull[1] = false;
1741         fcinfo.argnull[2] = false;
1742         fcinfo.argnull[3] = false;
1743         fcinfo.argnull[4] = false;
1744         fcinfo.argnull[5] = false;
1745
1746         result = FunctionCallInvoke(&fcinfo);
1747
1748         /* Check for null result, since caller is clearly not expecting one */
1749         if (fcinfo.isnull)
1750                 elog(ERROR, "function %u returned NULL", flinfo.fn_oid);
1751
1752         return result;
1753 }
1754
1755 Datum
1756 OidFunctionCall7Coll(Oid functionId, Oid collation, Datum arg1, Datum arg2,
1757                                          Datum arg3, Datum arg4, Datum arg5,
1758                                          Datum arg6, Datum arg7)
1759 {
1760         FmgrInfo        flinfo;
1761         FunctionCallInfoData fcinfo;
1762         Datum           result;
1763
1764         fmgr_info(functionId, &flinfo);
1765
1766         InitFunctionCallInfoData(fcinfo, &flinfo, 7, collation, NULL, NULL);
1767
1768         fcinfo.arg[0] = arg1;
1769         fcinfo.arg[1] = arg2;
1770         fcinfo.arg[2] = arg3;
1771         fcinfo.arg[3] = arg4;
1772         fcinfo.arg[4] = arg5;
1773         fcinfo.arg[5] = arg6;
1774         fcinfo.arg[6] = arg7;
1775         fcinfo.argnull[0] = false;
1776         fcinfo.argnull[1] = false;
1777         fcinfo.argnull[2] = false;
1778         fcinfo.argnull[3] = false;
1779         fcinfo.argnull[4] = false;
1780         fcinfo.argnull[5] = false;
1781         fcinfo.argnull[6] = false;
1782
1783         result = FunctionCallInvoke(&fcinfo);
1784
1785         /* Check for null result, since caller is clearly not expecting one */
1786         if (fcinfo.isnull)
1787                 elog(ERROR, "function %u returned NULL", flinfo.fn_oid);
1788
1789         return result;
1790 }
1791
1792 Datum
1793 OidFunctionCall8Coll(Oid functionId, Oid collation, Datum arg1, Datum arg2,
1794                                          Datum arg3, Datum arg4, Datum arg5,
1795                                          Datum arg6, Datum arg7, Datum arg8)
1796 {
1797         FmgrInfo        flinfo;
1798         FunctionCallInfoData fcinfo;
1799         Datum           result;
1800
1801         fmgr_info(functionId, &flinfo);
1802
1803         InitFunctionCallInfoData(fcinfo, &flinfo, 8, collation, NULL, NULL);
1804
1805         fcinfo.arg[0] = arg1;
1806         fcinfo.arg[1] = arg2;
1807         fcinfo.arg[2] = arg3;
1808         fcinfo.arg[3] = arg4;
1809         fcinfo.arg[4] = arg5;
1810         fcinfo.arg[5] = arg6;
1811         fcinfo.arg[6] = arg7;
1812         fcinfo.arg[7] = arg8;
1813         fcinfo.argnull[0] = false;
1814         fcinfo.argnull[1] = false;
1815         fcinfo.argnull[2] = false;
1816         fcinfo.argnull[3] = false;
1817         fcinfo.argnull[4] = false;
1818         fcinfo.argnull[5] = false;
1819         fcinfo.argnull[6] = false;
1820         fcinfo.argnull[7] = false;
1821
1822         result = FunctionCallInvoke(&fcinfo);
1823
1824         /* Check for null result, since caller is clearly not expecting one */
1825         if (fcinfo.isnull)
1826                 elog(ERROR, "function %u returned NULL", flinfo.fn_oid);
1827
1828         return result;
1829 }
1830
1831 Datum
1832 OidFunctionCall9Coll(Oid functionId, Oid collation, Datum arg1, Datum arg2,
1833                                          Datum arg3, Datum arg4, Datum arg5,
1834                                          Datum arg6, Datum arg7, Datum arg8,
1835                                          Datum arg9)
1836 {
1837         FmgrInfo        flinfo;
1838         FunctionCallInfoData fcinfo;
1839         Datum           result;
1840
1841         fmgr_info(functionId, &flinfo);
1842
1843         InitFunctionCallInfoData(fcinfo, &flinfo, 9, collation, NULL, NULL);
1844
1845         fcinfo.arg[0] = arg1;
1846         fcinfo.arg[1] = arg2;
1847         fcinfo.arg[2] = arg3;
1848         fcinfo.arg[3] = arg4;
1849         fcinfo.arg[4] = arg5;
1850         fcinfo.arg[5] = arg6;
1851         fcinfo.arg[6] = arg7;
1852         fcinfo.arg[7] = arg8;
1853         fcinfo.arg[8] = arg9;
1854         fcinfo.argnull[0] = false;
1855         fcinfo.argnull[1] = false;
1856         fcinfo.argnull[2] = false;
1857         fcinfo.argnull[3] = false;
1858         fcinfo.argnull[4] = false;
1859         fcinfo.argnull[5] = false;
1860         fcinfo.argnull[6] = false;
1861         fcinfo.argnull[7] = false;
1862         fcinfo.argnull[8] = false;
1863
1864         result = FunctionCallInvoke(&fcinfo);
1865
1866         /* Check for null result, since caller is clearly not expecting one */
1867         if (fcinfo.isnull)
1868                 elog(ERROR, "function %u returned NULL", flinfo.fn_oid);
1869
1870         return result;
1871 }
1872
1873
1874 /*
1875  * Special cases for convenient invocation of datatype I/O functions.
1876  */
1877
1878 /*
1879  * Call a previously-looked-up datatype input function.
1880  *
1881  * "str" may be NULL to indicate we are reading a NULL.  In this case
1882  * the caller should assume the result is NULL, but we'll call the input
1883  * function anyway if it's not strict.  So this is almost but not quite
1884  * the same as FunctionCall3.
1885  *
1886  * One important difference from the bare function call is that we will
1887  * push any active SPI context, allowing SPI-using I/O functions to be
1888  * called from other SPI functions without extra notation.      This is a hack,
1889  * but the alternative of expecting all SPI functions to do SPI_push/SPI_pop
1890  * around I/O calls seems worse.
1891  */
1892 Datum
1893 InputFunctionCall(FmgrInfo *flinfo, char *str, Oid typioparam, int32 typmod)
1894 {
1895         FunctionCallInfoData fcinfo;
1896         Datum           result;
1897         bool            pushed;
1898
1899         if (str == NULL && flinfo->fn_strict)
1900                 return (Datum) 0;               /* just return null result */
1901
1902         pushed = SPI_push_conditional();
1903
1904         InitFunctionCallInfoData(fcinfo, flinfo, 3, InvalidOid, NULL, NULL);
1905
1906         fcinfo.arg[0] = CStringGetDatum(str);
1907         fcinfo.arg[1] = ObjectIdGetDatum(typioparam);
1908         fcinfo.arg[2] = Int32GetDatum(typmod);
1909         fcinfo.argnull[0] = (str == NULL);
1910         fcinfo.argnull[1] = false;
1911         fcinfo.argnull[2] = false;
1912
1913         result = FunctionCallInvoke(&fcinfo);
1914
1915         /* Should get null result if and only if str is NULL */
1916         if (str == NULL)
1917         {
1918                 if (!fcinfo.isnull)
1919                         elog(ERROR, "input function %u returned non-NULL",
1920                                  fcinfo.flinfo->fn_oid);
1921         }
1922         else
1923         {
1924                 if (fcinfo.isnull)
1925                         elog(ERROR, "input function %u returned NULL",
1926                                  fcinfo.flinfo->fn_oid);
1927         }
1928
1929         SPI_pop_conditional(pushed);
1930
1931         return result;
1932 }
1933
1934 /*
1935  * Call a previously-looked-up datatype output function.
1936  *
1937  * Do not call this on NULL datums.
1938  *
1939  * This is almost just window dressing for FunctionCall1, but it includes
1940  * SPI context pushing for the same reasons as InputFunctionCall.
1941  */
1942 char *
1943 OutputFunctionCall(FmgrInfo *flinfo, Datum val)
1944 {
1945         char       *result;
1946         bool            pushed;
1947
1948         pushed = SPI_push_conditional();
1949
1950         result = DatumGetCString(FunctionCall1(flinfo, val));
1951
1952         SPI_pop_conditional(pushed);
1953
1954         return result;
1955 }
1956
1957 /*
1958  * Call a previously-looked-up datatype binary-input function.
1959  *
1960  * "buf" may be NULL to indicate we are reading a NULL.  In this case
1961  * the caller should assume the result is NULL, but we'll call the receive
1962  * function anyway if it's not strict.  So this is almost but not quite
1963  * the same as FunctionCall3.  Also, this includes SPI context pushing for
1964  * the same reasons as InputFunctionCall.
1965  */
1966 Datum
1967 ReceiveFunctionCall(FmgrInfo *flinfo, StringInfo buf,
1968                                         Oid typioparam, int32 typmod)
1969 {
1970         FunctionCallInfoData fcinfo;
1971         Datum           result;
1972         bool            pushed;
1973
1974         if (buf == NULL && flinfo->fn_strict)
1975                 return (Datum) 0;               /* just return null result */
1976
1977         pushed = SPI_push_conditional();
1978
1979         InitFunctionCallInfoData(fcinfo, flinfo, 3, InvalidOid, NULL, NULL);
1980
1981         fcinfo.arg[0] = PointerGetDatum(buf);
1982         fcinfo.arg[1] = ObjectIdGetDatum(typioparam);
1983         fcinfo.arg[2] = Int32GetDatum(typmod);
1984         fcinfo.argnull[0] = (buf == NULL);
1985         fcinfo.argnull[1] = false;
1986         fcinfo.argnull[2] = false;
1987
1988         result = FunctionCallInvoke(&fcinfo);
1989
1990         /* Should get null result if and only if buf is NULL */
1991         if (buf == NULL)
1992         {
1993                 if (!fcinfo.isnull)
1994                         elog(ERROR, "receive function %u returned non-NULL",
1995                                  fcinfo.flinfo->fn_oid);
1996         }
1997         else
1998         {
1999                 if (fcinfo.isnull)
2000                         elog(ERROR, "receive function %u returned NULL",
2001                                  fcinfo.flinfo->fn_oid);
2002         }
2003
2004         SPI_pop_conditional(pushed);
2005
2006         return result;
2007 }
2008
2009 /*
2010  * Call a previously-looked-up datatype binary-output function.
2011  *
2012  * Do not call this on NULL datums.
2013  *
2014  * This is little more than window dressing for FunctionCall1, but it does
2015  * guarantee a non-toasted result, which strictly speaking the underlying
2016  * function doesn't.  Also, this includes SPI context pushing for the same
2017  * reasons as InputFunctionCall.
2018  */
2019 bytea *
2020 SendFunctionCall(FmgrInfo *flinfo, Datum val)
2021 {
2022         bytea      *result;
2023         bool            pushed;
2024
2025         pushed = SPI_push_conditional();
2026
2027         result = DatumGetByteaP(FunctionCall1(flinfo, val));
2028
2029         SPI_pop_conditional(pushed);
2030
2031         return result;
2032 }
2033
2034 /*
2035  * As above, for I/O functions identified by OID.  These are only to be used
2036  * in seldom-executed code paths.  They are not only slow but leak memory.
2037  */
2038 Datum
2039 OidInputFunctionCall(Oid functionId, char *str, Oid typioparam, int32 typmod)
2040 {
2041         FmgrInfo        flinfo;
2042
2043         fmgr_info(functionId, &flinfo);
2044         return InputFunctionCall(&flinfo, str, typioparam, typmod);
2045 }
2046
2047 char *
2048 OidOutputFunctionCall(Oid functionId, Datum val)
2049 {
2050         FmgrInfo        flinfo;
2051
2052         fmgr_info(functionId, &flinfo);
2053         return OutputFunctionCall(&flinfo, val);
2054 }
2055
2056 Datum
2057 OidReceiveFunctionCall(Oid functionId, StringInfo buf,
2058                                            Oid typioparam, int32 typmod)
2059 {
2060         FmgrInfo        flinfo;
2061
2062         fmgr_info(functionId, &flinfo);
2063         return ReceiveFunctionCall(&flinfo, buf, typioparam, typmod);
2064 }
2065
2066 bytea *
2067 OidSendFunctionCall(Oid functionId, Datum val)
2068 {
2069         FmgrInfo        flinfo;
2070
2071         fmgr_info(functionId, &flinfo);
2072         return SendFunctionCall(&flinfo, val);
2073 }
2074
2075
2076 /*
2077  * !!! OLD INTERFACE !!!
2078  *
2079  * fmgr() is the only remaining vestige of the old-style caller support
2080  * functions.  It's no longer used anywhere in the Postgres distribution,
2081  * but we should leave it around for a release or two to ease the transition
2082  * for user-supplied C functions.  OidFunctionCallN() replaces it for new
2083  * code.
2084  *
2085  * DEPRECATED, DO NOT USE IN NEW CODE
2086  */
2087 char *
2088 fmgr(Oid procedureId,...)
2089 {
2090         FmgrInfo        flinfo;
2091         FunctionCallInfoData fcinfo;
2092         int                     n_arguments;
2093         Datum           result;
2094
2095         fmgr_info(procedureId, &flinfo);
2096
2097         MemSet(&fcinfo, 0, sizeof(fcinfo));
2098         fcinfo.flinfo = &flinfo;
2099         fcinfo.nargs = flinfo.fn_nargs;
2100         n_arguments = fcinfo.nargs;
2101
2102         if (n_arguments > 0)
2103         {
2104                 va_list         pvar;
2105                 int                     i;
2106
2107                 if (n_arguments > FUNC_MAX_ARGS)
2108                         ereport(ERROR,
2109                                         (errcode(ERRCODE_TOO_MANY_ARGUMENTS),
2110                          errmsg("function %u has too many arguments (%d, maximum is %d)",
2111                                         flinfo.fn_oid, n_arguments, FUNC_MAX_ARGS)));
2112                 va_start(pvar, procedureId);
2113                 for (i = 0; i < n_arguments; i++)
2114                         fcinfo.arg[i] = PointerGetDatum(va_arg(pvar, char *));
2115                 va_end(pvar);
2116         }
2117
2118         result = FunctionCallInvoke(&fcinfo);
2119
2120         /* Check for null result, since caller is clearly not expecting one */
2121         if (fcinfo.isnull)
2122                 elog(ERROR, "function %u returned NULL", flinfo.fn_oid);
2123
2124         return DatumGetPointer(result);
2125 }
2126
2127
2128 /*-------------------------------------------------------------------------
2129  *              Support routines for standard maybe-pass-by-reference datatypes
2130  *
2131  * int8, float4, and float8 can be passed by value if Datum is wide enough.
2132  * (For backwards-compatibility reasons, we allow pass-by-ref to be chosen
2133  * at compile time even if pass-by-val is possible.)  For the float types,
2134  * we need a support routine even if we are passing by value, because many
2135  * machines pass int and float function parameters/results differently;
2136  * so we need to play weird games with unions.
2137  *
2138  * Note: there is only one switch controlling the pass-by-value option for
2139  * both int8 and float8; this is to avoid making things unduly complicated
2140  * for the timestamp types, which might have either representation.
2141  *-------------------------------------------------------------------------
2142  */
2143
2144 #ifndef USE_FLOAT8_BYVAL                /* controls int8 too */
2145
2146 Datum
2147 Int64GetDatum(int64 X)
2148 {
2149         int64      *retval = (int64 *) palloc(sizeof(int64));
2150
2151         *retval = X;
2152         return PointerGetDatum(retval);
2153 }
2154 #endif   /* USE_FLOAT8_BYVAL */
2155
2156 Datum
2157 Float4GetDatum(float4 X)
2158 {
2159 #ifdef USE_FLOAT4_BYVAL
2160         union
2161         {
2162                 float4          value;
2163                 int32           retval;
2164         }                       myunion;
2165
2166         myunion.value = X;
2167         return SET_4_BYTES(myunion.retval);
2168 #else
2169         float4     *retval = (float4 *) palloc(sizeof(float4));
2170
2171         *retval = X;
2172         return PointerGetDatum(retval);
2173 #endif
2174 }
2175
2176 #ifdef USE_FLOAT4_BYVAL
2177
2178 float4
2179 DatumGetFloat4(Datum X)
2180 {
2181         union
2182         {
2183                 int32           value;
2184                 float4          retval;
2185         }                       myunion;
2186
2187         myunion.value = GET_4_BYTES(X);
2188         return myunion.retval;
2189 }
2190 #endif   /* USE_FLOAT4_BYVAL */
2191
2192 Datum
2193 Float8GetDatum(float8 X)
2194 {
2195 #ifdef USE_FLOAT8_BYVAL
2196         union
2197         {
2198                 float8          value;
2199                 int64           retval;
2200         }                       myunion;
2201
2202         myunion.value = X;
2203         return SET_8_BYTES(myunion.retval);
2204 #else
2205         float8     *retval = (float8 *) palloc(sizeof(float8));
2206
2207         *retval = X;
2208         return PointerGetDatum(retval);
2209 #endif
2210 }
2211
2212 #ifdef USE_FLOAT8_BYVAL
2213
2214 float8
2215 DatumGetFloat8(Datum X)
2216 {
2217         union
2218         {
2219                 int64           value;
2220                 float8          retval;
2221         }                       myunion;
2222
2223         myunion.value = GET_8_BYTES(X);
2224         return myunion.retval;
2225 }
2226 #endif   /* USE_FLOAT8_BYVAL */
2227
2228
2229 /*-------------------------------------------------------------------------
2230  *              Support routines for toastable datatypes
2231  *-------------------------------------------------------------------------
2232  */
2233
2234 struct varlena *
2235 pg_detoast_datum(struct varlena * datum)
2236 {
2237         if (VARATT_IS_EXTENDED(datum))
2238                 return heap_tuple_untoast_attr(datum);
2239         else
2240                 return datum;
2241 }
2242
2243 struct varlena *
2244 pg_detoast_datum_copy(struct varlena * datum)
2245 {
2246         if (VARATT_IS_EXTENDED(datum))
2247                 return heap_tuple_untoast_attr(datum);
2248         else
2249         {
2250                 /* Make a modifiable copy of the varlena object */
2251                 Size            len = VARSIZE(datum);
2252                 struct varlena *result = (struct varlena *) palloc(len);
2253
2254                 memcpy(result, datum, len);
2255                 return result;
2256         }
2257 }
2258
2259 struct varlena *
2260 pg_detoast_datum_slice(struct varlena * datum, int32 first, int32 count)
2261 {
2262         /* Only get the specified portion from the toast rel */
2263         return heap_tuple_untoast_attr_slice(datum, first, count);
2264 }
2265
2266 struct varlena *
2267 pg_detoast_datum_packed(struct varlena * datum)
2268 {
2269         if (VARATT_IS_COMPRESSED(datum) || VARATT_IS_EXTERNAL(datum))
2270                 return heap_tuple_untoast_attr(datum);
2271         else
2272                 return datum;
2273 }
2274
2275 /*-------------------------------------------------------------------------
2276  *              Support routines for extracting info from fn_expr parse tree
2277  *
2278  * These are needed by polymorphic functions, which accept multiple possible
2279  * input types and need help from the parser to know what they've got.
2280  * Also, some functions might be interested in whether a parameter is constant.
2281  * Functions taking VARIADIC ANY also need to know about the VARIADIC keyword.
2282  *-------------------------------------------------------------------------
2283  */
2284
2285 /*
2286  * Get the actual type OID of the function return type
2287  *
2288  * Returns InvalidOid if information is not available
2289  */
2290 Oid
2291 get_fn_expr_rettype(FmgrInfo *flinfo)
2292 {
2293         Node       *expr;
2294
2295         /*
2296          * can't return anything useful if we have no FmgrInfo or if its fn_expr
2297          * node has not been initialized
2298          */
2299         if (!flinfo || !flinfo->fn_expr)
2300                 return InvalidOid;
2301
2302         expr = flinfo->fn_expr;
2303
2304         return exprType(expr);
2305 }
2306
2307 /*
2308  * Get the actual type OID of a specific function argument (counting from 0)
2309  *
2310  * Returns InvalidOid if information is not available
2311  */
2312 Oid
2313 get_fn_expr_argtype(FmgrInfo *flinfo, int argnum)
2314 {
2315         /*
2316          * can't return anything useful if we have no FmgrInfo or if its fn_expr
2317          * node has not been initialized
2318          */
2319         if (!flinfo || !flinfo->fn_expr)
2320                 return InvalidOid;
2321
2322         return get_call_expr_argtype(flinfo->fn_expr, argnum);
2323 }
2324
2325 /*
2326  * Get the actual type OID of a specific function argument (counting from 0),
2327  * but working from the calling expression tree instead of FmgrInfo
2328  *
2329  * Returns InvalidOid if information is not available
2330  */
2331 Oid
2332 get_call_expr_argtype(Node *expr, int argnum)
2333 {
2334         List       *args;
2335         Oid                     argtype;
2336
2337         if (expr == NULL)
2338                 return InvalidOid;
2339
2340         if (IsA(expr, FuncExpr))
2341                 args = ((FuncExpr *) expr)->args;
2342         else if (IsA(expr, OpExpr))
2343                 args = ((OpExpr *) expr)->args;
2344         else if (IsA(expr, DistinctExpr))
2345                 args = ((DistinctExpr *) expr)->args;
2346         else if (IsA(expr, ScalarArrayOpExpr))
2347                 args = ((ScalarArrayOpExpr *) expr)->args;
2348         else if (IsA(expr, ArrayCoerceExpr))
2349                 args = list_make1(((ArrayCoerceExpr *) expr)->arg);
2350         else if (IsA(expr, NullIfExpr))
2351                 args = ((NullIfExpr *) expr)->args;
2352         else if (IsA(expr, WindowFunc))
2353                 args = ((WindowFunc *) expr)->args;
2354         else
2355                 return InvalidOid;
2356
2357         if (argnum < 0 || argnum >= list_length(args))
2358                 return InvalidOid;
2359
2360         argtype = exprType((Node *) list_nth(args, argnum));
2361
2362         /*
2363          * special hack for ScalarArrayOpExpr and ArrayCoerceExpr: what the
2364          * underlying function will actually get passed is the element type of the
2365          * array.
2366          */
2367         if (IsA(expr, ScalarArrayOpExpr) &&
2368                 argnum == 1)
2369                 argtype = get_base_element_type(argtype);
2370         else if (IsA(expr, ArrayCoerceExpr) &&
2371                          argnum == 0)
2372                 argtype = get_base_element_type(argtype);
2373
2374         return argtype;
2375 }
2376
2377 /*
2378  * Find out whether a specific function argument is constant for the
2379  * duration of a query
2380  *
2381  * Returns false if information is not available
2382  */
2383 bool
2384 get_fn_expr_arg_stable(FmgrInfo *flinfo, int argnum)
2385 {
2386         /*
2387          * can't return anything useful if we have no FmgrInfo or if its fn_expr
2388          * node has not been initialized
2389          */
2390         if (!flinfo || !flinfo->fn_expr)
2391                 return false;
2392
2393         return get_call_expr_arg_stable(flinfo->fn_expr, argnum);
2394 }
2395
2396 /*
2397  * Find out whether a specific function argument is constant for the
2398  * duration of a query, but working from the calling expression tree
2399  *
2400  * Returns false if information is not available
2401  */
2402 bool
2403 get_call_expr_arg_stable(Node *expr, int argnum)
2404 {
2405         List       *args;
2406         Node       *arg;
2407
2408         if (expr == NULL)
2409                 return false;
2410
2411         if (IsA(expr, FuncExpr))
2412                 args = ((FuncExpr *) expr)->args;
2413         else if (IsA(expr, OpExpr))
2414                 args = ((OpExpr *) expr)->args;
2415         else if (IsA(expr, DistinctExpr))
2416                 args = ((DistinctExpr *) expr)->args;
2417         else if (IsA(expr, ScalarArrayOpExpr))
2418                 args = ((ScalarArrayOpExpr *) expr)->args;
2419         else if (IsA(expr, ArrayCoerceExpr))
2420                 args = list_make1(((ArrayCoerceExpr *) expr)->arg);
2421         else if (IsA(expr, NullIfExpr))
2422                 args = ((NullIfExpr *) expr)->args;
2423         else if (IsA(expr, WindowFunc))
2424                 args = ((WindowFunc *) expr)->args;
2425         else
2426                 return false;
2427
2428         if (argnum < 0 || argnum >= list_length(args))
2429                 return false;
2430
2431         arg = (Node *) list_nth(args, argnum);
2432
2433         /*
2434          * Either a true Const or an external Param will have a value that doesn't
2435          * change during the execution of the query.  In future we might want to
2436          * consider other cases too, e.g. now().
2437          */
2438         if (IsA(arg, Const))
2439                 return true;
2440         if (IsA(arg, Param) &&
2441                 ((Param *) arg)->paramkind == PARAM_EXTERN)
2442                 return true;
2443
2444         return false;
2445 }
2446
2447 /*
2448  * Get the VARIADIC flag from the function invocation
2449  *
2450  * Returns false (the default assumption) if information is not available
2451  */
2452 bool
2453 get_fn_expr_variadic(FmgrInfo *flinfo)
2454 {
2455         Node       *expr;
2456
2457         /*
2458          * can't return anything useful if we have no FmgrInfo or if its fn_expr
2459          * node has not been initialized
2460          */
2461         if (!flinfo || !flinfo->fn_expr)
2462                 return false;
2463
2464         expr = flinfo->fn_expr;
2465
2466         if (IsA(expr, FuncExpr))
2467                 return ((FuncExpr *) expr)->funcvariadic;
2468         else
2469                 return false;
2470 }