PostgreSQL Source Code git master
Loading...
Searching...
No Matches
tupdesc.c File Reference
#include "postgres.h"
#include "access/htup_details.h"
#include "access/toast_compression.h"
#include "access/tupdesc_details.h"
#include "catalog/catalog.h"
#include "catalog/pg_collation.h"
#include "catalog/pg_type.h"
#include "common/hashfn.h"
#include "utils/builtins.h"
#include "utils/datum.h"
#include "utils/resowner.h"
#include "utils/syscache.h"
Include dependency graph for tupdesc.c:

Go to the source code of this file.

Functions

static void ResOwnerReleaseTupleDesc (Datum res)
 
static charResOwnerPrintTupleDesc (Datum res)
 
static void ResourceOwnerRememberTupleDesc (ResourceOwner owner, TupleDesc tupdesc)
 
static void ResourceOwnerForgetTupleDesc (ResourceOwner owner, TupleDesc tupdesc)
 
static void populate_compact_attribute_internal (Form_pg_attribute src, CompactAttribute *dst)
 
void populate_compact_attribute (TupleDesc tupdesc, int attnum)
 
void verify_compact_attribute (TupleDesc tupdesc, int attnum)
 
TupleDesc CreateTemplateTupleDesc (int natts)
 
TupleDesc CreateTupleDesc (int natts, Form_pg_attribute *attrs)
 
TupleDesc CreateTupleDescCopy (TupleDesc tupdesc)
 
TupleDesc CreateTupleDescTruncatedCopy (TupleDesc tupdesc, int natts)
 
TupleDesc CreateTupleDescCopyConstr (TupleDesc tupdesc)
 
void TupleDescCopy (TupleDesc dst, TupleDesc src)
 
void TupleDescCopyEntry (TupleDesc dst, AttrNumber dstAttno, TupleDesc src, AttrNumber srcAttno)
 
void FreeTupleDesc (TupleDesc tupdesc)
 
void IncrTupleDescRefCount (TupleDesc tupdesc)
 
void DecrTupleDescRefCount (TupleDesc tupdesc)
 
bool equalTupleDescs (TupleDesc tupdesc1, TupleDesc tupdesc2)
 
bool equalRowTypes (TupleDesc tupdesc1, TupleDesc tupdesc2)
 
uint32 hashRowType (TupleDesc desc)
 
void TupleDescInitEntry (TupleDesc desc, AttrNumber attributeNumber, const char *attributeName, Oid oidtypeid, int32 typmod, int attdim)
 
void TupleDescInitBuiltinEntry (TupleDesc desc, AttrNumber attributeNumber, const char *attributeName, Oid oidtypeid, int32 typmod, int attdim)
 
void TupleDescInitEntryCollation (TupleDesc desc, AttrNumber attributeNumber, Oid collationid)
 
TupleDesc BuildDescFromLists (const List *names, const List *types, const List *typmods, const List *collations)
 
NodeTupleDescGetDefault (TupleDesc tupdesc, AttrNumber attnum)
 

Variables

static const ResourceOwnerDesc tupdesc_resowner_desc
 

Function Documentation

◆ BuildDescFromLists()

TupleDesc BuildDescFromLists ( const List names,
const List types,
const List typmods,
const List collations 
)

Definition at line 1034 of file tupdesc.c.

1035{
1036 int natts;
1038 ListCell *l1;
1039 ListCell *l2;
1040 ListCell *l3;
1041 ListCell *l4;
1042 TupleDesc desc;
1043
1044 natts = list_length(names);
1045 Assert(natts == list_length(types));
1046 Assert(natts == list_length(typmods));
1047 Assert(natts == list_length(collations));
1048
1049 /*
1050 * allocate a new tuple descriptor
1051 */
1052 desc = CreateTemplateTupleDesc(natts);
1053
1054 attnum = 0;
1055 forfour(l1, names, l2, types, l3, typmods, l4, collations)
1056 {
1057 char *attname = strVal(lfirst(l1));
1058 Oid atttypid = lfirst_oid(l2);
1059 int32 atttypmod = lfirst_int(l3);
1060 Oid attcollation = lfirst_oid(l4);
1061
1062 attnum++;
1063
1064 TupleDescInitEntry(desc, attnum, attname, atttypid, atttypmod, 0);
1065 TupleDescInitEntryCollation(desc, attnum, attcollation);
1066 }
1067
1068 return desc;
1069}
int16 AttrNumber
Definition attnum.h:21
#define Assert(condition)
Definition c.h:873
int32_t int32
Definition c.h:542
struct typedefs * types
Definition ecpg.c:30
NameData attname
int16 attnum
#define lfirst(lc)
Definition pg_list.h:172
static int list_length(const List *l)
Definition pg_list.h:152
#define lfirst_int(lc)
Definition pg_list.h:173
#define forfour(cell1, list1, cell2, list2, cell3, list3, cell4, list4)
Definition pg_list.h:575
#define lfirst_oid(lc)
Definition pg_list.h:174
unsigned int Oid
static int fb(int x)
TupleDesc CreateTemplateTupleDesc(int natts)
Definition tupdesc.c:165
void TupleDescInitEntryCollation(TupleDesc desc, AttrNumber attributeNumber, Oid collationid)
Definition tupdesc.c:1009
void TupleDescInitEntry(TupleDesc desc, AttrNumber attributeNumber, const char *attributeName, Oid oidtypeid, int32 typmod, int attdim)
Definition tupdesc.c:825
#define strVal(v)
Definition value.h:82

References Assert, attname, attnum, CreateTemplateTupleDesc(), fb(), forfour, lfirst, lfirst_int, lfirst_oid, list_length(), strVal, TupleDescInitEntry(), TupleDescInitEntryCollation(), and types.

Referenced by ExecInitFunctionScan(), ExecInitTableFuncScan(), and inline_sql_function_in_from().

◆ CreateTemplateTupleDesc()

TupleDesc CreateTemplateTupleDesc ( int  natts)

Definition at line 165 of file tupdesc.c.

166{
167 TupleDesc desc;
168
169 /*
170 * sanity checks
171 */
172 Assert(natts >= 0);
173
174 /*
175 * Allocate enough memory for the tuple descriptor, the CompactAttribute
176 * array and also an array of FormData_pg_attribute.
177 *
178 * Note: the FormData_pg_attribute array stride is
179 * sizeof(FormData_pg_attribute), since we declare the array elements as
180 * FormData_pg_attribute for notational convenience. However, we only
181 * guarantee that the first ATTRIBUTE_FIXED_PART_SIZE bytes of each entry
182 * are valid; most code that copies tupdesc entries around copies just
183 * that much. In principle that could be less due to trailing padding,
184 * although with the current definition of pg_attribute there probably
185 * isn't any padding.
186 */
187 desc = (TupleDesc) palloc(offsetof(struct TupleDescData, compact_attrs) +
188 natts * sizeof(CompactAttribute) +
189 natts * sizeof(FormData_pg_attribute));
190
191 /*
192 * Initialize other fields of the tupdesc.
193 */
194 desc->natts = natts;
195 desc->constr = NULL;
196 desc->tdtypeid = RECORDOID;
197 desc->tdtypmod = -1;
198 desc->tdrefcount = -1; /* assume not reference-counted */
199
200 return desc;
201}
void * palloc(Size size)
Definition mcxt.c:1387
FormData_pg_attribute
TupleConstr * constr
Definition tupdesc.h:141
int32 tdtypmod
Definition tupdesc.h:139
struct TupleDescData * TupleDesc
Definition tupdesc.h:145

References Assert, TupleDescData::constr, fb(), FormData_pg_attribute, TupleDescData::natts, palloc(), TupleDescData::tdrefcount, TupleDescData::tdtypeid, and TupleDescData::tdtypmod.

Referenced by aclexplode(), addRangeTableEntryForFunction(), AllocateRelationDesc(), brtuple_disk_tupdesc(), build_function_result_tupdesc_d(), build_row_from_vars(), BuildDescForRelation(), BuildDescFromLists(), BuildHardcodedDescriptor(), ConstructTupleDescriptor(), create_toast_table(), CreateReplicationSlot(), CreateTupleDesc(), CreateTupleDescCopy(), CreateTupleDescCopyConstr(), CreateTupleDescTruncatedCopy(), dblink_get_pkey(), ExecInitFunctionScan(), ExecMakeTableFunctionResult(), ExecTypeFromExprList(), ExecTypeFromTLInternal(), expandRecordVariable(), ExplainResultDesc(), formrdesc(), get_expr_result_type(), GetPGVariableResultDesc(), gistrescan(), IdentifySystem(), init_sexpr(), initGinState(), libpqrcv_processTuples(), load_relcache_init_file(), materializeQueryResult(), materializeResult(), ordered_set_startup(), pg_buffercache_os_pages_internal(), pg_buffercache_pages(), 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_visibility_tupdesc(), pg_walfile_name_offset(), ReadReplicationSlot(), SendTablespaceList(), SendTimeLineHistory(), SendXlogRecPtrResult(), show_all_settings(), ShowAllGUCConfig(), ShowGUCConfigOption(), StartReplication(), test_custom_stats_fixed_report(), test_predtest(), tsvector_unnest(), TypeGetTupleDesc(), and WaitStmtResultDesc().

◆ CreateTupleDesc()

TupleDesc CreateTupleDesc ( int  natts,
Form_pg_attribute attrs 
)

Definition at line 212 of file tupdesc.c.

213{
214 TupleDesc desc;
215 int i;
216
217 desc = CreateTemplateTupleDesc(natts);
218
219 for (i = 0; i < natts; ++i)
220 {
223 }
224 return desc;
225}
int i
Definition isn.c:77
#define ATTRIBUTE_FIXED_PART_SIZE
void populate_compact_attribute(TupleDesc tupdesc, int attnum)
Definition tupdesc.c:100
static FormData_pg_attribute * TupleDescAttr(TupleDesc tupdesc, int i)
Definition tupdesc.h:160

References ATTRIBUTE_FIXED_PART_SIZE, CreateTemplateTupleDesc(), fb(), i, populate_compact_attribute(), and TupleDescAttr().

Referenced by AddNewAttributeTuples(), and InsertOneTuple().

◆ CreateTupleDescCopy()

TupleDesc CreateTupleDescCopy ( TupleDesc  tupdesc)

Definition at line 235 of file tupdesc.c.

236{
237 TupleDesc desc;
238 int i;
239
240 desc = CreateTemplateTupleDesc(tupdesc->natts);
241
242 /* Flat-copy the attribute array */
243 memcpy(TupleDescAttr(desc, 0),
244 TupleDescAttr(tupdesc, 0),
245 desc->natts * sizeof(FormData_pg_attribute));
246
247 /*
248 * Since we're not copying constraints and defaults, clear fields
249 * associated with them.
250 */
251 for (i = 0; i < desc->natts; i++)
252 {
254
255 att->attnotnull = false;
256 att->atthasdef = false;
257 att->atthasmissing = false;
258 att->attidentity = '\0';
259 att->attgenerated = '\0';
260
262 }
263
264 /* We can copy the tuple type identification, too */
265 desc->tdtypeid = tupdesc->tdtypeid;
266 desc->tdtypmod = tupdesc->tdtypmod;
267
268 return desc;
269}
FormData_pg_attribute * Form_pg_attribute

References CreateTemplateTupleDesc(), fb(), FormData_pg_attribute, i, TupleDescData::natts, populate_compact_attribute(), TupleDescData::tdtypeid, TupleDescData::tdtypmod, and TupleDescAttr().

Referenced by assign_record_type_typmod(), BuildTupleHashTable(), cfunc_hashtable_insert(), CompleteCachedPlan(), connectby_text(), connectby_text_serial(), CopyCachedPlan(), crosstab(), crosstab_hash(), database_to_xmlschema_internal(), do_autovacuum(), ExecEvalWholeRowVar(), ExecInitForeignScan(), ExecInitFunctionScan(), ExecInsert(), ExecPrepareTuplestoreResult(), FetchPreparedStatementResultDesc(), fmgr_sql(), get_record_type_from_query(), get_tupdesc_for_join_scan_tuples(), GetAfterTriggersStoreSlot(), getSpGistTupleDesc(), init_sexpr(), InitMaterializedSRF(), make_expanded_record_from_exprecord(), make_expanded_record_from_tupdesc(), materializeResult(), PersistHoldablePortal(), plperl_return_next_internal(), plpgsql_exec_function(), pltcl_func_handler(), PLy_spi_execute_fetch_result(), populate_recordset_worker(), RelationBuildLocalRelation(), RelationNameGetTupleDesc(), RevalidateCachedQuery(), schema_to_xmlschema_internal(), spi_dest_startup(), sql_compile_callback(), storeRow(), update_cached_tupdesc(), and UtilityTupleDescriptor().

◆ CreateTupleDescCopyConstr()

TupleDesc CreateTupleDescCopyConstr ( TupleDesc  tupdesc)

Definition at line 323 of file tupdesc.c.

324{
325 TupleDesc desc;
326 TupleConstr *constr = tupdesc->constr;
327 int i;
328
329 desc = CreateTemplateTupleDesc(tupdesc->natts);
330
331 /* Flat-copy the attribute array */
332 memcpy(TupleDescAttr(desc, 0),
333 TupleDescAttr(tupdesc, 0),
334 desc->natts * sizeof(FormData_pg_attribute));
335
336 for (i = 0; i < desc->natts; i++)
337 {
339
342 }
343
344 /* Copy the TupleConstr data structure, if any */
345 if (constr)
346 {
348
349 cpy->has_not_null = constr->has_not_null;
350 cpy->has_generated_stored = constr->has_generated_stored;
351 cpy->has_generated_virtual = constr->has_generated_virtual;
352
353 if ((cpy->num_defval = constr->num_defval) > 0)
354 {
355 cpy->defval = (AttrDefault *) palloc(cpy->num_defval * sizeof(AttrDefault));
356 memcpy(cpy->defval, constr->defval, cpy->num_defval * sizeof(AttrDefault));
357 for (i = cpy->num_defval - 1; i >= 0; i--)
358 cpy->defval[i].adbin = pstrdup(constr->defval[i].adbin);
359 }
360
361 if (constr->missing)
362 {
363 cpy->missing = (AttrMissing *) palloc(tupdesc->natts * sizeof(AttrMissing));
364 memcpy(cpy->missing, constr->missing, tupdesc->natts * sizeof(AttrMissing));
365 for (i = tupdesc->natts - 1; i >= 0; i--)
366 {
367 if (constr->missing[i].am_present)
368 {
369 CompactAttribute *attr = TupleDescCompactAttr(tupdesc, i);
370
371 cpy->missing[i].am_value = datumCopy(constr->missing[i].am_value,
372 attr->attbyval,
373 attr->attlen);
374 }
375 }
376 }
377
378 if ((cpy->num_check = constr->num_check) > 0)
379 {
380 cpy->check = (ConstrCheck *) palloc(cpy->num_check * sizeof(ConstrCheck));
381 memcpy(cpy->check, constr->check, cpy->num_check * sizeof(ConstrCheck));
382 for (i = cpy->num_check - 1; i >= 0; i--)
383 {
384 cpy->check[i].ccname = pstrdup(constr->check[i].ccname);
385 cpy->check[i].ccbin = pstrdup(constr->check[i].ccbin);
386 cpy->check[i].ccenforced = constr->check[i].ccenforced;
387 cpy->check[i].ccvalid = constr->check[i].ccvalid;
388 cpy->check[i].ccnoinherit = constr->check[i].ccnoinherit;
389 }
390 }
391
392 desc->constr = cpy;
393 }
394
395 /* We can copy the tuple type identification, too */
396 desc->tdtypeid = tupdesc->tdtypeid;
397 desc->tdtypmod = tupdesc->tdtypmod;
398
399 return desc;
400}
Datum datumCopy(Datum value, bool typByVal, int typLen)
Definition datum.c:132
#define palloc0_object(type)
Definition fe_memutils.h:75
char * pstrdup(const char *in)
Definition mcxt.c:1781
char * adbin
Definition tupdesc.h:25
char attnullability
Definition tupdesc.h:79
char * ccname
Definition tupdesc.h:30
bool ccenforced
Definition tupdesc.h:32
bool ccnoinherit
Definition tupdesc.h:34
bool ccvalid
Definition tupdesc.h:33
char * ccbin
Definition tupdesc.h:31
bool has_generated_virtual
Definition tupdesc.h:47
bool has_not_null
Definition tupdesc.h:45
AttrDefault * defval
Definition tupdesc.h:40
bool has_generated_stored
Definition tupdesc.h:46
struct AttrMissing * missing
Definition tupdesc.h:42
ConstrCheck * check
Definition tupdesc.h:41
uint16 num_defval
Definition tupdesc.h:43
uint16 num_check
Definition tupdesc.h:44
static CompactAttribute * TupleDescCompactAttr(TupleDesc tupdesc, int i)
Definition tupdesc.h:175

References AttrDefault::adbin, AttrMissing::am_present, AttrMissing::am_value, CompactAttribute::attbyval, CompactAttribute::attlen, CompactAttribute::attnullability, ConstrCheck::ccbin, ConstrCheck::ccenforced, ConstrCheck::ccname, ConstrCheck::ccnoinherit, ConstrCheck::ccvalid, TupleConstr::check, TupleDescData::constr, CreateTemplateTupleDesc(), datumCopy(), TupleConstr::defval, fb(), FormData_pg_attribute, TupleConstr::has_generated_stored, TupleConstr::has_generated_virtual, TupleConstr::has_not_null, i, TupleConstr::missing, TupleDescData::natts, TupleConstr::num_check, TupleConstr::num_defval, palloc(), palloc0_object, populate_compact_attribute(), pstrdup(), TupleDescData::tdtypeid, TupleDescData::tdtypmod, TupleDescAttr(), and TupleDescCompactAttr().

Referenced by ATGetQueueEntry(), CatalogCacheInitializeCache(), init_tuple_slot(), and lookup_rowtype_tupdesc_copy().

◆ CreateTupleDescTruncatedCopy()

TupleDesc CreateTupleDescTruncatedCopy ( TupleDesc  tupdesc,
int  natts 
)

Definition at line 279 of file tupdesc.c.

280{
281 TupleDesc desc;
282 int i;
283
285
286 desc = CreateTemplateTupleDesc(natts);
287
288 /* Flat-copy the attribute array */
289 memcpy(TupleDescAttr(desc, 0),
290 TupleDescAttr(tupdesc, 0),
291 desc->natts * sizeof(FormData_pg_attribute));
292
293 /*
294 * Since we're not copying constraints and defaults, clear fields
295 * associated with them.
296 */
297 for (i = 0; i < desc->natts; i++)
298 {
300
301 att->attnotnull = false;
302 att->atthasdef = false;
303 att->atthasmissing = false;
304 att->attidentity = '\0';
305 att->attgenerated = '\0';
306
308 }
309
310 /* We can copy the tuple type identification, too */
311 desc->tdtypeid = tupdesc->tdtypeid;
312 desc->tdtypmod = tupdesc->tdtypmod;
313
314 return desc;
315}

References Assert, CreateTemplateTupleDesc(), fb(), FormData_pg_attribute, i, TupleDescData::natts, populate_compact_attribute(), TupleDescData::tdtypeid, TupleDescData::tdtypmod, and TupleDescAttr().

Referenced by gist_page_items(), index_truncate_tuple(), and initGISTstate().

◆ DecrTupleDescRefCount()

void DecrTupleDescRefCount ( TupleDesc  tupdesc)

Definition at line 560 of file tupdesc.c.

561{
562 Assert(tupdesc->tdrefcount > 0);
563
565 if (--tupdesc->tdrefcount == 0)
566 FreeTupleDesc(tupdesc);
567}
ResourceOwner CurrentResourceOwner
Definition resowner.c:173
void FreeTupleDesc(TupleDesc tupdesc)
Definition tupdesc.c:485
static void ResourceOwnerForgetTupleDesc(ResourceOwner owner, TupleDesc tupdesc)
Definition tupdesc.c:55

References Assert, CurrentResourceOwner, FreeTupleDesc(), ResourceOwnerForgetTupleDesc(), and TupleDescData::tdrefcount.

Referenced by cache_record_field_properties(), and ExecEvalConvertRowtype().

◆ equalRowTypes()

bool equalRowTypes ( TupleDesc  tupdesc1,
TupleDesc  tupdesc2 
)

Definition at line 760 of file tupdesc.c.

761{
762 if (tupdesc1->natts != tupdesc2->natts)
763 return false;
764 if (tupdesc1->tdtypeid != tupdesc2->tdtypeid)
765 return false;
766
767 for (int i = 0; i < tupdesc1->natts; i++)
768 {
771
772 if (strcmp(NameStr(attr1->attname), NameStr(attr2->attname)) != 0)
773 return false;
774 if (attr1->atttypid != attr2->atttypid)
775 return false;
776 if (attr1->atttypmod != attr2->atttypmod)
777 return false;
778 if (attr1->attcollation != attr2->attcollation)
779 return false;
780
781 /* Record types derived from tables could have dropped fields. */
782 if (attr1->attisdropped != attr2->attisdropped)
783 return false;
784 }
785
786 return true;
787}
#define NameStr(name)
Definition c.h:765

References fb(), i, NameStr, and TupleDescAttr().

Referenced by acquire_inherited_sample_rows(), cfunc_match(), ProcedureCreate(), record_type_typmod_compare(), RevalidateCachedQuery(), and shared_record_table_compare().

◆ equalTupleDescs()

bool equalTupleDescs ( TupleDesc  tupdesc1,
TupleDesc  tupdesc2 
)

Definition at line 573 of file tupdesc.c.

574{
575 int i,
576 n;
577
578 if (tupdesc1->natts != tupdesc2->natts)
579 return false;
580 if (tupdesc1->tdtypeid != tupdesc2->tdtypeid)
581 return false;
582
583 /* tdtypmod and tdrefcount are not checked */
584
585 for (i = 0; i < tupdesc1->natts; i++)
586 {
589
590 /*
591 * We do not need to check every single field here: we can disregard
592 * attrelid and attnum (which were used to place the row in the attrs
593 * array in the first place). It might look like we could dispense
594 * with checking attlen/attbyval/attalign, since these are derived
595 * from atttypid; but in the case of dropped columns we must check
596 * them (since atttypid will be zero for all dropped columns) and in
597 * general it seems safer to check them always.
598 *
599 * We intentionally ignore atthasmissing, since that's not very
600 * relevant in tupdescs, which lack the attmissingval field.
601 */
602 if (strcmp(NameStr(attr1->attname), NameStr(attr2->attname)) != 0)
603 return false;
604 if (attr1->atttypid != attr2->atttypid)
605 return false;
606 if (attr1->attlen != attr2->attlen)
607 return false;
608 if (attr1->attndims != attr2->attndims)
609 return false;
610 if (attr1->atttypmod != attr2->atttypmod)
611 return false;
612 if (attr1->attbyval != attr2->attbyval)
613 return false;
614 if (attr1->attalign != attr2->attalign)
615 return false;
616 if (attr1->attstorage != attr2->attstorage)
617 return false;
618 if (attr1->attcompression != attr2->attcompression)
619 return false;
620 if (attr1->attnotnull != attr2->attnotnull)
621 return false;
622
623 /*
624 * When the column has a not-null constraint, we also need to consider
625 * its validity aspect, which only manifests in CompactAttribute->
626 * attnullability, so verify that.
627 */
628 if (attr1->attnotnull)
629 {
632
633 Assert(cattr1->attnullability != ATTNULLABLE_UNKNOWN);
634 Assert((cattr1->attnullability == ATTNULLABLE_UNKNOWN) ==
635 (cattr2->attnullability == ATTNULLABLE_UNKNOWN));
636
637 if (cattr1->attnullability != cattr2->attnullability)
638 return false;
639 }
640 if (attr1->atthasdef != attr2->atthasdef)
641 return false;
642 if (attr1->attidentity != attr2->attidentity)
643 return false;
644 if (attr1->attgenerated != attr2->attgenerated)
645 return false;
646 if (attr1->attisdropped != attr2->attisdropped)
647 return false;
648 if (attr1->attislocal != attr2->attislocal)
649 return false;
650 if (attr1->attinhcount != attr2->attinhcount)
651 return false;
652 if (attr1->attcollation != attr2->attcollation)
653 return false;
654 /* variable-length fields are not even present... */
655 }
656
657 if (tupdesc1->constr != NULL)
658 {
659 TupleConstr *constr1 = tupdesc1->constr;
660 TupleConstr *constr2 = tupdesc2->constr;
661
662 if (constr2 == NULL)
663 return false;
664 if (constr1->has_not_null != constr2->has_not_null)
665 return false;
666 if (constr1->has_generated_stored != constr2->has_generated_stored)
667 return false;
668 if (constr1->has_generated_virtual != constr2->has_generated_virtual)
669 return false;
670 n = constr1->num_defval;
671 if (n != (int) constr2->num_defval)
672 return false;
673 /* We assume here that both AttrDefault arrays are in adnum order */
674 for (i = 0; i < n; i++)
675 {
676 AttrDefault *defval1 = constr1->defval + i;
677 AttrDefault *defval2 = constr2->defval + i;
678
679 if (defval1->adnum != defval2->adnum)
680 return false;
681 if (strcmp(defval1->adbin, defval2->adbin) != 0)
682 return false;
683 }
684 if (constr1->missing)
685 {
686 if (!constr2->missing)
687 return false;
688 for (i = 0; i < tupdesc1->natts; i++)
689 {
690 AttrMissing *missval1 = constr1->missing + i;
691 AttrMissing *missval2 = constr2->missing + i;
692
693 if (missval1->am_present != missval2->am_present)
694 return false;
695 if (missval1->am_present)
696 {
698
699 if (!datumIsEqual(missval1->am_value, missval2->am_value,
700 missatt1->attbyval, missatt1->attlen))
701 return false;
702 }
703 }
704 }
705 else if (constr2->missing)
706 return false;
707 n = constr1->num_check;
708 if (n != (int) constr2->num_check)
709 return false;
710
711 /*
712 * Similarly, we rely here on the ConstrCheck entries being sorted by
713 * name. If there are duplicate names, the outcome of the comparison
714 * is uncertain, but that should not happen.
715 */
716 for (i = 0; i < n; i++)
717 {
718 ConstrCheck *check1 = constr1->check + i;
719 ConstrCheck *check2 = constr2->check + i;
720
721 if (!(strcmp(check1->ccname, check2->ccname) == 0 &&
722 strcmp(check1->ccbin, check2->ccbin) == 0 &&
723 check1->ccenforced == check2->ccenforced &&
724 check1->ccvalid == check2->ccvalid &&
725 check1->ccnoinherit == check2->ccnoinherit))
726 return false;
727 }
728 }
729 else if (tupdesc2->constr != NULL)
730 return false;
731 return true;
732}
bool datumIsEqual(Datum value1, Datum value2, bool typByVal, int typLen)
Definition datum.c:223
#define ATTNULLABLE_UNKNOWN
Definition tupdesc.h:85

References Assert, ATTNULLABLE_UNKNOWN, datumIsEqual(), fb(), i, NameStr, TupleConstr::num_defval, TupleDescAttr(), and TupleDescCompactAttr().

Referenced by RelationFindDeletedTupleInfoByIndex(), RelationFindDeletedTupleInfoSeq(), RelationFindReplTupleSeq(), and RelationRebuildRelation().

◆ FreeTupleDesc()

void FreeTupleDesc ( TupleDesc  tupdesc)

Definition at line 485 of file tupdesc.c.

486{
487 int i;
488
489 /*
490 * Possibly this should assert tdrefcount == 0, to disallow explicit
491 * freeing of un-refcounted tupdescs?
492 */
493 Assert(tupdesc->tdrefcount <= 0);
494
495 if (tupdesc->constr)
496 {
497 if (tupdesc->constr->num_defval > 0)
498 {
499 AttrDefault *attrdef = tupdesc->constr->defval;
500
501 for (i = tupdesc->constr->num_defval - 1; i >= 0; i--)
502 pfree(attrdef[i].adbin);
503 pfree(attrdef);
504 }
505 if (tupdesc->constr->missing)
506 {
507 AttrMissing *attrmiss = tupdesc->constr->missing;
508
509 for (i = tupdesc->natts - 1; i >= 0; i--)
510 {
511 if (attrmiss[i].am_present
512 && !TupleDescAttr(tupdesc, i)->attbyval)
513 pfree(DatumGetPointer(attrmiss[i].am_value));
514 }
516 }
517 if (tupdesc->constr->num_check > 0)
518 {
519 ConstrCheck *check = tupdesc->constr->check;
520
521 for (i = tupdesc->constr->num_check - 1; i >= 0; i--)
522 {
523 pfree(check[i].ccname);
524 pfree(check[i].ccbin);
525 }
526 pfree(check);
527 }
528 pfree(tupdesc->constr);
529 }
530
531 pfree(tupdesc);
532}
void pfree(void *pointer)
Definition mcxt.c:1616
static Pointer DatumGetPointer(Datum X)
Definition postgres.h:342

References Assert, TupleConstr::check, TupleDescData::constr, DatumGetPointer(), TupleConstr::defval, fb(), i, TupleConstr::missing, TupleDescData::natts, TupleConstr::num_check, TupleConstr::num_defval, pfree(), TupleDescData::tdrefcount, and TupleDescAttr().

Referenced by AddNewAttributeTuples(), AtEOXact_RelationCache(), cfunc_hashtable_delete(), DecrTupleDescRefCount(), do_autovacuum(), ER_mc_callback(), ExecMakeTableFunctionResult(), ExecPrepareTuplestoreResult(), get_record_type_from_query(), get_rel_sync_entry(), InvalidateCompositeTypeCacheEntry(), ordered_set_startup(), PLy_result_dealloc(), RelationDestroyRelation(), ResOwnerReleaseTupleDesc(), RevalidateCachedQuery(), spgendscan(), update_cached_tupdesc(), and walrcv_clear_result().

◆ hashRowType()

uint32 hashRowType ( TupleDesc  desc)

Definition at line 796 of file tupdesc.c.

797{
798 uint32 s;
799 int i;
800
801 s = hash_combine(0, hash_bytes_uint32(desc->natts));
803 for (i = 0; i < desc->natts; ++i)
805
806 return s;
807}
uint32_t uint32
Definition c.h:546
uint32 hash_bytes_uint32(uint32 k)
Definition hashfn.c:610
static uint32 hash_combine(uint32 a, uint32 b)
Definition hashfn.h:68

References fb(), hash_bytes_uint32(), hash_combine(), i, TupleDescData::natts, TupleDescData::tdtypeid, and TupleDescAttr().

Referenced by cfunc_hash(), record_type_typmod_hash(), and shared_record_table_hash().

◆ IncrTupleDescRefCount()

void IncrTupleDescRefCount ( TupleDesc  tupdesc)

Definition at line 542 of file tupdesc.c.

543{
544 Assert(tupdesc->tdrefcount >= 0);
545
547 tupdesc->tdrefcount++;
549}
void ResourceOwnerEnlarge(ResourceOwner owner)
Definition resowner.c:449
static void ResourceOwnerRememberTupleDesc(ResourceOwner owner, TupleDesc tupdesc)
Definition tupdesc.c:49

References Assert, CurrentResourceOwner, ResourceOwnerEnlarge(), ResourceOwnerRememberTupleDesc(), and TupleDescData::tdrefcount.

Referenced by cache_record_field_properties(), and ExecEvalConvertRowtype().

◆ populate_compact_attribute()

void populate_compact_attribute ( TupleDesc  tupdesc,
int  attnum 
)

Definition at line 100 of file tupdesc.c.

101{
102 Form_pg_attribute src = TupleDescAttr(tupdesc, attnum);
104
105 /*
106 * Don't use TupleDescCompactAttr to prevent infinite recursion in assert
107 * builds.
108 */
109 dst = &tupdesc->compact_attrs[attnum];
110
112}
CompactAttribute compact_attrs[FLEXIBLE_ARRAY_MEMBER]
Definition tupdesc.h:143
static void populate_compact_attribute_internal(Form_pg_attribute src, CompactAttribute *dst)
Definition tupdesc.c:65

References attnum, TupleDescData::compact_attrs, fb(), populate_compact_attribute_internal(), and TupleDescAttr().

Referenced by BuildDescForRelation(), BuildHardcodedDescriptor(), ConstructTupleDescriptor(), CreateTupleDesc(), CreateTupleDescCopy(), CreateTupleDescCopyConstr(), CreateTupleDescTruncatedCopy(), formrdesc(), getSpGistTupleDesc(), load_relcache_init_file(), RelationBuildLocalRelation(), RelationBuildTupleDesc(), TupleDescCopy(), TupleDescCopyEntry(), TupleDescInitBuiltinEntry(), and TupleDescInitEntry().

◆ populate_compact_attribute_internal()

static void populate_compact_attribute_internal ( Form_pg_attribute  src,
CompactAttribute dst 
)
inlinestatic

Definition at line 65 of file tupdesc.c.

67{
68 memset(dst, 0, sizeof(CompactAttribute));
69
70 dst->attcacheoff = -1;
71 dst->attlen = src->attlen;
72
73 dst->attbyval = src->attbyval;
74 dst->attispackable = (src->attstorage != TYPSTORAGE_PLAIN);
75 dst->atthasmissing = src->atthasmissing;
76 dst->attisdropped = src->attisdropped;
77 dst->attgenerated = (src->attgenerated != '\0');
78
79 /*
80 * Assign nullability status for this column. Assuming that a constraint
81 * exists, at this point we don't know if a not-null constraint is valid,
82 * so we assign UNKNOWN unless the table is a catalog, in which case we
83 * know it's valid.
84 */
85 dst->attnullability = !src->attnotnull ? ATTNULLABLE_UNRESTRICTED :
88
89 /* Compute numeric alignment requirement, too */
90 dst->attalignby = typalign_to_alignby(src->attalign);
91}
bool IsCatalogRelationOid(Oid relid)
Definition catalog.c:121
#define ATTNULLABLE_VALID
Definition tupdesc.h:86
#define ATTNULLABLE_UNRESTRICTED
Definition tupdesc.h:84
static uint8 typalign_to_alignby(char typalign)
Definition tupmacs.h:80

References ATTNULLABLE_UNKNOWN, ATTNULLABLE_UNRESTRICTED, ATTNULLABLE_VALID, fb(), IsCatalogRelationOid(), and typalign_to_alignby().

Referenced by populate_compact_attribute(), and verify_compact_attribute().

◆ ResourceOwnerForgetTupleDesc()

static void ResourceOwnerForgetTupleDesc ( ResourceOwner  owner,
TupleDesc  tupdesc 
)
inlinestatic

Definition at line 55 of file tupdesc.c.

56{
58}
static Datum PointerGetDatum(const void *X)
Definition postgres.h:352
void ResourceOwnerForget(ResourceOwner owner, Datum value, const ResourceOwnerDesc *kind)
Definition resowner.c:561
static const ResourceOwnerDesc tupdesc_resowner_desc
Definition tupdesc.c:38

References PointerGetDatum(), ResourceOwnerForget(), and tupdesc_resowner_desc.

Referenced by DecrTupleDescRefCount().

◆ ResourceOwnerRememberTupleDesc()

static void ResourceOwnerRememberTupleDesc ( ResourceOwner  owner,
TupleDesc  tupdesc 
)
inlinestatic

Definition at line 49 of file tupdesc.c.

50{
52}
void ResourceOwnerRemember(ResourceOwner owner, Datum value, const ResourceOwnerDesc *kind)
Definition resowner.c:521

References PointerGetDatum(), ResourceOwnerRemember(), and tupdesc_resowner_desc.

Referenced by IncrTupleDescRefCount().

◆ ResOwnerPrintTupleDesc()

static char * ResOwnerPrintTupleDesc ( Datum  res)
static

Definition at line 1110 of file tupdesc.c.

1111{
1112 TupleDesc tupdesc = (TupleDesc) DatumGetPointer(res);
1113
1114 return psprintf("TupleDesc %p (%u,%d)",
1115 tupdesc, tupdesc->tdtypeid, tupdesc->tdtypmod);
1116}
char * psprintf(const char *fmt,...)
Definition psprintf.c:43

References DatumGetPointer(), psprintf(), TupleDescData::tdtypeid, and TupleDescData::tdtypmod.

◆ ResOwnerReleaseTupleDesc()

static void ResOwnerReleaseTupleDesc ( Datum  res)
static

Definition at line 1099 of file tupdesc.c.

1100{
1101 TupleDesc tupdesc = (TupleDesc) DatumGetPointer(res);
1102
1103 /* Like DecrTupleDescRefCount, but don't call ResourceOwnerForget() */
1104 Assert(tupdesc->tdrefcount > 0);
1105 if (--tupdesc->tdrefcount == 0)
1106 FreeTupleDesc(tupdesc);
1107}

References Assert, DatumGetPointer(), FreeTupleDesc(), and TupleDescData::tdrefcount.

◆ TupleDescCopy()

void TupleDescCopy ( TupleDesc  dst,
TupleDesc  src 
)

Definition at line 411 of file tupdesc.c.

412{
413 int i;
414
415 /* Flat-copy the header and attribute arrays */
416 memcpy(dst, src, TupleDescSize(src));
417
418 /*
419 * Since we're not copying constraints and defaults, clear fields
420 * associated with them.
421 */
422 for (i = 0; i < dst->natts; i++)
423 {
425
426 att->attnotnull = false;
427 att->atthasdef = false;
428 att->atthasmissing = false;
429 att->attidentity = '\0';
430 att->attgenerated = '\0';
431
433 }
434 dst->constr = NULL;
435
436 /*
437 * Also, assume the destination is not to be ref-counted. (Copying the
438 * source's refcount would be wrong in any case.)
439 */
440 dst->tdrefcount = -1;
441}
#define TupleDescSize(src)
Definition tupdesc.h:198

References fb(), i, populate_compact_attribute(), TupleDescAttr(), and TupleDescSize.

Referenced by share_tupledesc().

◆ TupleDescCopyEntry()

void TupleDescCopyEntry ( TupleDesc  dst,
AttrNumber  dstAttno,
TupleDesc  src,
AttrNumber  srcAttno 
)

Definition at line 451 of file tupdesc.c.

453{
456
457 /*
458 * sanity checks
459 */
460 Assert(src);
461 Assert(dst);
462 Assert(srcAttno >= 1);
464 Assert(dstAttno >= 1);
466
468
469 dstAtt->attnum = dstAttno;
470
471 /* since we're not copying constraints or defaults, clear these */
472 dstAtt->attnotnull = false;
473 dstAtt->atthasdef = false;
474 dstAtt->atthasmissing = false;
475 dstAtt->attidentity = '\0';
476 dstAtt->attgenerated = '\0';
477
479}

References Assert, ATTRIBUTE_FIXED_PART_SIZE, fb(), populate_compact_attribute(), and TupleDescAttr().

Referenced by addRangeTableEntryForFunction(), ExecInitFunctionScan(), and ordered_set_startup().

◆ TupleDescGetDefault()

Node * TupleDescGetDefault ( TupleDesc  tupdesc,
AttrNumber  attnum 
)

Definition at line 1075 of file tupdesc.c.

1076{
1077 Node *result = NULL;
1078
1079 if (tupdesc->constr)
1080 {
1081 AttrDefault *attrdef = tupdesc->constr->defval;
1082
1083 for (int i = 0; i < tupdesc->constr->num_defval; i++)
1084 {
1085 if (attrdef[i].adnum == attnum)
1086 {
1087 result = stringToNode(attrdef[i].adbin);
1088 break;
1089 }
1090 }
1091 }
1092
1093 return result;
1094}
void * stringToNode(const char *str)
Definition read.c:90
Definition nodes.h:135

References attnum, TupleDescData::constr, TupleConstr::defval, fb(), i, TupleConstr::num_defval, and stringToNode().

Referenced by build_column_default(), createTableConstraints(), expandTableLikeClause(), and MergeAttributes().

◆ TupleDescInitBuiltinEntry()

void TupleDescInitBuiltinEntry ( TupleDesc  desc,
AttrNumber  attributeNumber,
const char attributeName,
Oid  oidtypeid,
int32  typmod,
int  attdim 
)

Definition at line 901 of file tupdesc.c.

907{
909
910 /* sanity checks */
911 Assert(desc);
914 Assert(attdim >= 0);
916
917 /* initialize the attribute fields */
918 att = TupleDescAttr(desc, attributeNumber - 1);
919 att->attrelid = 0; /* dummy value */
920
921 /* unlike TupleDescInitEntry, we require an attribute name */
923 namestrcpy(&(att->attname), attributeName);
924
925 att->atttypmod = typmod;
926
927 att->attnum = attributeNumber;
928 att->attndims = attdim;
929
930 att->attnotnull = false;
931 att->atthasdef = false;
932 att->atthasmissing = false;
933 att->attidentity = '\0';
934 att->attgenerated = '\0';
935 att->attisdropped = false;
936 att->attislocal = true;
937 att->attinhcount = 0;
938 /* variable-length fields are not present in tupledescs */
939
940 att->atttypid = oidtypeid;
941
942 /*
943 * Our goal here is to support just enough types to let basic builtin
944 * commands work without catalog access - e.g. so that we can do certain
945 * things even in processes that are not connected to a database.
946 */
947 switch (oidtypeid)
948 {
949 case TEXTOID:
950 case TEXTARRAYOID:
951 att->attlen = -1;
952 att->attbyval = false;
953 att->attalign = TYPALIGN_INT;
954 att->attstorage = TYPSTORAGE_EXTENDED;
955 att->attcompression = InvalidCompressionMethod;
956 att->attcollation = DEFAULT_COLLATION_OID;
957 break;
958
959 case BOOLOID:
960 att->attlen = 1;
961 att->attbyval = true;
962 att->attalign = TYPALIGN_CHAR;
963 att->attstorage = TYPSTORAGE_PLAIN;
964 att->attcompression = InvalidCompressionMethod;
965 att->attcollation = InvalidOid;
966 break;
967
968 case INT4OID:
969 att->attlen = 4;
970 att->attbyval = true;
971 att->attalign = TYPALIGN_INT;
972 att->attstorage = TYPSTORAGE_PLAIN;
973 att->attcompression = InvalidCompressionMethod;
974 att->attcollation = InvalidOid;
975 break;
976
977 case INT8OID:
978 att->attlen = 8;
979 att->attbyval = true;
980 att->attalign = TYPALIGN_DOUBLE;
981 att->attstorage = TYPSTORAGE_PLAIN;
982 att->attcompression = InvalidCompressionMethod;
983 att->attcollation = InvalidOid;
984 break;
985
986 case OIDOID:
987 att->attlen = 4;
988 att->attbyval = true;
989 att->attalign = TYPALIGN_INT;
990 att->attstorage = TYPSTORAGE_PLAIN;
991 att->attcompression = InvalidCompressionMethod;
992 att->attcollation = InvalidOid;
993 break;
994
995 default:
996 elog(ERROR, "unsupported type %u", oidtypeid);
997 }
998
1000}
#define PG_INT16_MAX
Definition c.h:600
#define ERROR
Definition elog.h:39
#define elog(elevel,...)
Definition elog.h:226
void namestrcpy(Name name, const char *str)
Definition name.c:233
#define InvalidOid
#define InvalidCompressionMethod

References Assert, elog, ERROR, fb(), InvalidCompressionMethod, InvalidOid, namestrcpy(), PG_INT16_MAX, populate_compact_attribute(), and TupleDescAttr().

Referenced by CreateReplicationSlot(), IdentifySystem(), ReadReplicationSlot(), SendTablespaceList(), SendTimeLineHistory(), SendXlogRecPtrResult(), ShowAllGUCConfig(), ShowGUCConfigOption(), and StartReplication().

◆ TupleDescInitEntry()

void TupleDescInitEntry ( TupleDesc  desc,
AttrNumber  attributeNumber,
const char attributeName,
Oid  oidtypeid,
int32  typmod,
int  attdim 
)

Definition at line 825 of file tupdesc.c.

831{
832 HeapTuple tuple;
835
836 /*
837 * sanity checks
838 */
839 Assert(desc);
842 Assert(attdim >= 0);
844
845 /*
846 * initialize the attribute fields
847 */
848 att = TupleDescAttr(desc, attributeNumber - 1);
849
850 att->attrelid = 0; /* dummy value */
851
852 /*
853 * Note: attributeName can be NULL, because the planner doesn't always
854 * fill in valid resname values in targetlists, particularly for resjunk
855 * attributes. Also, do nothing if caller wants to re-use the old attname.
856 */
857 if (attributeName == NULL)
858 MemSet(NameStr(att->attname), 0, NAMEDATALEN);
859 else if (attributeName != NameStr(att->attname))
860 namestrcpy(&(att->attname), attributeName);
861
862 att->atttypmod = typmod;
863
864 att->attnum = attributeNumber;
865 att->attndims = attdim;
866
867 att->attnotnull = false;
868 att->atthasdef = false;
869 att->atthasmissing = false;
870 att->attidentity = '\0';
871 att->attgenerated = '\0';
872 att->attisdropped = false;
873 att->attislocal = true;
874 att->attinhcount = 0;
875 /* variable-length fields are not present in tupledescs */
876
878 if (!HeapTupleIsValid(tuple))
879 elog(ERROR, "cache lookup failed for type %u", oidtypeid);
881
882 att->atttypid = oidtypeid;
883 att->attlen = typeForm->typlen;
884 att->attbyval = typeForm->typbyval;
885 att->attalign = typeForm->typalign;
886 att->attstorage = typeForm->typstorage;
887 att->attcompression = InvalidCompressionMethod;
888 att->attcollation = typeForm->typcollation;
889
891
892 ReleaseSysCache(tuple);
893}
#define MemSet(start, val, len)
Definition c.h:1013
#define HeapTupleIsValid(tuple)
Definition htup.h:78
static void * GETSTRUCT(const HeapTupleData *tuple)
#define NAMEDATALEN
FormData_pg_type * Form_pg_type
Definition pg_type.h:261
static Datum ObjectIdGetDatum(Oid X)
Definition postgres.h:262
void ReleaseSysCache(HeapTuple tuple)
Definition syscache.c:264
HeapTuple SearchSysCache1(int cacheId, Datum key1)
Definition syscache.c:220

References Assert, elog, ERROR, fb(), GETSTRUCT(), HeapTupleIsValid, InvalidCompressionMethod, MemSet, NAMEDATALEN, NameStr, namestrcpy(), ObjectIdGetDatum(), PG_INT16_MAX, populate_compact_attribute(), ReleaseSysCache(), SearchSysCache1(), and TupleDescAttr().

Referenced by aclexplode(), addRangeTableEntryForFunction(), brtuple_disk_tupdesc(), build_function_result_tupdesc_d(), build_row_from_vars(), BuildDescForRelation(), BuildDescFromLists(), CallStmtResultDesc(), create_toast_table(), dblink_get_pkey(), ExecInitFunctionScan(), ExecMakeTableFunctionResult(), ExecTypeFromExprList(), ExecTypeFromTLInternal(), expandRecordVariable(), ExplainResultDesc(), get_expr_result_type(), GetPGVariableResultDesc(), gistrescan(), init_sexpr(), initGinState(), libpqrcv_processTuples(), materializeQueryResult(), materializeResult(), ordered_set_startup(), pg_buffercache_os_pages_internal(), pg_buffercache_pages(), 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_visibility_tupdesc(), pg_walfile_name_offset(), resolve_polymorphic_tupdesc(), show_all_settings(), test_custom_stats_fixed_report(), test_predtest(), tsvector_unnest(), TypeGetTupleDesc(), and WaitStmtResultDesc().

◆ TupleDescInitEntryCollation()

void TupleDescInitEntryCollation ( TupleDesc  desc,
AttrNumber  attributeNumber,
Oid  collationid 
)

◆ verify_compact_attribute()

void verify_compact_attribute ( TupleDesc  tupdesc,
int  attnum 
)

Definition at line 125 of file tupdesc.c.

126{
127#ifdef USE_ASSERT_CHECKING
129 Form_pg_attribute attr = TupleDescAttr(tupdesc, attnum);
131
132 /*
133 * Make a temp copy of the TupleDesc's CompactAttribute. This may be a
134 * shared TupleDesc and the attcacheoff might get changed by another
135 * backend.
136 */
137 memcpy(&cattr, &tupdesc->compact_attrs[attnum], sizeof(CompactAttribute));
138
139 /*
140 * Populate the temporary CompactAttribute from the corresponding
141 * Form_pg_attribute
142 */
144
145 /*
146 * Make the attcacheoff match since it's been reset to -1 by
147 * populate_compact_attribute_internal. Same with attnullability.
148 */
149 tmp.attcacheoff = cattr.attcacheoff;
150 tmp.attnullability = cattr.attnullability;
151
152 /* Check the freshly populated CompactAttribute matches the TupleDesc's */
153 Assert(memcmp(&tmp, &cattr, sizeof(CompactAttribute)) == 0);
154#endif
155}
int32 attcacheoff
Definition tupdesc.h:70

References Assert, CompactAttribute::attcacheoff, CompactAttribute::attnullability, attnum, TupleDescData::compact_attrs, fb(), populate_compact_attribute_internal(), and TupleDescAttr().

Referenced by TupleDescCompactAttr().

Variable Documentation

◆ tupdesc_resowner_desc

const ResourceOwnerDesc tupdesc_resowner_desc
static
Initial value:
=
{
.name = "tupdesc reference",
.release_phase = RESOURCE_RELEASE_AFTER_LOCKS,
.release_priority = RELEASE_PRIO_TUPDESC_REFS,
.ReleaseResource = ResOwnerReleaseTupleDesc,
.DebugPrint = ResOwnerPrintTupleDesc
}
@ RESOURCE_RELEASE_AFTER_LOCKS
Definition resowner.h:56
#define RELEASE_PRIO_TUPDESC_REFS
Definition resowner.h:74
static void ResOwnerReleaseTupleDesc(Datum res)
Definition tupdesc.c:1099
static char * ResOwnerPrintTupleDesc(Datum res)
Definition tupdesc.c:1110

Definition at line 38 of file tupdesc.c.

39{
40 .name = "tupdesc reference",
41 .release_phase = RESOURCE_RELEASE_AFTER_LOCKS,
42 .release_priority = RELEASE_PRIO_TUPDESC_REFS,
43 .ReleaseResource = ResOwnerReleaseTupleDesc,
44 .DebugPrint = ResOwnerPrintTupleDesc
45};

Referenced by ResourceOwnerForgetTupleDesc(), and ResourceOwnerRememberTupleDesc().