PostgreSQL Source Code: src/include/funcapi.h File Reference (original) (raw)
Go to the source code of this file.
Macros | |
---|---|
#define | TupleGetDatum(_slot, _tuple) HeapTupleGetDatum(_tuple) |
#define | MAT_SRF_USE_EXPECTED_DESC 0x01 /* use expectedDesc as tupdesc. */ |
#define | MAT_SRF_BLESS |
#define | SRF_IS_FIRSTCALL() (fcinfo->flinfo->fn_extra == NULL) |
#define | SRF_FIRSTCALL_INIT() init_MultiFuncCall(fcinfo) |
#define | SRF_PERCALL_SETUP() per_MultiFuncCall(fcinfo) |
#define | SRF_RETURN_NEXT(_funcctx, _result) |
#define | SRF_RETURN_NEXT_NULL(_funcctx) |
#define | SRF_RETURN_DONE(_funcctx) |
Typedefs | |
---|---|
typedef struct AttInMetadata | AttInMetadata |
typedef struct FuncCallContext | FuncCallContext |
typedef enum TypeFuncClass | TypeFuncClass |
◆ MAT_SRF_BLESS
◆ MAT_SRF_USE_EXPECTED_DESC
#define MAT_SRF_USE_EXPECTED_DESC 0x01 /* use expectedDesc as tupdesc. */
◆ SRF_FIRSTCALL_INIT
◆ SRF_IS_FIRSTCALL
#define SRF_IS_FIRSTCALL | ( | ) | (fcinfo->flinfo->fn_extra == NULL) |
---|
◆ SRF_PERCALL_SETUP
◆ SRF_RETURN_DONE
| #define SRF_RETURN_DONE | ( | | _funcctx | ) | | ------------------------- | - | | --------- | - |
Value:
do { \
ReturnSetInfo *rsi; \
end_MultiFuncCall(fcinfo, _funcctx); \
} while (0)
Definition at line 328 of file funcapi.h.
◆ SRF_RETURN_NEXT
| #define SRF_RETURN_NEXT | ( | | _funcctx, | | ------------------------- | - | | ---------- | | | _result | | | | | ) | | | |
Value:
do { \
ReturnSetInfo *rsi; \
(_funcctx)->call_cntr++; \
} while (0)
#define PG_RETURN_DATUM(x)
Definition at line 310 of file funcapi.h.
◆ SRF_RETURN_NEXT_NULL
| #define SRF_RETURN_NEXT_NULL | ( | | _funcctx | ) | | ------------------------------- | - | | --------- | - |
Value:
do { \
ReturnSetInfo *rsi; \
(_funcctx)->call_cntr++; \
} while (0)
Definition at line 319 of file funcapi.h.
◆ TupleGetDatum
◆ AttInMetadata
◆ FuncCallContext
◆ TypeFuncClass
◆ TypeFuncClass
Enumerator |
---|
TYPEFUNC_SCALAR |
TYPEFUNC_COMPOSITE |
TYPEFUNC_COMPOSITE_DOMAIN |
TYPEFUNC_RECORD |
TYPEFUNC_OTHER |
Definition at line 146 of file funcapi.h.
147{
@ TYPEFUNC_COMPOSITE_DOMAIN
◆ BlessTupleDesc()
Definition at line 2260 of file execTuples.c.
2261{
2262 if (tupdesc->tdtypeid == RECORDOID &&
2265
2266 return tupdesc;
2267}
void assign_record_type_typmod(TupleDesc tupDesc)
References assign_record_type_typmod(), TupleDescData::tdtypeid, and TupleDescData::tdtypmod.
Referenced by aclexplode(), brin_metapage_info(), bt_page_items_bytea(), bt_page_items_internal(), exec_eval_datum(), ExecEvalWholeRowVar(), ExecInitExprRec(), ExecInitFunctionScan(), get_expr_result_type(), hash_bitmap_info(), hash_metapage_info(), hash_page_items(), hash_page_stats(), init_execution_state(), InitMaterializedSRF(), injection_points_stats_fixed(), pg_buffercache_numa_pages(), pg_buffercache_pages(), pg_get_catalog_foreign_keys(), pg_get_publication_tables(), pg_get_sequence_data(), pg_lock_status(), pg_prepared_xact(), pg_stat_file(), pg_stat_get_archiver(), pg_stat_get_backend_subxact(), pg_stat_get_replication_slot(), pg_stat_get_subscription_stats(), pg_stat_wal_build_tuple(), pg_stats_ext_mcvlist_items(), pg_visibility_tupdesc(), pg_walfile_name_offset(), pgstathashindex(), PLy_output_setup_record(), setup_firstcall(), ssl_extension_info(), test_enc_conversion(), test_predtest(), and TupleDescGetAttInMetadata().
◆ build_function_result_tupdesc_d()
Definition at line 1751 of file funcapi.c.
1755{
1758 int numargs;
1759 Oid *argtypes;
1760 char *argmodes;
1761 Datum *argnames = NULL;
1762 Oid *outargtypes;
1763 char **outargnames;
1764 int numoutargs;
1765 int nargnames;
1766 int i;
1767
1768
1771 return NULL;
1772
1773
1774
1775
1776
1777
1781 numargs < 0 ||
1784 elog(ERROR, "proallargtypes is not a 1-D Oid array or it contains nulls");
1788 ARR_DIMS(arr)[0] != numargs ||
1791 elog(ERROR, "proargmodes is not a 1-D char array of length %d or it contains nulls",
1792 numargs);
1795 {
1798 ARR_DIMS(arr)[0] != numargs ||
1801 elog(ERROR, "proargnames is not a 1-D text array of length %d or it contains nulls",
1802 numargs);
1804 Assert(nargnames == numargs);
1805 }
1806
1807
1808 if (numargs <= 0)
1809 return NULL;
1810
1811
1812 outargtypes = (Oid *) palloc(numargs * sizeof(Oid));
1813 outargnames = (char **) palloc(numargs * sizeof(char *));
1814 numoutargs = 0;
1815 for (i = 0; i < numargs; i++)
1816 {
1817 char *pname;
1818
1819 if (argmodes[i] == PROARGMODE_IN ||
1820 argmodes[i] == PROARGMODE_VARIADIC)
1821 continue;
1822 Assert(argmodes[i] == PROARGMODE_OUT ||
1823 argmodes[i] == PROARGMODE_INOUT ||
1824 argmodes[i] == PROARGMODE_TABLE);
1825 outargtypes[numoutargs] = argtypes[i];
1826 if (argnames)
1828 else
1829 pname = NULL;
1830 if (pname == NULL || pname[0] == '\0')
1831 {
1832
1833 pname = psprintf("column%d", numoutargs + 1);
1834 }
1835 outargnames[numoutargs] = pname;
1836 numoutargs++;
1837 }
1838
1839
1840
1841
1842
1843 if (numoutargs < 2 && prokind != PROKIND_PROCEDURE)
1844 return NULL;
1845
1847 for (i = 0; i < numoutargs; i++)
1848 {
1850 outargnames[i],
1851 outargtypes[i],
1852 -1,
1853 0);
1854 }
1855
1856 return desc;
1857}
#define DatumGetArrayTypeP(X)
void deconstruct_array_builtin(ArrayType *array, Oid elmtype, Datum **elemsp, bool **nullsp, int *nelemsp)
#define TextDatumGetCString(d)
Assert(PointerIsAligned(start, uint64))
static Datum PointerGetDatum(const void *X)
char * psprintf(const char *fmt,...)
TupleDesc CreateTemplateTupleDesc(int natts)
void TupleDescInitEntry(TupleDesc desc, AttrNumber attributeNumber, const char *attributeName, Oid oidtypeid, int32 typmod, int attdim)
References ARR_DATA_PTR, ARR_DIMS, ARR_ELEMTYPE, ARR_HASNULL, ARR_NDIM, Assert(), CreateTemplateTupleDesc(), DatumGetArrayTypeP, deconstruct_array_builtin(), elog, ERROR, i, palloc(), PointerGetDatum(), psprintf(), TextDatumGetCString, and TupleDescInitEntry().
Referenced by build_function_result_tupdesc_t(), and ProcedureCreate().
◆ build_function_result_tupdesc_t()
Definition at line 1705 of file funcapi.c.
1706{
1708 Datum proallargtypes;
1709 Datum proargmodes;
1710 Datum proargnames;
1711 bool isnull;
1712
1713
1714 if (procform->prorettype != RECORDOID)
1715 return NULL;
1716
1717
1718 if (heap_attisnull(procTuple, Anum_pg_proc_proallargtypes, NULL) ||
1719 heap_attisnull(procTuple, Anum_pg_proc_proargmodes, NULL))
1720 return NULL;
1721
1722
1724 Anum_pg_proc_proallargtypes);
1726 Anum_pg_proc_proargmodes);
1728 Anum_pg_proc_proargnames,
1729 &isnull);
1730 if (isnull)
1731 proargnames = PointerGetDatum(NULL);
1732
1734 proallargtypes,
1735 proargmodes,
1736 proargnames);
1737}
TupleDesc build_function_result_tupdesc_d(char prokind, Datum proallargtypes, Datum proargmodes, Datum proargnames)
bool heap_attisnull(HeapTuple tup, int attnum, TupleDesc tupleDesc)
static void * GETSTRUCT(const HeapTupleData *tuple)
FormData_pg_proc * Form_pg_proc
Datum SysCacheGetAttr(int cacheId, HeapTuple tup, AttrNumber attributeNumber, bool *isNull)
Datum SysCacheGetAttrNotNull(int cacheId, HeapTuple tup, AttrNumber attributeNumber)
References build_function_result_tupdesc_d(), GETSTRUCT(), heap_attisnull(), PointerGetDatum(), SysCacheGetAttr(), and SysCacheGetAttrNotNull().
Referenced by CallStmtResultDesc(), internal_get_result_type(), and ProcedureCreate().
◆ BuildTupleFromCStrings()
Definition at line 2324 of file execTuples.c.
2325{
2327 int natts = tupdesc->natts;
2329 bool *nulls;
2330 int i;
2332
2334 nulls = (bool *) palloc(natts * sizeof(bool));
2335
2336
2337
2338
2339
2340 for (i = 0; i < natts; i++)
2341 {
2343 {
2344
2350 nulls[i] = false;
2351 else
2352 nulls[i] = true;
2353 }
2354 else
2355 {
2356
2358 nulls[i] = true;
2359 }
2360 }
2361
2362
2363
2364
2366
2367
2368
2369
2370
2373
2374 return tuple;
2375}
static Datum values[MAXATTR]
Datum InputFunctionCall(FmgrInfo *flinfo, char *str, Oid typioparam, int32 typmod)
HeapTuple heap_form_tuple(TupleDesc tupleDescriptor, const Datum *values, const bool *isnull)
void pfree(void *pointer)
static CompactAttribute * TupleDescCompactAttr(TupleDesc tupdesc, int i)
References AttInMetadata::attinfuncs, AttInMetadata::attioparams, CompactAttribute::attisdropped, AttInMetadata::atttypmods, heap_form_tuple(), i, InputFunctionCall(), TupleDescData::natts, palloc(), pfree(), AttInMetadata::tupdesc, TupleDescCompactAttr(), and values.
Referenced by bt_metap(), bt_multi_page_stats(), bt_page_stats_internal(), build_pgstattuple_type(), build_tuplestore_recursively(), crosstab(), dblink_get_pkey(), get_crosstab_tuplestore(), libpqrcv_processTuples(), materializeResult(), pg_get_keywords(), pg_get_multixact_members(), pgp_armor_headers(), pgrowlocks(), pgstatindex_impl(), pltcl_build_tuple_result(), prs_process_call(), show_all_settings(), storeRow(), ts_process_call(), tt_process_call(), and xpath_table().
◆ end_MultiFuncCall()
◆ extract_variadic_args()
int extract_variadic_args | ( | FunctionCallInfo | fcinfo, |
---|---|---|---|
int | variadic_start, | ||
bool | convert_unknown, | ||
Datum ** | args, | ||
Oid ** | types, | ||
bool ** | nulls | ||
) |
Definition at line 2005 of file funcapi.c.
2008{
2010 Datum *args_res;
2011 bool *nulls_res;
2012 Oid *types_res;
2013 int nargs,
2014 i;
2015
2016 *args = NULL;
2018 *nulls = NULL;
2019
2020 if (variadic)
2021 {
2023 Oid element_type;
2024 bool typbyval;
2027
2029
2031 return -1;
2032
2035
2037 &typlen, &typbyval, &typalign);
2039 typalign, &args_res, &nulls_res,
2040 &nargs);
2041
2042
2043 types_res = (Oid *) palloc0(nargs * sizeof(Oid));
2044 for (i = 0; i < nargs; i++)
2045 types_res[i] = element_type;
2046 }
2047 else
2048 {
2049 nargs = PG_NARGS() - variadic_start;
2051 nulls_res = (bool *) palloc0(nargs * sizeof(bool));
2053 types_res = (Oid *) palloc0(nargs * sizeof(Oid));
2054
2055 for (i = 0; i < nargs; i++)
2056 {
2059 i + variadic_start);
2060
2061
2062
2063
2064
2065
2066
2067
2068 if (convert_unknown &&
2069 types_res[i] == UNKNOWNOID &&
2071 {
2072 types_res[i] = TEXTOID;
2073
2076 else
2077 args_res[i] =
2079 }
2080 else
2081 {
2082
2084 }
2085
2087 (convert_unknown && types_res[i] == UNKNOWNOID))
2089 (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
2090 errmsg("could not determine data type for argument %d",
2091 i + 1)));
2092 }
2093 }
2094
2095
2096 *args = args_res;
2097 *nulls = nulls_res;
2098 *types = types_res;
2099
2100 return nargs;
2101}
#define PG_GETARG_ARRAYTYPE_P(n)
void deconstruct_array(ArrayType *array, Oid elmtype, int elmlen, bool elmbyval, char elmalign, Datum **elemsp, bool **nullsp, int *nelemsp)
Datum array_in(PG_FUNCTION_ARGS)
#define CStringGetTextDatum(s)
#define OidIsValid(objectId)
int errcode(int sqlerrcode)
int errmsg(const char *fmt,...)
#define ereport(elevel,...)
bool get_fn_expr_arg_stable(FmgrInfo *flinfo, int argnum)
bool get_fn_expr_variadic(FmgrInfo *flinfo)
Oid get_fn_expr_argtype(FmgrInfo *flinfo, int argnum)
#define PG_GETARG_POINTER(n)
#define PG_GETARG_DATUM(n)
void get_typlenbyvalalign(Oid typid, int16 *typlen, bool *typbyval, char *typalign)
void * palloc0(Size size)
References generate_unaccent_rules::args, ARR_ELEMTYPE, array_in(), Assert(), CStringGetTextDatum, deconstruct_array(), ereport, errcode(), errmsg(), ERROR, FunctionCallInfoBaseData::flinfo, get_fn_expr_arg_stable(), get_fn_expr_argtype(), get_fn_expr_variadic(), get_typlenbyvalalign(), i, OidIsValid, palloc0(), PG_ARGISNULL, PG_GETARG_ARRAYTYPE_P, PG_GETARG_DATUM, PG_GETARG_POINTER, PG_NARGS, typalign, and types.
Referenced by json_build_array(), json_build_object(), jsonb_build_array(), jsonb_build_object(), and stats_fill_fcinfo_from_arg_pairs().
◆ get_call_result_type()
Definition at line 276 of file funcapi.c.
279{
283 resultTypeId,
284 resultTupleDesc);
285}
static TypeFuncClass internal_get_result_type(Oid funcid, Node *call_expr, ReturnSetInfo *rsinfo, Oid *resultTypeId, TupleDesc *resultTupleDesc)
References FunctionCallInfoBaseData::flinfo, FmgrInfo::fn_expr, FmgrInfo::fn_oid, internal_get_result_type(), and FunctionCallInfoBaseData::resultinfo.
Referenced by brin_metapage_info(), bt_metap(), bt_multi_page_stats(), bt_page_items_bytea(), bt_page_items_internal(), bt_page_stats_internal(), build_pgstattuple_type(), compute_function_hashkey(), copy_replication_slot(), crosstab(), get_record_type_from_query(), gin_leafpage_items(), gin_metapage_info(), gin_page_opaque_info(), gist_page_opaque_info(), hash_bitmap_info(), hash_metapage_info(), hash_page_items(), hash_page_stats(), heap_page_items(), heap_tuple_infomask_flags(), InitMaterializedSRF(), materializeResult(), page_header(), pg_backup_stop(), pg_buffercache_evict(), pg_buffercache_evict_all(), pg_buffercache_evict_relation(), pg_buffercache_numa_pages(), pg_buffercache_pages(), pg_buffercache_summary(), pg_control_checkpoint(), pg_control_init(), pg_control_recovery(), pg_control_system(), pg_create_logical_replication_slot(), pg_create_physical_replication_slot(), pg_get_catalog_foreign_keys(), pg_get_keywords(), pg_get_logical_snapshot_info(), pg_get_logical_snapshot_meta(), pg_get_multixact_members(), pg_get_object_address(), pg_get_wal_record_info(), pg_get_wal_summarizer_state(), pg_identify_object(), pg_identify_object_as_address(), pg_input_error_info(), pg_last_committed_xact(), pg_partition_tree(), pg_replication_slot_advance(), pg_sequence_parameters(), pg_split_walfile_name(), pg_stat_get_wal_receiver(), pg_stat_statements_info(), pg_stats_ext_mcvlist_items(), pg_timezone_abbrevs_abbrevs(), pg_timezone_abbrevs_zone(), pg_visibility_map_summary(), pg_xact_commit_timestamp_origin(), pgp_armor_headers(), pgstatginindex_internal(), pgstathashindex(), pgstatindex_impl(), pgstattuple_approx_internal(), plperl_return_next_internal(), plperl_sv_to_datum(), plpgsql_exec_function(), pltcl_func_handler(), PLy_exec_function(), prs_setup_firstcall(), setup_firstcall(), sql_compile_callback(), ssl_extension_info(), storeRow(), test_enc_conversion(), ts_setup_firstcall(), tsvector_unnest(), and tt_setup_firstcall().
◆ get_expr_result_tupdesc()
Definition at line 551 of file funcapi.c.
552{
555
557
560 return tupleDesc;
561
562 if (!noError)
563 {
565
566 if (exprTypeId != RECORDOID)
568 (errcode(ERRCODE_WRONG_OBJECT_TYPE),
569 errmsg("type %s is not composite",
571 else
573 (errcode(ERRCODE_WRONG_OBJECT_TYPE),
574 errmsg("record type has not been registered")));
575 }
576
577 return NULL;
578}
char * format_type_be(Oid type_oid)
TypeFuncClass get_expr_result_type(Node *expr, Oid *resultTypeId, TupleDesc *resultTupleDesc)
Oid exprType(const Node *expr)
References ereport, errcode(), errmsg(), ERROR, exprType(), format_type_be(), get_expr_result_type(), TYPEFUNC_COMPOSITE, and TYPEFUNC_COMPOSITE_DOMAIN.
Referenced by expandRecordVariable(), ExpandRowReference(), get_name_for_var_field(), get_rte_attribute_is_dropped(), ParseComplexProjection(), and process_function_rte_ref().
◆ get_expr_result_type()
Definition at line 299 of file funcapi.c.
302{
304
307 expr,
308 NULL,
309 resultTypeId,
310 resultTupleDesc);
311 else if (expr && IsA(expr, OpExpr))
313 expr,
314 NULL,
315 resultTypeId,
316 resultTupleDesc);
317 else if (expr && IsA(expr, RowExpr) &&
318 ((RowExpr *) expr)->row_typeid == RECORDOID)
319 {
320
325 *lcn;
326
329 forboth(lcc, rexpr->args, lcn, rexpr->colnames)
330 {
333
335 colname,
338 0);
341 i++;
342 }
343 if (resultTypeId)
344 *resultTypeId = rexpr->row_typeid;
345 if (resultTupleDesc)
348 }
349 else if (expr && IsA(expr, Const) &&
350 ((Const *) expr)->consttype == RECORDOID &&
351 !((Const *) expr)->constisnull)
352 {
353
354
355
356
357
359 Oid tupType;
361
365 if (resultTypeId)
366 *resultTypeId = tupType;
367 if (tupType != RECORDOID || tupTypmod >= 0)
368 {
369
370 if (resultTupleDesc)
372 tupTypmod);
374 }
375 else
376 {
377
378 if (resultTupleDesc)
379 *resultTupleDesc = NULL;
381 }
382 }
383 else
384 {
385
387 Oid base_typid;
388
389 if (resultTypeId)
390 *resultTypeId = typid;
391 if (resultTupleDesc)
392 *resultTupleDesc = NULL;
396 resultTupleDesc)
398 }
399
400 return result;
401}
TupleDesc BlessTupleDesc(TupleDesc tupdesc)
#define DatumGetHeapTupleHeader(X)
static TypeFuncClass get_type_func_class(Oid typid, Oid *base_typeid)
static int32 HeapTupleHeaderGetTypMod(const HeapTupleHeaderData *tup)
static Oid HeapTupleHeaderGetTypeId(const HeapTupleHeaderData *tup)
RegProcedure get_opcode(Oid opno)
int32 exprTypmod(const Node *expr)
Oid exprCollation(const Node *expr)
#define IsA(nodeptr, _type_)
static int list_length(const List *l)
#define forboth(cell1, list1, cell2, list2)
void TupleDescInitEntryCollation(TupleDesc desc, AttrNumber attributeNumber, Oid collationid)
TupleDesc lookup_rowtype_tupdesc_copy(Oid type_id, int32 typmod)
References RowExpr::args, Assert(), BlessTupleDesc(), CreateTemplateTupleDesc(), DatumGetHeapTupleHeader, exprCollation(), exprType(), exprTypmod(), forboth, get_opcode(), get_type_func_class(), HeapTupleHeaderGetTypeId(), HeapTupleHeaderGetTypMod(), i, internal_get_result_type(), IsA, lfirst, list_length(), lookup_rowtype_tupdesc_copy(), strVal, TupleDescInitEntry(), TupleDescInitEntryCollation(), TYPEFUNC_COMPOSITE, TYPEFUNC_COMPOSITE_DOMAIN, and TYPEFUNC_RECORD.
Referenced by addRangeTableEntryForFunction(), ExecInitFunctionScan(), expandRTE(), get_expr_result_tupdesc(), init_sexpr(), inline_function(), inline_set_returning_function(), and pull_up_constant_function().
◆ get_func_arg_info()
int get_func_arg_info | ( | HeapTuple | procTup, |
---|---|---|---|
Oid ** | p_argtypes, | ||
char *** | p_argnames, | ||
char ** | p_argmodes | ||
) |
Definition at line 1379 of file funcapi.c.
1381{
1383 Datum proallargtypes;
1384 Datum proargmodes;
1385 Datum proargnames;
1386 bool isNull;
1388 int numargs;
1390 int nelems;
1391 int i;
1392
1393
1395 Anum_pg_proc_proallargtypes,
1396 &isNull);
1397 if (!isNull)
1398 {
1399
1400
1401
1402
1403
1404
1408 numargs < 0 ||
1411 elog(ERROR, "proallargtypes is not a 1-D Oid array or it contains nulls");
1412 Assert(numargs >= procStruct->pronargs);
1413 *p_argtypes = (Oid *) palloc(numargs * sizeof(Oid));
1415 numargs * sizeof(Oid));
1416 }
1417 else
1418 {
1419
1420 numargs = procStruct->proargtypes.dim1;
1421 Assert(numargs == procStruct->pronargs);
1422 *p_argtypes = (Oid *) palloc(numargs * sizeof(Oid));
1423 memcpy(*p_argtypes, procStruct->proargtypes.values,
1424 numargs * sizeof(Oid));
1425 }
1426
1427
1429 Anum_pg_proc_proargnames,
1430 &isNull);
1431 if (isNull)
1432 *p_argnames = NULL;
1433 else
1434 {
1436 &elems, NULL, &nelems);
1437 if (nelems != numargs)
1438 elog(ERROR, "proargnames must have the same number of elements as the function has arguments");
1439 *p_argnames = (char **) palloc(sizeof(char *) * numargs);
1440 for (i = 0; i < numargs; i++)
1442 }
1443
1444
1446 Anum_pg_proc_proargmodes,
1447 &isNull);
1448 if (isNull)
1449 *p_argmodes = NULL;
1450 else
1451 {
1454 ARR_DIMS(arr)[0] != numargs ||
1457 elog(ERROR, "proargmodes is not a 1-D char array of length %d or it contains nulls",
1458 numargs);
1459 *p_argmodes = (char *) palloc(numargs * sizeof(char));
1461 numargs * sizeof(char));
1462 }
1463
1464 return numargs;
1465}
References ARR_DATA_PTR, ARR_DIMS, ARR_ELEMTYPE, ARR_HASNULL, ARR_NDIM, Assert(), DatumGetArrayTypeP, deconstruct_array_builtin(), elog, ERROR, GETSTRUCT(), i, palloc(), SysCacheGetAttr(), and TextDatumGetCString.
Referenced by make_callstmt_target(), MatchNamedCall(), pg_get_function_arg_default(), plperl_validator(), plpgsql_compile_callback(), plpgsql_validator(), plsample_func_handler(), PLy_procedure_create(), print_function_arguments(), and print_function_sqlbody().
◆ get_func_input_arg_names()
int get_func_input_arg_names | ( | Datum | proargnames, |
---|---|---|---|
Datum | proargmodes, | ||
char *** | arg_names | ||
) |
Definition at line 1522 of file funcapi.c.
1524{
1526 int numargs;
1527 Datum *argnames;
1528 char *argmodes;
1529 char **inargnames;
1530 int numinargs;
1531 int i;
1532
1533
1535 {
1536 *arg_names = NULL;
1537 return 0;
1538 }
1539
1540
1541
1542
1543
1544
1549 elog(ERROR, "proargnames is not a 1-D text array or it contains nulls");
1552 {
1555 ARR_DIMS(arr)[0] != numargs ||
1558 elog(ERROR, "proargmodes is not a 1-D char array of length %d or it contains nulls",
1559 numargs);
1561 }
1562 else
1563 argmodes = NULL;
1564
1565
1566 if (numargs <= 0)
1567 {
1568 *arg_names = NULL;
1569 return 0;
1570 }
1571
1572
1573 inargnames = (char **) palloc(numargs * sizeof(char *));
1574 numinargs = 0;
1575 for (i = 0; i < numargs; i++)
1576 {
1577 if (argmodes == NULL ||
1578 argmodes[i] == PROARGMODE_IN ||
1579 argmodes[i] == PROARGMODE_INOUT ||
1580 argmodes[i] == PROARGMODE_VARIADIC)
1581 {
1583
1584 if (pname[0] != '\0')
1585 inargnames[numinargs] = pname;
1586 else
1587 inargnames[numinargs] = NULL;
1588 numinargs++;
1589 }
1590 }
1591
1592 *arg_names = inargnames;
1593 return numinargs;
1594}
References ARR_DATA_PTR, ARR_DIMS, ARR_ELEMTYPE, ARR_HASNULL, ARR_NDIM, DatumGetArrayTypeP, deconstruct_array_builtin(), elog, ERROR, i, palloc(), PointerGetDatum(), and TextDatumGetCString.
Referenced by prepare_sql_fn_parse_info(), and ProcedureCreate().
◆ get_func_result_name()
char * get_func_result_name | ( | Oid | functionId | ) |
---|
Definition at line 1607 of file funcapi.c.
1608{
1609 char *result;
1611 Datum proargmodes;
1612 Datum proargnames;
1614 int numargs;
1615 char *argmodes;
1616 Datum *argnames;
1617 int numoutargs;
1618 int nargnames;
1619 int i;
1620
1621
1624 elog(ERROR, "cache lookup failed for function %u", functionId);
1625
1626
1627 if (heap_attisnull(procTuple, Anum_pg_proc_proargmodes, NULL) ||
1628 heap_attisnull(procTuple, Anum_pg_proc_proargnames, NULL))
1629 result = NULL;
1630 else
1631 {
1632
1634 Anum_pg_proc_proargmodes);
1636 Anum_pg_proc_proargnames);
1637
1638
1639
1640
1641
1642
1643
1647 numargs < 0 ||
1650 elog(ERROR, "proargmodes is not a 1-D char array or it contains nulls");
1654 ARR_DIMS(arr)[0] != numargs ||
1657 elog(ERROR, "proargnames is not a 1-D text array of length %d or it contains nulls",
1658 numargs);
1660 Assert(nargnames == numargs);
1661
1662
1663 result = NULL;
1664 numoutargs = 0;
1665 for (i = 0; i < numargs; i++)
1666 {
1667 if (argmodes[i] == PROARGMODE_IN ||
1668 argmodes[i] == PROARGMODE_VARIADIC)
1669 continue;
1670 Assert(argmodes[i] == PROARGMODE_OUT ||
1671 argmodes[i] == PROARGMODE_INOUT ||
1672 argmodes[i] == PROARGMODE_TABLE);
1673 if (++numoutargs > 1)
1674 {
1675
1676 result = NULL;
1677 break;
1678 }
1680 if (result == NULL || result[0] == '\0')
1681 {
1682
1683 result = NULL;
1684 break;
1685 }
1686 }
1687 }
1688
1690
1691 return result;
1692}
#define HeapTupleIsValid(tuple)
static Datum ObjectIdGetDatum(Oid X)
void ReleaseSysCache(HeapTuple tuple)
HeapTuple SearchSysCache1(int cacheId, Datum key1)
References ARR_DATA_PTR, ARR_DIMS, ARR_ELEMTYPE, ARR_HASNULL, ARR_NDIM, Assert(), DatumGetArrayTypeP, deconstruct_array_builtin(), elog, ERROR, heap_attisnull(), HeapTupleIsValid, i, ObjectIdGetDatum(), ReleaseSysCache(), SearchSysCache1(), SysCacheGetAttrNotNull(), and TextDatumGetCString.
Referenced by chooseScalarFunctionAlias().
◆ get_func_result_type()
◆ get_func_trftypes()
int get_func_trftypes | ( | HeapTuple | procTup, |
---|---|---|---|
Oid ** | p_trftypes | ||
) |
Definition at line 1475 of file funcapi.c.
1477{
1478 Datum protrftypes;
1480 int nelems;
1481 bool isNull;
1482
1484 Anum_pg_proc_protrftypes,
1485 &isNull);
1486 if (!isNull)
1487 {
1488
1489
1490
1491
1492
1493
1497 nelems < 0 ||
1500 elog(ERROR, "protrftypes is not a 1-D Oid array or it contains nulls");
1501 *p_trftypes = (Oid *) palloc(nelems * sizeof(Oid));
1503 nelems * sizeof(Oid));
1504
1505 return nelems;
1506 }
1507 else
1508 return 0;
1509}
References ARR_DATA_PTR, ARR_DIMS, ARR_ELEMTYPE, ARR_HASNULL, ARR_NDIM, DatumGetArrayTypeP, elog, ERROR, palloc(), and SysCacheGetAttr().
Referenced by print_function_trftypes().
◆ HeapTupleGetDatum()
Definition at line 230 of file funcapi.h.
231{
233}
Datum HeapTupleHeaderGetDatum(HeapTupleHeader tuple)
References HeapTupleHeaderGetDatum(), and HeapTupleData::t_data.
Referenced by aclexplode(), brin_metapage_info(), bt_metap(), bt_multi_page_stats(), bt_page_print_tuples(), bt_page_stats_internal(), build_pgstattuple_type(), copy_replication_slot(), dblink_get_pkey(), exec_eval_datum(), ExecEvalConvertRowtype(), ExecEvalFieldStoreForm(), ExecEvalRow(), gin_leafpage_items(), gin_metapage_info(), gin_page_opaque_info(), gist_page_opaque_info(), hash_bitmap_info(), hash_metapage_info(), hash_page_items(), hash_page_stats(), heap_page_items(), heap_tuple_infomask_flags(), hstore_each(), hstore_populate_record(), injection_points_stats_fixed(), page_header(), pg_backup_stop(), pg_buffercache_evict(), pg_buffercache_evict_all(), pg_buffercache_evict_relation(), pg_buffercache_numa_pages(), pg_buffercache_pages(), pg_buffercache_summary(), pg_control_checkpoint(), pg_control_init(), pg_control_recovery(), pg_control_system(), pg_create_logical_replication_slot(), pg_create_physical_replication_slot(), pg_get_catalog_foreign_keys(), pg_get_keywords(), pg_get_logical_snapshot_info(), pg_get_logical_snapshot_meta(), pg_get_multixact_members(), pg_get_object_address(), pg_get_publication_tables(), pg_get_sequence_data(), pg_get_wal_record_info(), pg_get_wal_summarizer_state(), pg_identify_object(), pg_identify_object_as_address(), pg_input_error_info(), pg_last_committed_xact(), pg_lock_status(), pg_partition_tree(), pg_prepared_xact(), pg_replication_slot_advance(), pg_sequence_parameters(), pg_split_walfile_name(), pg_stat_file(), pg_stat_get_archiver(), pg_stat_get_backend_subxact(), pg_stat_get_replication_slot(), pg_stat_get_subscription_stats(), pg_stat_get_wal_receiver(), pg_stat_statements_info(), pg_stat_wal_build_tuple(), pg_stats_ext_mcvlist_items(), pg_timezone_abbrevs_abbrevs(), pg_timezone_abbrevs_zone(), pg_visibility(), pg_visibility_map(), pg_visibility_map_rel(), pg_visibility_map_summary(), pg_visibility_rel(), pg_walfile_name_offset(), pg_xact_commit_timestamp_origin(), pgp_armor_headers(), pgstatginindex_internal(), pgstathashindex(), pgstatindex_impl(), pgstattuple_approx_internal(), plperl_hash_to_datum(), plperl_return_next_internal(), pltcl_build_tuple_result(), pltcl_func_handler(), prs_process_call(), show_all_settings(), ssl_extension_info(), test_enc_conversion(), test_predtest(), ts_process_call(), tsvector_unnest(), and tt_process_call().
◆ HeapTupleHeaderGetDatum()
Definition at line 2413 of file execTuples.c.
2414{
2417
2418
2421
2422
2425
2426
2429 tupDesc);
2430
2432
2433 return result;
2434}
Datum toast_flatten_tuple_to_datum(HeapTupleHeader tup, uint32 tup_len, TupleDesc tupleDesc)
static uint32 HeapTupleHeaderGetDatumLength(const HeapTupleHeaderData *tup)
#define HeapTupleHeaderHasExternal(tup)
#define ReleaseTupleDesc(tupdesc)
TupleDesc lookup_rowtype_tupdesc(Oid type_id, int32 typmod)
References HeapTupleHeaderGetDatumLength(), HeapTupleHeaderGetTypeId(), HeapTupleHeaderGetTypMod(), HeapTupleHeaderHasExternal, lookup_rowtype_tupdesc(), PointerGetDatum(), ReleaseTupleDesc, and toast_flatten_tuple_to_datum().
Referenced by HeapTupleGetDatum(), populate_composite(), and populate_recordset_record().
◆ init_MultiFuncCall()
Definition at line 133 of file funcapi.c.
134{
136
137
138
139
140 if (fcinfo->resultinfo == NULL || (fcinfo->resultinfo, ReturnSetInfo))
142 (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
143 errmsg("set-valued function called in context that cannot accept a set")));
144
145 if (fcinfo->flinfo->fn_extra == NULL)
146 {
147
148
149
152
153
154
155
157 "SRF multi-call context",
159
160
161
162
166
167
168
169
176
177
178
179
180 fcinfo->flinfo->fn_extra = retval;
181
182
183
184
185
189 }
190 else
191 {
192
193 elog(ERROR, "init_MultiFuncCall cannot be called more than once");
194
195
196 retval = NULL;
197 }
198
199 return retval;
200}
void RegisterExprContextCallback(ExprContext *econtext, ExprContextCallbackFunction function, Datum arg)
void * MemoryContextAllocZero(MemoryContext context, Size size)
#define AllocSetContextCreate
#define ALLOCSET_SMALL_SIZES
AttInMetadata * attinmeta
MemoryContext multi_call_memory_ctx
References ALLOCSET_SMALL_SIZES, AllocSetContextCreate, FuncCallContext::attinmeta, FuncCallContext::call_cntr, ReturnSetInfo::econtext, elog, ereport, errcode(), errmsg(), ERROR, IsA, FuncCallContext::max_calls, MemoryContextAllocZero(), FuncCallContext::multi_call_memory_ctx, PointerGetDatum(), RegisterExprContextCallback(), shutdown_MultiFuncCall(), FuncCallContext::tuple_desc, and FuncCallContext::user_fctx.
◆ InitMaterializedSRF()
Definition at line 76 of file funcapi.c.
77{
78 bool random_access;
82 per_query_ctx;
84
85
88 (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
89 errmsg("set-valued function called in context that cannot accept a set")));
93 (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
94 errmsg("materialize mode required, but it is not allowed in this context")));
95
96
97
98
99
102
103
106 else
107 {
109 elog(ERROR, "return type must be a row type");
110 }
111
112
115
117
121 rsinfo->setDesc = stored_tupdesc;
123}
@ SFRM_Materialize_Random
TypeFuncClass get_call_result_type(FunctionCallInfo fcinfo, Oid *resultTypeId, TupleDesc *resultTupleDesc)
#define MAT_SRF_USE_EXPECTED_DESC
if(TABLE==NULL||TABLE_index==NULL)
static MemoryContext MemoryContextSwitchTo(MemoryContext context)
MemoryContext ecxt_per_query_memory
SetFunctionReturnMode returnMode
Tuplestorestate * setResult
TupleDesc CreateTupleDescCopy(TupleDesc tupdesc)
Tuplestorestate * tuplestore_begin_heap(bool randomAccess, bool interXact, int maxKBytes)
References ReturnSetInfo::allowedModes, BlessTupleDesc(), CreateTupleDescCopy(), ReturnSetInfo::econtext, ExprContext::ecxt_per_query_memory, elog, ereport, errcode(), errmsg(), ERROR, ReturnSetInfo::expectedDesc, get_call_result_type(), if(), IsA, MAT_SRF_BLESS, MAT_SRF_USE_EXPECTED_DESC, MemoryContextSwitchTo(), FunctionCallInfoBaseData::resultinfo, ReturnSetInfo::returnMode, ReturnSetInfo::setDesc, ReturnSetInfo::setResult, SFRM_Materialize, SFRM_Materialize_Random, tuplestore_begin_heap(), TYPEFUNC_COMPOSITE, and work_mem.
Referenced by brin_page_items(), dblink_get_notify(), each_worker(), each_worker_jsonb(), elements_worker(), elements_worker_jsonb(), get_altertable_subcmdinfo(), GetWALRecordsInfo(), gist_page_items(), gist_page_items_bytea(), pg_available_extension_versions(), pg_available_extensions(), pg_available_wal_summaries(), pg_config(), pg_cursor(), pg_event_trigger_ddl_commands(), pg_event_trigger_dropped_objects(), pg_extension_update_paths(), pg_get_aios(), pg_get_backend_memory_contexts(), pg_get_loaded_modules(), pg_get_replication_slots(), pg_get_shmem_allocations(), pg_get_shmem_allocations_numa(), pg_get_wait_events(), pg_get_wal_block_info(), pg_hba_file_rules(), pg_ident_file_mappings(), pg_logical_slot_get_changes_guts(), pg_ls_dir(), pg_ls_dir_files(), pg_options_to_table(), pg_prepared_statement(), pg_show_replication_origin_status(), pg_stat_get_activity(), pg_stat_get_backend_io(), pg_stat_get_io(), pg_stat_get_progress_info(), pg_stat_get_recovery_prefetch(), pg_stat_get_slru(), pg_stat_get_subscription(), pg_stat_get_wal_senders(), pg_stat_statements_internal(), pg_tablespace_databases(), pg_wal_summary_contents(), pgrowlocks(), postgres_fdw_get_connections_internal(), show_all_file_settings(), text_to_table(), verify_heapam(), and xpath_table().
◆ per_MultiFuncCall()
Definition at line 208 of file funcapi.c.
209{
211
212 return retval;
213}
◆ RelationNameGetTupleDesc()
TupleDesc RelationNameGetTupleDesc | ( | const char * | relname | ) |
---|
Definition at line 1870 of file funcapi.c.
1871{
1875 List *relname_list;
1876
1877
1883
1884 return tupdesc;
1885}
RangeVar * makeRangeVarFromNameList(const List *names)
List * stringToQualifiedNameList(const char *string, Node *escontext)
#define RelationGetDescr(relation)
void relation_close(Relation relation, LOCKMODE lockmode)
Relation relation_openrv(const RangeVar *relation, LOCKMODE lockmode)
References AccessShareLock, CreateTupleDescCopy(), makeRangeVarFromNameList(), relation_close(), relation_openrv(), RelationGetDescr, relname, and stringToQualifiedNameList().
◆ resolve_polymorphic_argtypes()
bool resolve_polymorphic_argtypes | ( | int | numargs, |
---|---|---|---|
Oid * | argtypes, | ||
char * | argmodes, | ||
Node * | call_expr | ||
) |
Definition at line 1064 of file funcapi.c.
1066{
1067 bool have_polymorphic_result = false;
1068 bool have_anyelement_result = false;
1069 bool have_anyarray_result = false;
1070 bool have_anyrange_result = false;
1071 bool have_anymultirange_result = false;
1072 bool have_anycompatible_result = false;
1073 bool have_anycompatible_array_result = false;
1074 bool have_anycompatible_range_result = false;
1075 bool have_anycompatible_multirange_result = false;
1078 int inargno;
1079 int i;
1080
1081
1082
1083
1084
1085
1086 memset(&poly_actuals, 0, sizeof(poly_actuals));
1087 memset(&anyc_actuals, 0, sizeof(anyc_actuals));
1088 inargno = 0;
1089 for (i = 0; i < numargs; i++)
1090 {
1091 char argmode = argmodes ? argmodes[i] : PROARGMODE_IN;
1092
1093 switch (argtypes[i])
1094 {
1095 case ANYELEMENTOID:
1096 case ANYNONARRAYOID:
1097 case ANYENUMOID:
1098 if (argmode == PROARGMODE_OUT || argmode == PROARGMODE_TABLE)
1099 {
1100 have_polymorphic_result = true;
1101 have_anyelement_result = true;
1102 }
1103 else
1104 {
1106 {
1110 return false;
1111 }
1113 }
1114 break;
1115 case ANYARRAYOID:
1116 if (argmode == PROARGMODE_OUT || argmode == PROARGMODE_TABLE)
1117 {
1118 have_polymorphic_result = true;
1119 have_anyarray_result = true;
1120 }
1121 else
1122 {
1124 {
1128 return false;
1129 }
1131 }
1132 break;
1133 case ANYRANGEOID:
1134 if (argmode == PROARGMODE_OUT || argmode == PROARGMODE_TABLE)
1135 {
1136 have_polymorphic_result = true;
1137 have_anyrange_result = true;
1138 }
1139 else
1140 {
1142 {
1146 return false;
1147 }
1149 }
1150 break;
1151 case ANYMULTIRANGEOID:
1152 if (argmode == PROARGMODE_OUT || argmode == PROARGMODE_TABLE)
1153 {
1154 have_polymorphic_result = true;
1155 have_anymultirange_result = true;
1156 }
1157 else
1158 {
1160 {
1164 return false;
1165 }
1167 }
1168 break;
1169 case ANYCOMPATIBLEOID:
1170 case ANYCOMPATIBLENONARRAYOID:
1171 if (argmode == PROARGMODE_OUT || argmode == PROARGMODE_TABLE)
1172 {
1173 have_polymorphic_result = true;
1174 have_anycompatible_result = true;
1175 }
1176 else
1177 {
1179 {
1183 return false;
1184 }
1186 }
1187 break;
1188 case ANYCOMPATIBLEARRAYOID:
1189 if (argmode == PROARGMODE_OUT || argmode == PROARGMODE_TABLE)
1190 {
1191 have_polymorphic_result = true;
1192 have_anycompatible_array_result = true;
1193 }
1194 else
1195 {
1197 {
1201 return false;
1202 }
1204 }
1205 break;
1206 case ANYCOMPATIBLERANGEOID:
1207 if (argmode == PROARGMODE_OUT || argmode == PROARGMODE_TABLE)
1208 {
1209 have_polymorphic_result = true;
1210 have_anycompatible_range_result = true;
1211 }
1212 else
1213 {
1215 {
1219 return false;
1220 }
1222 }
1223 break;
1224 case ANYCOMPATIBLEMULTIRANGEOID:
1225 if (argmode == PROARGMODE_OUT || argmode == PROARGMODE_TABLE)
1226 {
1227 have_polymorphic_result = true;
1228 have_anycompatible_multirange_result = true;
1229 }
1230 else
1231 {
1233 {
1237 return false;
1238 }
1240 }
1241 break;
1242 default:
1243 break;
1244 }
1245 if (argmode != PROARGMODE_OUT && argmode != PROARGMODE_TABLE)
1246 inargno++;
1247 }
1248
1249
1250 if (!have_polymorphic_result)
1251 return true;
1252
1253
1256
1259
1262
1265
1268
1271
1274
1277
1278
1279 for (i = 0; i < numargs; i++)
1280 {
1281 switch (argtypes[i])
1282 {
1283 case ANYELEMENTOID:
1284 case ANYNONARRAYOID:
1285 case ANYENUMOID:
1287 break;
1288 case ANYARRAYOID:
1290 break;
1291 case ANYRANGEOID:
1293 break;
1294 case ANYMULTIRANGEOID:
1296 break;
1297 case ANYCOMPATIBLEOID:
1298 case ANYCOMPATIBLENONARRAYOID:
1300 break;
1301 case ANYCOMPATIBLEARRAYOID:
1303 break;
1304 case ANYCOMPATIBLERANGEOID:
1306 break;
1307 case ANYCOMPATIBLEMULTIRANGEOID:
1309 break;
1310 default:
1311 break;
1312 }
1313 }
1314
1315 return true;
1316}
Oid get_call_expr_argtype(Node *expr, int argnum)
static void resolve_anyelement_from_others(polymorphic_actuals *actuals)
static void resolve_anyrange_from_others(polymorphic_actuals *actuals)
static void resolve_anymultirange_from_others(polymorphic_actuals *actuals)
static void resolve_anyarray_from_others(polymorphic_actuals *actuals)
References polymorphic_actuals::anyarray_type, polymorphic_actuals::anyelement_type, polymorphic_actuals::anymultirange_type, polymorphic_actuals::anyrange_type, get_call_expr_argtype(), i, OidIsValid, resolve_anyarray_from_others(), resolve_anyelement_from_others(), resolve_anymultirange_from_others(), and resolve_anyrange_from_others().
Referenced by cfunc_resolve_polymorphic_argtypes().
◆ TupleDescGetAttInMetadata()
Definition at line 2275 of file execTuples.c.
2276{
2277 int natts = tupdesc->natts;
2278 int i;
2279 Oid atttypeid;
2280 Oid attinfuncid;
2282 Oid *attioparams;
2283 int32 *atttypmods;
2285
2287
2288
2290
2291
2292
2293
2295 attioparams = (Oid *) palloc0(natts * sizeof(Oid));
2297
2298 for (i = 0; i < natts; i++)
2299 {
2301
2302
2303 if (!att->attisdropped)
2304 {
2305 atttypeid = att->atttypid;
2307 fmgr_info(attinfuncid, &attinfuncinfo[i]);
2308 atttypmods[i] = att->atttypmod;
2309 }
2310 }
2311 attinmeta->attinfuncs = attinfuncinfo;
2314
2315 return attinmeta;
2316}
void fmgr_info(Oid functionId, FmgrInfo *finfo)
void getTypeInputInfo(Oid type, Oid *typInput, Oid *typIOParam)
FormData_pg_attribute * Form_pg_attribute
static FormData_pg_attribute * TupleDescAttr(TupleDesc tupdesc, int i)
References AttInMetadata::attinfuncs, AttInMetadata::attioparams, AttInMetadata::atttypmods, BlessTupleDesc(), fmgr_info(), getTypeInputInfo(), i, TupleDescData::natts, palloc(), palloc0(), AttInMetadata::tupdesc, and TupleDescAttr().
Referenced by bt_metap(), bt_multi_page_stats(), bt_page_stats_internal(), build_pgstattuple_type(), connectby_text(), connectby_text_serial(), create_foreign_modify(), crosstab(), dblink_get_pkey(), get_crosstab_tuplestore(), hash_page_items(), libpqrcv_processTuples(), materializeResult(), pg_get_keywords(), pg_get_multixact_members(), pg_stats_ext_mcvlist_items(), pgp_armor_headers(), pgrowlocks(), pgstatindex_impl(), pltcl_build_tuple_result(), pltcl_func_handler(), pltcl_init_tuple_store(), postgresAcquireSampleRowsFunc(), postgresBeginDirectModify(), postgresBeginForeignScan(), prs_setup_firstcall(), show_all_settings(), storeRow(), ts_setup_firstcall(), tt_setup_firstcall(), and xpath_table().
◆ TypeGetTupleDesc()
Definition at line 1903 of file funcapi.c.
1904{
1905 Oid base_typeoid;
1908
1909
1910
1911
1912
1913
1914
1916 {
1917
1919
1920 if (colaliases != NIL)
1921 {
1922 int natts = tupdesc->natts;
1923 int varattno;
1924
1925
1928 (errcode(ERRCODE_DATATYPE_MISMATCH),
1929 errmsg("number of aliases does not match number of columns")));
1930
1931
1932 for (varattno = 0; varattno < natts; varattno++)
1933 {
1936
1937 if (label != NULL)
1939 }
1940
1941
1942 tupdesc->tdtypeid = RECORDOID;
1944 }
1945 }
1947 {
1948
1950
1951
1952 if (colaliases == NIL)
1954 (errcode(ERRCODE_DATATYPE_MISMATCH),
1955 errmsg("no column alias was provided")));
1956
1957
1960 (errcode(ERRCODE_DATATYPE_MISMATCH),
1961 errmsg("number of aliases does not match number of columns")));
1962
1963
1965
1970 typeoid,
1971 -1,
1972 0);
1973 }
1975 {
1976
1978 (errcode(ERRCODE_DATATYPE_MISMATCH),
1979 errmsg("could not determine row description for function returning record")));
1980 }
1981 else
1982 {
1983
1984 elog(ERROR, "function in FROM has unsupported return type");
1985 }
1986
1987 return tupdesc;
1988}
void namestrcpy(Name name, const char *str)
static void * list_nth(const List *list, int n)
References attname, CreateTemplateTupleDesc(), elog, ereport, errcode(), errmsg(), ERROR, get_type_func_class(), label, linitial, list_length(), list_nth(), lookup_rowtype_tupdesc_copy(), namestrcpy(), TupleDescData::natts, NIL, strVal, TupleDescData::tdtypeid, TupleDescData::tdtypmod, TupleDescAttr(), TupleDescInitEntry(), TYPEFUNC_COMPOSITE, TYPEFUNC_RECORD, and TYPEFUNC_SCALAR.