mirror of
https://git.postgresql.org/git/postgresql.git
synced 2024-09-06 09:09:21 +02:00
Change tupledesc->attrs[n] to TupleDescAttr(tupledesc, n).
This is a mechanical change in preparation for a later commit that will change the layout of TupleDesc. Introducing a macro to abstract the details of where attributes are stored will allow us to change that in separate step and revise it in future. Author: Thomas Munro, editorialized by Andres Freund Reviewed-By: Andres Freund Discussion: https://postgr.es/m/CAEepm=0ZtQ-SpsgCyzzYpsXS6e=kZWqk3g5Ygn3MDV7A8dabUA@mail.gmail.com
This commit is contained in:
parent
b1c2d76a2f
commit
2cd7084524
@ -2172,14 +2172,16 @@ get_sql_insert(Relation rel, int *pkattnums, int pknumatts, char **src_pkattvals
|
||||
needComma = false;
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
|
||||
if (att->attisdropped)
|
||||
continue;
|
||||
|
||||
if (needComma)
|
||||
appendStringInfoChar(&buf, ',');
|
||||
|
||||
appendStringInfoString(&buf,
|
||||
quote_ident_cstr(NameStr(tupdesc->attrs[i]->attname)));
|
||||
quote_ident_cstr(NameStr(att->attname)));
|
||||
needComma = true;
|
||||
}
|
||||
|
||||
@ -2191,7 +2193,7 @@ get_sql_insert(Relation rel, int *pkattnums, int pknumatts, char **src_pkattvals
|
||||
needComma = false;
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
if (TupleDescAttr(tupdesc, i)->attisdropped)
|
||||
continue;
|
||||
|
||||
if (needComma)
|
||||
@ -2237,12 +2239,13 @@ get_sql_delete(Relation rel, int *pkattnums, int pknumatts, char **tgt_pkattvals
|
||||
for (i = 0; i < pknumatts; i++)
|
||||
{
|
||||
int pkattnum = pkattnums[i];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, pkattnum);
|
||||
|
||||
if (i > 0)
|
||||
appendStringInfoString(&buf, " AND ");
|
||||
|
||||
appendStringInfoString(&buf,
|
||||
quote_ident_cstr(NameStr(tupdesc->attrs[pkattnum]->attname)));
|
||||
quote_ident_cstr(NameStr(attr->attname)));
|
||||
|
||||
if (tgt_pkattvals[i] != NULL)
|
||||
appendStringInfo(&buf, " = %s",
|
||||
@ -2289,14 +2292,16 @@ get_sql_update(Relation rel, int *pkattnums, int pknumatts, char **src_pkattvals
|
||||
needComma = false;
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, i);
|
||||
|
||||
if (attr->attisdropped)
|
||||
continue;
|
||||
|
||||
if (needComma)
|
||||
appendStringInfoString(&buf, ", ");
|
||||
|
||||
appendStringInfo(&buf, "%s = ",
|
||||
quote_ident_cstr(NameStr(tupdesc->attrs[i]->attname)));
|
||||
quote_ident_cstr(NameStr(attr->attname)));
|
||||
|
||||
key = get_attnum_pk_pos(pkattnums, pknumatts, i);
|
||||
|
||||
@ -2320,12 +2325,13 @@ get_sql_update(Relation rel, int *pkattnums, int pknumatts, char **src_pkattvals
|
||||
for (i = 0; i < pknumatts; i++)
|
||||
{
|
||||
int pkattnum = pkattnums[i];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, pkattnum);
|
||||
|
||||
if (i > 0)
|
||||
appendStringInfoString(&buf, " AND ");
|
||||
|
||||
appendStringInfoString(&buf,
|
||||
quote_ident_cstr(NameStr(tupdesc->attrs[pkattnum]->attname)));
|
||||
quote_ident_cstr(NameStr(attr->attname)));
|
||||
|
||||
val = tgt_pkattvals[i];
|
||||
|
||||
@ -2409,14 +2415,16 @@ get_tuple_of_interest(Relation rel, int *pkattnums, int pknumatts, char **src_pk
|
||||
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, i);
|
||||
|
||||
if (i > 0)
|
||||
appendStringInfoString(&buf, ", ");
|
||||
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
if (attr->attisdropped)
|
||||
appendStringInfoString(&buf, "NULL");
|
||||
else
|
||||
appendStringInfoString(&buf,
|
||||
quote_ident_cstr(NameStr(tupdesc->attrs[i]->attname)));
|
||||
quote_ident_cstr(NameStr(attr->attname)));
|
||||
}
|
||||
|
||||
appendStringInfo(&buf, " FROM %s WHERE ", relname);
|
||||
@ -2424,12 +2432,13 @@ get_tuple_of_interest(Relation rel, int *pkattnums, int pknumatts, char **src_pk
|
||||
for (i = 0; i < pknumatts; i++)
|
||||
{
|
||||
int pkattnum = pkattnums[i];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, pkattnum);
|
||||
|
||||
if (i > 0)
|
||||
appendStringInfoString(&buf, " AND ");
|
||||
|
||||
appendStringInfoString(&buf,
|
||||
quote_ident_cstr(NameStr(tupdesc->attrs[pkattnum]->attname)));
|
||||
quote_ident_cstr(NameStr(attr->attname)));
|
||||
|
||||
if (src_pkattvals[i] != NULL)
|
||||
appendStringInfo(&buf, " = %s",
|
||||
@ -2894,7 +2903,7 @@ validate_pkattnums(Relation rel,
|
||||
for (j = 0; j < natts; j++)
|
||||
{
|
||||
/* dropped columns don't count */
|
||||
if (tupdesc->attrs[j]->attisdropped)
|
||||
if (TupleDescAttr(tupdesc, j)->attisdropped)
|
||||
continue;
|
||||
|
||||
if (++lnum == pkattnum)
|
||||
|
@ -430,7 +430,7 @@ get_file_fdw_attribute_options(Oid relid)
|
||||
/* Retrieve FDW options for all user-defined attributes. */
|
||||
for (attnum = 1; attnum <= natts; attnum++)
|
||||
{
|
||||
Form_pg_attribute attr = tupleDesc->attrs[attnum - 1];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupleDesc, attnum - 1);
|
||||
List *options;
|
||||
ListCell *lc;
|
||||
|
||||
@ -898,7 +898,7 @@ check_selective_binary_conversion(RelOptInfo *baserel,
|
||||
/* Get user attributes. */
|
||||
if (attnum > 0)
|
||||
{
|
||||
Form_pg_attribute attr = tupleDesc->attrs[attnum - 1];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupleDesc, attnum - 1);
|
||||
char *attname = NameStr(attr->attname);
|
||||
|
||||
/* Skip dropped attributes (probably shouldn't see any here). */
|
||||
@ -912,7 +912,7 @@ check_selective_binary_conversion(RelOptInfo *baserel,
|
||||
numattrs = 0;
|
||||
for (i = 0; i < tupleDesc->natts; i++)
|
||||
{
|
||||
Form_pg_attribute attr = tupleDesc->attrs[i];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupleDesc, i);
|
||||
|
||||
if (attr->attisdropped)
|
||||
continue;
|
||||
|
@ -855,15 +855,16 @@ hstore_from_record(PG_FUNCTION_ARGS)
|
||||
for (i = 0, j = 0; i < ncolumns; ++i)
|
||||
{
|
||||
ColumnIOData *column_info = &my_extra->columns[i];
|
||||
Oid column_type = tupdesc->attrs[i]->atttypid;
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
Oid column_type = att->atttypid;
|
||||
char *value;
|
||||
|
||||
/* Ignore dropped columns in datatype */
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
if (att->attisdropped)
|
||||
continue;
|
||||
|
||||
pairs[j].key = NameStr(tupdesc->attrs[i]->attname);
|
||||
pairs[j].keylen = hstoreCheckKeyLen(strlen(NameStr(tupdesc->attrs[i]->attname)));
|
||||
pairs[j].key = NameStr(att->attname);
|
||||
pairs[j].keylen = hstoreCheckKeyLen(strlen(NameStr(att->attname)));
|
||||
|
||||
if (!nulls || nulls[i])
|
||||
{
|
||||
@ -1034,21 +1035,22 @@ hstore_populate_record(PG_FUNCTION_ARGS)
|
||||
for (i = 0; i < ncolumns; ++i)
|
||||
{
|
||||
ColumnIOData *column_info = &my_extra->columns[i];
|
||||
Oid column_type = tupdesc->attrs[i]->atttypid;
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
Oid column_type = att->atttypid;
|
||||
char *value;
|
||||
int idx;
|
||||
int vallen;
|
||||
|
||||
/* Ignore dropped columns in datatype */
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
if (att->attisdropped)
|
||||
{
|
||||
nulls[i] = true;
|
||||
continue;
|
||||
}
|
||||
|
||||
idx = hstoreFindKey(hs, 0,
|
||||
NameStr(tupdesc->attrs[i]->attname),
|
||||
strlen(NameStr(tupdesc->attrs[i]->attname)));
|
||||
NameStr(att->attname),
|
||||
strlen(NameStr(att->attname)));
|
||||
|
||||
/*
|
||||
* we can't just skip here if the key wasn't found since we might have
|
||||
@ -1082,7 +1084,7 @@ hstore_populate_record(PG_FUNCTION_ARGS)
|
||||
*/
|
||||
values[i] = InputFunctionCall(&column_info->proc, NULL,
|
||||
column_info->typioparam,
|
||||
tupdesc->attrs[i]->atttypmod);
|
||||
att->atttypmod);
|
||||
nulls[i] = true;
|
||||
}
|
||||
else
|
||||
@ -1094,7 +1096,7 @@ hstore_populate_record(PG_FUNCTION_ARGS)
|
||||
|
||||
values[i] = InputFunctionCall(&column_info->proc, value,
|
||||
column_info->typioparam,
|
||||
tupdesc->attrs[i]->atttypmod);
|
||||
att->atttypmod);
|
||||
nulls[i] = false;
|
||||
}
|
||||
}
|
||||
|
@ -316,7 +316,7 @@ tuple_data_split_internal(Oid relid, char *tupdata,
|
||||
bool is_null;
|
||||
bytea *attr_data = NULL;
|
||||
|
||||
attr = tupdesc->attrs[i];
|
||||
attr = TupleDescAttr(tupdesc, i);
|
||||
is_null = (t_infomask & HEAP_HASNULL) && att_isnull(i, t_bits);
|
||||
|
||||
/*
|
||||
@ -334,7 +334,7 @@ tuple_data_split_internal(Oid relid, char *tupdata,
|
||||
|
||||
if (attr->attlen == -1)
|
||||
{
|
||||
off = att_align_pointer(off, tupdesc->attrs[i]->attalign, -1,
|
||||
off = att_align_pointer(off, attr->attalign, -1,
|
||||
tupdata + off);
|
||||
|
||||
/*
|
||||
@ -353,7 +353,7 @@ tuple_data_split_internal(Oid relid, char *tupdata,
|
||||
}
|
||||
else
|
||||
{
|
||||
off = att_align_nominal(off, tupdesc->attrs[i]->attalign);
|
||||
off = att_align_nominal(off, attr->attalign);
|
||||
len = attr->attlen;
|
||||
}
|
||||
|
||||
@ -371,7 +371,7 @@ tuple_data_split_internal(Oid relid, char *tupdata,
|
||||
memcpy(VARDATA(attr_data), tupdata + off, len);
|
||||
}
|
||||
|
||||
off = att_addlength_pointer(off, tupdesc->attrs[i]->attlen,
|
||||
off = att_addlength_pointer(off, attr->attlen,
|
||||
tupdata + off);
|
||||
}
|
||||
|
||||
|
@ -253,7 +253,7 @@ page_header(PG_FUNCTION_ARGS)
|
||||
lsn = PageGetLSN(page);
|
||||
|
||||
/* pageinspect >= 1.2 uses pg_lsn instead of text for the LSN field. */
|
||||
if (tupdesc->attrs[0]->atttypid == TEXTOID)
|
||||
if (TupleDescAttr(tupdesc, 0)->atttypid == TEXTOID)
|
||||
{
|
||||
char lsnchar[64];
|
||||
|
||||
|
@ -1115,7 +1115,7 @@ deparseTargetList(StringInfo buf,
|
||||
first = true;
|
||||
for (i = 1; i <= tupdesc->natts; i++)
|
||||
{
|
||||
Form_pg_attribute attr = tupdesc->attrs[i - 1];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, i - 1);
|
||||
|
||||
/* Ignore dropped attributes. */
|
||||
if (attr->attisdropped)
|
||||
@ -1851,7 +1851,7 @@ deparseAnalyzeSql(StringInfo buf, Relation rel, List **retrieved_attrs)
|
||||
for (i = 0; i < tupdesc->natts; i++)
|
||||
{
|
||||
/* Ignore dropped columns. */
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
if (TupleDescAttr(tupdesc, i)->attisdropped)
|
||||
continue;
|
||||
|
||||
if (!first)
|
||||
@ -1859,7 +1859,7 @@ deparseAnalyzeSql(StringInfo buf, Relation rel, List **retrieved_attrs)
|
||||
first = false;
|
||||
|
||||
/* Use attribute name or column_name option. */
|
||||
colname = NameStr(tupdesc->attrs[i]->attname);
|
||||
colname = NameStr(TupleDescAttr(tupdesc, i)->attname);
|
||||
options = GetForeignColumnOptions(relid, i + 1);
|
||||
|
||||
foreach(lc, options)
|
||||
|
@ -1575,7 +1575,7 @@ postgresPlanForeignModify(PlannerInfo *root,
|
||||
|
||||
for (attnum = 1; attnum <= tupdesc->natts; attnum++)
|
||||
{
|
||||
Form_pg_attribute attr = tupdesc->attrs[attnum - 1];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, attnum - 1);
|
||||
|
||||
if (!attr->attisdropped)
|
||||
targetAttrs = lappend_int(targetAttrs, attnum);
|
||||
@ -1675,6 +1675,7 @@ postgresBeginForeignModify(ModifyTableState *mtstate,
|
||||
Oid typefnoid;
|
||||
bool isvarlena;
|
||||
ListCell *lc;
|
||||
TupleDesc tupdesc = RelationGetDescr(rel);
|
||||
|
||||
/*
|
||||
* Do nothing in EXPLAIN (no ANALYZE) case. resultRelInfo->ri_FdwState
|
||||
@ -1719,7 +1720,7 @@ postgresBeginForeignModify(ModifyTableState *mtstate,
|
||||
|
||||
/* Prepare for input conversion of RETURNING results. */
|
||||
if (fmstate->has_returning)
|
||||
fmstate->attinmeta = TupleDescGetAttInMetadata(RelationGetDescr(rel));
|
||||
fmstate->attinmeta = TupleDescGetAttInMetadata(tupdesc);
|
||||
|
||||
/* Prepare for output conversion of parameters used in prepared stmt. */
|
||||
n_params = list_length(fmstate->target_attrs) + 1;
|
||||
@ -1748,7 +1749,7 @@ postgresBeginForeignModify(ModifyTableState *mtstate,
|
||||
foreach(lc, fmstate->target_attrs)
|
||||
{
|
||||
int attnum = lfirst_int(lc);
|
||||
Form_pg_attribute attr = RelationGetDescr(rel)->attrs[attnum - 1];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, attnum - 1);
|
||||
|
||||
Assert(!attr->attisdropped);
|
||||
|
||||
@ -5090,9 +5091,10 @@ conversion_error_callback(void *arg)
|
||||
{
|
||||
/* error occurred in a scan against a foreign table */
|
||||
TupleDesc tupdesc = RelationGetDescr(errpos->rel);
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, errpos->cur_attno - 1);
|
||||
|
||||
if (errpos->cur_attno > 0 && errpos->cur_attno <= tupdesc->natts)
|
||||
attname = NameStr(tupdesc->attrs[errpos->cur_attno - 1]->attname);
|
||||
attname = NameStr(attr->attname);
|
||||
else if (errpos->cur_attno == SelfItemPointerAttributeNumber)
|
||||
attname = "ctid";
|
||||
else if (errpos->cur_attno == ObjectIdAttributeNumber)
|
||||
|
@ -328,7 +328,7 @@ timetravel(PG_FUNCTION_ARGS)
|
||||
for (i = 1; i <= natts; i++)
|
||||
{
|
||||
ctypes[i - 1] = SPI_gettypeid(tupdesc, i);
|
||||
if (!(tupdesc->attrs[i - 1]->attisdropped)) /* skip dropped columns */
|
||||
if (!(TupleDescAttr(tupdesc, i - 1)->attisdropped)) /* skip dropped columns */
|
||||
{
|
||||
snprintf(sql + strlen(sql), sizeof(sql) - strlen(sql), "%c$%d", separ, i);
|
||||
separ = ',';
|
||||
|
@ -1421,7 +1421,7 @@ build_tuplestore_recursively(char *key_fld,
|
||||
* Check expected (query runtime) tupdesc suitable for Connectby
|
||||
*/
|
||||
static void
|
||||
validateConnectbyTupleDesc(TupleDesc tupdesc, bool show_branch, bool show_serial)
|
||||
validateConnectbyTupleDesc(TupleDesc td, bool show_branch, bool show_serial)
|
||||
{
|
||||
int serial_column = 0;
|
||||
|
||||
@ -1431,7 +1431,7 @@ validateConnectbyTupleDesc(TupleDesc tupdesc, bool show_branch, bool show_serial
|
||||
/* are there the correct number of columns */
|
||||
if (show_branch)
|
||||
{
|
||||
if (tupdesc->natts != (CONNECTBY_NCOLS + serial_column))
|
||||
if (td->natts != (CONNECTBY_NCOLS + serial_column))
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_DATATYPE_MISMATCH),
|
||||
errmsg("invalid return type"),
|
||||
@ -1440,7 +1440,7 @@ validateConnectbyTupleDesc(TupleDesc tupdesc, bool show_branch, bool show_serial
|
||||
}
|
||||
else
|
||||
{
|
||||
if (tupdesc->natts != CONNECTBY_NCOLS_NOBRANCH + serial_column)
|
||||
if (td->natts != CONNECTBY_NCOLS_NOBRANCH + serial_column)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_DATATYPE_MISMATCH),
|
||||
errmsg("invalid return type"),
|
||||
@ -1449,14 +1449,14 @@ validateConnectbyTupleDesc(TupleDesc tupdesc, bool show_branch, bool show_serial
|
||||
}
|
||||
|
||||
/* check that the types of the first two columns match */
|
||||
if (tupdesc->attrs[0]->atttypid != tupdesc->attrs[1]->atttypid)
|
||||
if (TupleDescAttr(td, 0)->atttypid != TupleDescAttr(td, 1)->atttypid)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_DATATYPE_MISMATCH),
|
||||
errmsg("invalid return type"),
|
||||
errdetail("First two columns must be the same type.")));
|
||||
|
||||
/* check that the type of the third column is INT4 */
|
||||
if (tupdesc->attrs[2]->atttypid != INT4OID)
|
||||
if (TupleDescAttr(td, 2)->atttypid != INT4OID)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_DATATYPE_MISMATCH),
|
||||
errmsg("invalid return type"),
|
||||
@ -1464,7 +1464,7 @@ validateConnectbyTupleDesc(TupleDesc tupdesc, bool show_branch, bool show_serial
|
||||
format_type_be(INT4OID))));
|
||||
|
||||
/* check that the type of the fourth column is TEXT if applicable */
|
||||
if (show_branch && tupdesc->attrs[3]->atttypid != TEXTOID)
|
||||
if (show_branch && TupleDescAttr(td, 3)->atttypid != TEXTOID)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_DATATYPE_MISMATCH),
|
||||
errmsg("invalid return type"),
|
||||
@ -1472,7 +1472,8 @@ validateConnectbyTupleDesc(TupleDesc tupdesc, bool show_branch, bool show_serial
|
||||
format_type_be(TEXTOID))));
|
||||
|
||||
/* check that the type of the fifth column is INT4 */
|
||||
if (show_branch && show_serial && tupdesc->attrs[4]->atttypid != INT4OID)
|
||||
if (show_branch && show_serial &&
|
||||
TupleDescAttr(td, 4)->atttypid != INT4OID)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_DATATYPE_MISMATCH),
|
||||
errmsg("query-specified return tuple not valid for Connectby: "
|
||||
@ -1480,7 +1481,8 @@ validateConnectbyTupleDesc(TupleDesc tupdesc, bool show_branch, bool show_serial
|
||||
format_type_be(INT4OID))));
|
||||
|
||||
/* check that the type of the fifth column is INT4 */
|
||||
if (!show_branch && show_serial && tupdesc->attrs[3]->atttypid != INT4OID)
|
||||
if (!show_branch && show_serial &&
|
||||
TupleDescAttr(td, 3)->atttypid != INT4OID)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_DATATYPE_MISMATCH),
|
||||
errmsg("query-specified return tuple not valid for Connectby: "
|
||||
@ -1514,10 +1516,10 @@ compatConnectbyTupleDescs(TupleDesc ret_tupdesc, TupleDesc sql_tupdesc)
|
||||
* These columns must match the result type indicated by the calling
|
||||
* query.
|
||||
*/
|
||||
ret_atttypid = ret_tupdesc->attrs[0]->atttypid;
|
||||
sql_atttypid = sql_tupdesc->attrs[0]->atttypid;
|
||||
ret_atttypmod = ret_tupdesc->attrs[0]->atttypmod;
|
||||
sql_atttypmod = sql_tupdesc->attrs[0]->atttypmod;
|
||||
ret_atttypid = TupleDescAttr(ret_tupdesc, 0)->atttypid;
|
||||
sql_atttypid = TupleDescAttr(sql_tupdesc, 0)->atttypid;
|
||||
ret_atttypmod = TupleDescAttr(ret_tupdesc, 0)->atttypmod;
|
||||
sql_atttypmod = TupleDescAttr(sql_tupdesc, 0)->atttypmod;
|
||||
if (ret_atttypid != sql_atttypid ||
|
||||
(ret_atttypmod >= 0 && ret_atttypmod != sql_atttypmod))
|
||||
ereport(ERROR,
|
||||
@ -1528,10 +1530,10 @@ compatConnectbyTupleDescs(TupleDesc ret_tupdesc, TupleDesc sql_tupdesc)
|
||||
format_type_with_typemod(ret_atttypid, ret_atttypmod),
|
||||
format_type_with_typemod(sql_atttypid, sql_atttypmod))));
|
||||
|
||||
ret_atttypid = ret_tupdesc->attrs[1]->atttypid;
|
||||
sql_atttypid = sql_tupdesc->attrs[1]->atttypid;
|
||||
ret_atttypmod = ret_tupdesc->attrs[1]->atttypmod;
|
||||
sql_atttypmod = sql_tupdesc->attrs[1]->atttypmod;
|
||||
ret_atttypid = TupleDescAttr(ret_tupdesc, 1)->atttypid;
|
||||
sql_atttypid = TupleDescAttr(sql_tupdesc, 1)->atttypid;
|
||||
ret_atttypmod = TupleDescAttr(ret_tupdesc, 1)->atttypmod;
|
||||
sql_atttypmod = TupleDescAttr(sql_tupdesc, 1)->atttypmod;
|
||||
if (ret_atttypid != sql_atttypid ||
|
||||
(ret_atttypmod >= 0 && ret_atttypmod != sql_atttypmod))
|
||||
ereport(ERROR,
|
||||
@ -1562,8 +1564,8 @@ compatCrosstabTupleDescs(TupleDesc ret_tupdesc, TupleDesc sql_tupdesc)
|
||||
return false;
|
||||
|
||||
/* check the rowid types match */
|
||||
ret_atttypid = ret_tupdesc->attrs[0]->atttypid;
|
||||
sql_atttypid = sql_tupdesc->attrs[0]->atttypid;
|
||||
ret_atttypid = TupleDescAttr(ret_tupdesc, 0)->atttypid;
|
||||
sql_atttypid = TupleDescAttr(sql_tupdesc, 0)->atttypid;
|
||||
if (ret_atttypid != sql_atttypid)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_DATATYPE_MISMATCH),
|
||||
@ -1576,10 +1578,10 @@ compatCrosstabTupleDescs(TupleDesc ret_tupdesc, TupleDesc sql_tupdesc)
|
||||
* attribute [2] of the sql tuple should match attributes [1] to [natts]
|
||||
* of the return tuple
|
||||
*/
|
||||
sql_attr = sql_tupdesc->attrs[2];
|
||||
sql_attr = TupleDescAttr(sql_tupdesc, 2);
|
||||
for (i = 1; i < ret_tupdesc->natts; i++)
|
||||
{
|
||||
ret_attr = ret_tupdesc->attrs[i];
|
||||
ret_attr = TupleDescAttr(ret_tupdesc, i);
|
||||
|
||||
if (ret_attr->atttypid != sql_attr->atttypid)
|
||||
return false;
|
||||
|
@ -153,9 +153,10 @@ triggered_change_notification(PG_FUNCTION_ARGS)
|
||||
for (i = 0; i < numatts; i++)
|
||||
{
|
||||
int colno = index->indkey.values[i];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, colno - 1);
|
||||
|
||||
appendStringInfoCharMacro(payload, ',');
|
||||
strcpy_quoted(payload, NameStr((tupdesc->attrs[colno - 1])->attname), '"');
|
||||
strcpy_quoted(payload, NameStr(attr->attname), '"');
|
||||
appendStringInfoCharMacro(payload, '=');
|
||||
strcpy_quoted(payload, SPI_getvalue(trigtuple, tupdesc, colno), '\'');
|
||||
}
|
||||
|
@ -330,7 +330,7 @@ tuple_to_stringinfo(StringInfo s, TupleDesc tupdesc, HeapTuple tuple, bool skip_
|
||||
Datum origval; /* possibly toasted Datum */
|
||||
bool isnull; /* column is null? */
|
||||
|
||||
attr = tupdesc->attrs[natt];
|
||||
attr = TupleDescAttr(tupdesc, natt);
|
||||
|
||||
/*
|
||||
* don't print dropped columns, we can't be sure everything is
|
||||
|
@ -473,7 +473,8 @@ bringetbitmap(IndexScanDesc scan, TIDBitmap *tbm)
|
||||
*/
|
||||
Assert((key->sk_flags & SK_ISNULL) ||
|
||||
(key->sk_collation ==
|
||||
bdesc->bd_tupdesc->attrs[keyattno - 1]->attcollation));
|
||||
TupleDescAttr(bdesc->bd_tupdesc,
|
||||
keyattno - 1)->attcollation));
|
||||
|
||||
/* First time this column? look up consistent function */
|
||||
if (consistentFn[keyattno - 1].fn_oid == InvalidOid)
|
||||
@ -622,6 +623,7 @@ brinbuildCallback(Relation index,
|
||||
{
|
||||
FmgrInfo *addValue;
|
||||
BrinValues *col;
|
||||
Form_pg_attribute attr = TupleDescAttr(state->bs_bdesc->bd_tupdesc, i);
|
||||
|
||||
col = &state->bs_dtuple->bt_columns[i];
|
||||
addValue = index_getprocinfo(index, i + 1,
|
||||
@ -631,7 +633,7 @@ brinbuildCallback(Relation index,
|
||||
* Update dtuple state, if and as necessary.
|
||||
*/
|
||||
FunctionCall4Coll(addValue,
|
||||
state->bs_bdesc->bd_tupdesc->attrs[i]->attcollation,
|
||||
attr->attcollation,
|
||||
PointerGetDatum(state->bs_bdesc),
|
||||
PointerGetDatum(col),
|
||||
values[i], isnull[i]);
|
||||
@ -1019,12 +1021,12 @@ brin_build_desc(Relation rel)
|
||||
for (keyno = 0; keyno < tupdesc->natts; keyno++)
|
||||
{
|
||||
FmgrInfo *opcInfoFn;
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, keyno);
|
||||
|
||||
opcInfoFn = index_getprocinfo(rel, keyno + 1, BRIN_PROCNUM_OPCINFO);
|
||||
|
||||
opcinfo[keyno] = (BrinOpcInfo *)
|
||||
DatumGetPointer(FunctionCall1(opcInfoFn,
|
||||
tupdesc->attrs[keyno]->atttypid));
|
||||
DatumGetPointer(FunctionCall1(opcInfoFn, attr->atttypid));
|
||||
totalstored += opcinfo[keyno]->oi_nstored;
|
||||
}
|
||||
|
||||
|
@ -157,7 +157,7 @@ brin_inclusion_add_value(PG_FUNCTION_ARGS)
|
||||
}
|
||||
|
||||
attno = column->bv_attno;
|
||||
attr = bdesc->bd_tupdesc->attrs[attno - 1];
|
||||
attr = TupleDescAttr(bdesc->bd_tupdesc, attno - 1);
|
||||
|
||||
/*
|
||||
* If the recorded value is null, copy the new value (which we know to be
|
||||
@ -516,7 +516,7 @@ brin_inclusion_union(PG_FUNCTION_ARGS)
|
||||
PG_RETURN_VOID();
|
||||
|
||||
attno = col_a->bv_attno;
|
||||
attr = bdesc->bd_tupdesc->attrs[attno - 1];
|
||||
attr = TupleDescAttr(bdesc->bd_tupdesc, attno - 1);
|
||||
|
||||
/*
|
||||
* Adjust "allnulls". If A doesn't have values, just copy the values from
|
||||
@ -675,7 +675,7 @@ inclusion_get_strategy_procinfo(BrinDesc *bdesc, uint16 attno, Oid subtype,
|
||||
bool isNull;
|
||||
|
||||
opfamily = bdesc->bd_index->rd_opfamily[attno - 1];
|
||||
attr = bdesc->bd_tupdesc->attrs[attno - 1];
|
||||
attr = TupleDescAttr(bdesc->bd_tupdesc, attno - 1);
|
||||
tuple = SearchSysCache4(AMOPSTRATEGY, ObjectIdGetDatum(opfamily),
|
||||
ObjectIdGetDatum(attr->atttypid),
|
||||
ObjectIdGetDatum(subtype),
|
||||
|
@ -90,7 +90,7 @@ brin_minmax_add_value(PG_FUNCTION_ARGS)
|
||||
}
|
||||
|
||||
attno = column->bv_attno;
|
||||
attr = bdesc->bd_tupdesc->attrs[attno - 1];
|
||||
attr = TupleDescAttr(bdesc->bd_tupdesc, attno - 1);
|
||||
|
||||
/*
|
||||
* If the recorded value is null, store the new value (which we know to be
|
||||
@ -260,7 +260,7 @@ brin_minmax_union(PG_FUNCTION_ARGS)
|
||||
PG_RETURN_VOID();
|
||||
|
||||
attno = col_a->bv_attno;
|
||||
attr = bdesc->bd_tupdesc->attrs[attno - 1];
|
||||
attr = TupleDescAttr(bdesc->bd_tupdesc, attno - 1);
|
||||
|
||||
/*
|
||||
* Adjust "allnulls". If A doesn't have values, just copy the values from
|
||||
@ -347,7 +347,7 @@ minmax_get_strategy_procinfo(BrinDesc *bdesc, uint16 attno, Oid subtype,
|
||||
bool isNull;
|
||||
|
||||
opfamily = bdesc->bd_index->rd_opfamily[attno - 1];
|
||||
attr = bdesc->bd_tupdesc->attrs[attno - 1];
|
||||
attr = TupleDescAttr(bdesc->bd_tupdesc, attno - 1);
|
||||
tuple = SearchSysCache4(AMOPSTRATEGY, ObjectIdGetDatum(opfamily),
|
||||
ObjectIdGetDatum(attr->atttypid),
|
||||
ObjectIdGetDatum(subtype),
|
||||
|
@ -559,7 +559,7 @@ brin_deconstruct_tuple(BrinDesc *brdesc,
|
||||
datumno < brdesc->bd_info[attnum]->oi_nstored;
|
||||
datumno++)
|
||||
{
|
||||
Form_pg_attribute thisatt = diskdsc->attrs[stored];
|
||||
Form_pg_attribute thisatt = TupleDescAttr(diskdsc, stored);
|
||||
|
||||
if (thisatt->attlen == -1)
|
||||
{
|
||||
|
@ -89,7 +89,6 @@ heap_compute_data_size(TupleDesc tupleDesc,
|
||||
Size data_length = 0;
|
||||
int i;
|
||||
int numberOfAttributes = tupleDesc->natts;
|
||||
Form_pg_attribute *att = tupleDesc->attrs;
|
||||
|
||||
for (i = 0; i < numberOfAttributes; i++)
|
||||
{
|
||||
@ -100,7 +99,7 @@ heap_compute_data_size(TupleDesc tupleDesc,
|
||||
continue;
|
||||
|
||||
val = values[i];
|
||||
atti = att[i];
|
||||
atti = TupleDescAttr(tupleDesc, i);
|
||||
|
||||
if (ATT_IS_PACKABLE(atti) &&
|
||||
VARATT_CAN_MAKE_SHORT(DatumGetPointer(val)))
|
||||
@ -152,7 +151,6 @@ heap_fill_tuple(TupleDesc tupleDesc,
|
||||
int bitmask;
|
||||
int i;
|
||||
int numberOfAttributes = tupleDesc->natts;
|
||||
Form_pg_attribute *att = tupleDesc->attrs;
|
||||
|
||||
#ifdef USE_ASSERT_CHECKING
|
||||
char *start = data;
|
||||
@ -174,6 +172,7 @@ heap_fill_tuple(TupleDesc tupleDesc,
|
||||
|
||||
for (i = 0; i < numberOfAttributes; i++)
|
||||
{
|
||||
Form_pg_attribute att = TupleDescAttr(tupleDesc, i);
|
||||
Size data_length;
|
||||
|
||||
if (bit != NULL)
|
||||
@ -201,14 +200,14 @@ heap_fill_tuple(TupleDesc tupleDesc,
|
||||
* an offset. This is a bit of a hack.
|
||||
*/
|
||||
|
||||
if (att[i]->attbyval)
|
||||
if (att->attbyval)
|
||||
{
|
||||
/* pass-by-value */
|
||||
data = (char *) att_align_nominal(data, att[i]->attalign);
|
||||
store_att_byval(data, values[i], att[i]->attlen);
|
||||
data_length = att[i]->attlen;
|
||||
data = (char *) att_align_nominal(data, att->attalign);
|
||||
store_att_byval(data, values[i], att->attlen);
|
||||
data_length = att->attlen;
|
||||
}
|
||||
else if (att[i]->attlen == -1)
|
||||
else if (att->attlen == -1)
|
||||
{
|
||||
/* varlena */
|
||||
Pointer val = DatumGetPointer(values[i]);
|
||||
@ -225,7 +224,7 @@ heap_fill_tuple(TupleDesc tupleDesc,
|
||||
ExpandedObjectHeader *eoh = DatumGetEOHP(values[i]);
|
||||
|
||||
data = (char *) att_align_nominal(data,
|
||||
att[i]->attalign);
|
||||
att->attalign);
|
||||
data_length = EOH_get_flat_size(eoh);
|
||||
EOH_flatten_into(eoh, data, data_length);
|
||||
}
|
||||
@ -243,7 +242,7 @@ heap_fill_tuple(TupleDesc tupleDesc,
|
||||
data_length = VARSIZE_SHORT(val);
|
||||
memcpy(data, val, data_length);
|
||||
}
|
||||
else if (VARLENA_ATT_IS_PACKABLE(att[i]) &&
|
||||
else if (VARLENA_ATT_IS_PACKABLE(att) &&
|
||||
VARATT_CAN_MAKE_SHORT(val))
|
||||
{
|
||||
/* convert to short varlena -- no alignment */
|
||||
@ -255,25 +254,25 @@ heap_fill_tuple(TupleDesc tupleDesc,
|
||||
{
|
||||
/* full 4-byte header varlena */
|
||||
data = (char *) att_align_nominal(data,
|
||||
att[i]->attalign);
|
||||
att->attalign);
|
||||
data_length = VARSIZE(val);
|
||||
memcpy(data, val, data_length);
|
||||
}
|
||||
}
|
||||
else if (att[i]->attlen == -2)
|
||||
else if (att->attlen == -2)
|
||||
{
|
||||
/* cstring ... never needs alignment */
|
||||
*infomask |= HEAP_HASVARWIDTH;
|
||||
Assert(att[i]->attalign == 'c');
|
||||
Assert(att->attalign == 'c');
|
||||
data_length = strlen(DatumGetCString(values[i])) + 1;
|
||||
memcpy(data, DatumGetPointer(values[i]), data_length);
|
||||
}
|
||||
else
|
||||
{
|
||||
/* fixed-length pass-by-reference */
|
||||
data = (char *) att_align_nominal(data, att[i]->attalign);
|
||||
Assert(att[i]->attlen > 0);
|
||||
data_length = att[i]->attlen;
|
||||
data = (char *) att_align_nominal(data, att->attalign);
|
||||
Assert(att->attlen > 0);
|
||||
data_length = att->attlen;
|
||||
memcpy(data, DatumGetPointer(values[i]), data_length);
|
||||
}
|
||||
|
||||
@ -354,7 +353,6 @@ nocachegetattr(HeapTuple tuple,
|
||||
TupleDesc tupleDesc)
|
||||
{
|
||||
HeapTupleHeader tup = tuple->t_data;
|
||||
Form_pg_attribute *att = tupleDesc->attrs;
|
||||
char *tp; /* ptr to data part of tuple */
|
||||
bits8 *bp = tup->t_bits; /* ptr to null bitmap in tuple */
|
||||
bool slow = false; /* do we have to walk attrs? */
|
||||
@ -404,15 +402,15 @@ nocachegetattr(HeapTuple tuple,
|
||||
|
||||
if (!slow)
|
||||
{
|
||||
Form_pg_attribute att;
|
||||
|
||||
/*
|
||||
* If we get here, there are no nulls up to and including the target
|
||||
* attribute. If we have a cached offset, we can use it.
|
||||
*/
|
||||
if (att[attnum]->attcacheoff >= 0)
|
||||
{
|
||||
return fetchatt(att[attnum],
|
||||
tp + att[attnum]->attcacheoff);
|
||||
}
|
||||
att = TupleDescAttr(tupleDesc, attnum);
|
||||
if (att->attcacheoff >= 0)
|
||||
return fetchatt(att, tp + att->attcacheoff);
|
||||
|
||||
/*
|
||||
* Otherwise, check for non-fixed-length attrs up to and including
|
||||
@ -425,7 +423,7 @@ nocachegetattr(HeapTuple tuple,
|
||||
|
||||
for (j = 0; j <= attnum; j++)
|
||||
{
|
||||
if (att[j]->attlen <= 0)
|
||||
if (TupleDescAttr(tupleDesc, j)->attlen <= 0)
|
||||
{
|
||||
slow = true;
|
||||
break;
|
||||
@ -448,29 +446,32 @@ nocachegetattr(HeapTuple tuple,
|
||||
* fixed-width columns, in hope of avoiding future visits to this
|
||||
* routine.
|
||||
*/
|
||||
att[0]->attcacheoff = 0;
|
||||
TupleDescAttr(tupleDesc, 0)->attcacheoff = 0;
|
||||
|
||||
/* we might have set some offsets in the slow path previously */
|
||||
while (j < natts && att[j]->attcacheoff > 0)
|
||||
while (j < natts && TupleDescAttr(tupleDesc, j)->attcacheoff > 0)
|
||||
j++;
|
||||
|
||||
off = att[j - 1]->attcacheoff + att[j - 1]->attlen;
|
||||
off = TupleDescAttr(tupleDesc, j - 1)->attcacheoff +
|
||||
TupleDescAttr(tupleDesc, j - 1)->attlen;
|
||||
|
||||
for (; j < natts; j++)
|
||||
{
|
||||
if (att[j]->attlen <= 0)
|
||||
Form_pg_attribute att = TupleDescAttr(tupleDesc, j);
|
||||
|
||||
if (att->attlen <= 0)
|
||||
break;
|
||||
|
||||
off = att_align_nominal(off, att[j]->attalign);
|
||||
off = att_align_nominal(off, att->attalign);
|
||||
|
||||
att[j]->attcacheoff = off;
|
||||
att->attcacheoff = off;
|
||||
|
||||
off += att[j]->attlen;
|
||||
off += att->attlen;
|
||||
}
|
||||
|
||||
Assert(j > attnum);
|
||||
|
||||
off = att[attnum]->attcacheoff;
|
||||
off = TupleDescAttr(tupleDesc, attnum)->attcacheoff;
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -490,6 +491,8 @@ nocachegetattr(HeapTuple tuple,
|
||||
off = 0;
|
||||
for (i = 0;; i++) /* loop exit is at "break" */
|
||||
{
|
||||
Form_pg_attribute att = TupleDescAttr(tupleDesc, i);
|
||||
|
||||
if (HeapTupleHasNulls(tuple) && att_isnull(i, bp))
|
||||
{
|
||||
usecache = false;
|
||||
@ -497,9 +500,9 @@ nocachegetattr(HeapTuple tuple,
|
||||
}
|
||||
|
||||
/* If we know the next offset, we can skip the rest */
|
||||
if (usecache && att[i]->attcacheoff >= 0)
|
||||
off = att[i]->attcacheoff;
|
||||
else if (att[i]->attlen == -1)
|
||||
if (usecache && att->attcacheoff >= 0)
|
||||
off = att->attcacheoff;
|
||||
else if (att->attlen == -1)
|
||||
{
|
||||
/*
|
||||
* We can only cache the offset for a varlena attribute if the
|
||||
@ -508,11 +511,11 @@ nocachegetattr(HeapTuple tuple,
|
||||
* either an aligned or unaligned value.
|
||||
*/
|
||||
if (usecache &&
|
||||
off == att_align_nominal(off, att[i]->attalign))
|
||||
att[i]->attcacheoff = off;
|
||||
off == att_align_nominal(off, att->attalign))
|
||||
att->attcacheoff = off;
|
||||
else
|
||||
{
|
||||
off = att_align_pointer(off, att[i]->attalign, -1,
|
||||
off = att_align_pointer(off, att->attalign, -1,
|
||||
tp + off);
|
||||
usecache = false;
|
||||
}
|
||||
@ -520,23 +523,23 @@ nocachegetattr(HeapTuple tuple,
|
||||
else
|
||||
{
|
||||
/* not varlena, so safe to use att_align_nominal */
|
||||
off = att_align_nominal(off, att[i]->attalign);
|
||||
off = att_align_nominal(off, att->attalign);
|
||||
|
||||
if (usecache)
|
||||
att[i]->attcacheoff = off;
|
||||
att->attcacheoff = off;
|
||||
}
|
||||
|
||||
if (i == attnum)
|
||||
break;
|
||||
|
||||
off = att_addlength_pointer(off, att[i]->attlen, tp + off);
|
||||
off = att_addlength_pointer(off, att->attlen, tp + off);
|
||||
|
||||
if (usecache && att[i]->attlen <= 0)
|
||||
if (usecache && att->attlen <= 0)
|
||||
usecache = false;
|
||||
}
|
||||
}
|
||||
|
||||
return fetchatt(att[attnum], tp + off);
|
||||
return fetchatt(TupleDescAttr(tupleDesc, attnum), tp + off);
|
||||
}
|
||||
|
||||
/* ----------------
|
||||
@ -935,7 +938,6 @@ heap_deform_tuple(HeapTuple tuple, TupleDesc tupleDesc,
|
||||
{
|
||||
HeapTupleHeader tup = tuple->t_data;
|
||||
bool hasnulls = HeapTupleHasNulls(tuple);
|
||||
Form_pg_attribute *att = tupleDesc->attrs;
|
||||
int tdesc_natts = tupleDesc->natts;
|
||||
int natts; /* number of atts to extract */
|
||||
int attnum;
|
||||
@ -959,7 +961,7 @@ heap_deform_tuple(HeapTuple tuple, TupleDesc tupleDesc,
|
||||
|
||||
for (attnum = 0; attnum < natts; attnum++)
|
||||
{
|
||||
Form_pg_attribute thisatt = att[attnum];
|
||||
Form_pg_attribute thisatt = TupleDescAttr(tupleDesc, attnum);
|
||||
|
||||
if (hasnulls && att_isnull(attnum, bp))
|
||||
{
|
||||
@ -1039,7 +1041,6 @@ slot_deform_tuple(TupleTableSlot *slot, int natts)
|
||||
bool *isnull = slot->tts_isnull;
|
||||
HeapTupleHeader tup = tuple->t_data;
|
||||
bool hasnulls = HeapTupleHasNulls(tuple);
|
||||
Form_pg_attribute *att = tupleDesc->attrs;
|
||||
int attnum;
|
||||
char *tp; /* ptr to tuple data */
|
||||
long off; /* offset in tuple data */
|
||||
@ -1068,7 +1069,7 @@ slot_deform_tuple(TupleTableSlot *slot, int natts)
|
||||
|
||||
for (; attnum < natts; attnum++)
|
||||
{
|
||||
Form_pg_attribute thisatt = att[attnum];
|
||||
Form_pg_attribute thisatt = TupleDescAttr(tupleDesc, attnum);
|
||||
|
||||
if (hasnulls && att_isnull(attnum, bp))
|
||||
{
|
||||
@ -1209,7 +1210,7 @@ slot_getattr(TupleTableSlot *slot, int attnum, bool *isnull)
|
||||
* This case should not happen in normal use, but it could happen if we
|
||||
* are executing a plan cached before the column was dropped.
|
||||
*/
|
||||
if (tupleDesc->attrs[attnum - 1]->attisdropped)
|
||||
if (TupleDescAttr(tupleDesc, attnum - 1)->attisdropped)
|
||||
{
|
||||
*isnull = true;
|
||||
return (Datum) 0;
|
||||
|
@ -63,7 +63,7 @@ index_form_tuple(TupleDesc tupleDescriptor,
|
||||
#ifdef TOAST_INDEX_HACK
|
||||
for (i = 0; i < numberOfAttributes; i++)
|
||||
{
|
||||
Form_pg_attribute att = tupleDescriptor->attrs[i];
|
||||
Form_pg_attribute att = TupleDescAttr(tupleDescriptor, i);
|
||||
|
||||
untoasted_values[i] = values[i];
|
||||
untoasted_free[i] = false;
|
||||
@ -209,7 +209,6 @@ nocache_index_getattr(IndexTuple tup,
|
||||
int attnum,
|
||||
TupleDesc tupleDesc)
|
||||
{
|
||||
Form_pg_attribute *att = tupleDesc->attrs;
|
||||
char *tp; /* ptr to data part of tuple */
|
||||
bits8 *bp = NULL; /* ptr to null bitmap in tuple */
|
||||
bool slow = false; /* do we have to walk attrs? */
|
||||
@ -271,15 +270,15 @@ nocache_index_getattr(IndexTuple tup,
|
||||
|
||||
if (!slow)
|
||||
{
|
||||
Form_pg_attribute att;
|
||||
|
||||
/*
|
||||
* If we get here, there are no nulls up to and including the target
|
||||
* attribute. If we have a cached offset, we can use it.
|
||||
*/
|
||||
if (att[attnum]->attcacheoff >= 0)
|
||||
{
|
||||
return fetchatt(att[attnum],
|
||||
tp + att[attnum]->attcacheoff);
|
||||
}
|
||||
att = TupleDescAttr(tupleDesc, attnum);
|
||||
if (att->attcacheoff >= 0)
|
||||
return fetchatt(att, tp + att->attcacheoff);
|
||||
|
||||
/*
|
||||
* Otherwise, check for non-fixed-length attrs up to and including
|
||||
@ -292,7 +291,7 @@ nocache_index_getattr(IndexTuple tup,
|
||||
|
||||
for (j = 0; j <= attnum; j++)
|
||||
{
|
||||
if (att[j]->attlen <= 0)
|
||||
if (TupleDescAttr(tupleDesc, j)->attlen <= 0)
|
||||
{
|
||||
slow = true;
|
||||
break;
|
||||
@ -315,29 +314,32 @@ nocache_index_getattr(IndexTuple tup,
|
||||
* fixed-width columns, in hope of avoiding future visits to this
|
||||
* routine.
|
||||
*/
|
||||
att[0]->attcacheoff = 0;
|
||||
TupleDescAttr(tupleDesc, 0)->attcacheoff = 0;
|
||||
|
||||
/* we might have set some offsets in the slow path previously */
|
||||
while (j < natts && att[j]->attcacheoff > 0)
|
||||
while (j < natts && TupleDescAttr(tupleDesc, j)->attcacheoff > 0)
|
||||
j++;
|
||||
|
||||
off = att[j - 1]->attcacheoff + att[j - 1]->attlen;
|
||||
off = TupleDescAttr(tupleDesc, j - 1)->attcacheoff +
|
||||
TupleDescAttr(tupleDesc, j - 1)->attlen;
|
||||
|
||||
for (; j < natts; j++)
|
||||
{
|
||||
if (att[j]->attlen <= 0)
|
||||
Form_pg_attribute att = TupleDescAttr(tupleDesc, j);
|
||||
|
||||
if (att->attlen <= 0)
|
||||
break;
|
||||
|
||||
off = att_align_nominal(off, att[j]->attalign);
|
||||
off = att_align_nominal(off, att->attalign);
|
||||
|
||||
att[j]->attcacheoff = off;
|
||||
att->attcacheoff = off;
|
||||
|
||||
off += att[j]->attlen;
|
||||
off += att->attlen;
|
||||
}
|
||||
|
||||
Assert(j > attnum);
|
||||
|
||||
off = att[attnum]->attcacheoff;
|
||||
off = TupleDescAttr(tupleDesc, attnum)->attcacheoff;
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -357,6 +359,8 @@ nocache_index_getattr(IndexTuple tup,
|
||||
off = 0;
|
||||
for (i = 0;; i++) /* loop exit is at "break" */
|
||||
{
|
||||
Form_pg_attribute att = TupleDescAttr(tupleDesc, i);
|
||||
|
||||
if (IndexTupleHasNulls(tup) && att_isnull(i, bp))
|
||||
{
|
||||
usecache = false;
|
||||
@ -364,9 +368,9 @@ nocache_index_getattr(IndexTuple tup,
|
||||
}
|
||||
|
||||
/* If we know the next offset, we can skip the rest */
|
||||
if (usecache && att[i]->attcacheoff >= 0)
|
||||
off = att[i]->attcacheoff;
|
||||
else if (att[i]->attlen == -1)
|
||||
if (usecache && att->attcacheoff >= 0)
|
||||
off = att->attcacheoff;
|
||||
else if (att->attlen == -1)
|
||||
{
|
||||
/*
|
||||
* We can only cache the offset for a varlena attribute if the
|
||||
@ -375,11 +379,11 @@ nocache_index_getattr(IndexTuple tup,
|
||||
* either an aligned or unaligned value.
|
||||
*/
|
||||
if (usecache &&
|
||||
off == att_align_nominal(off, att[i]->attalign))
|
||||
att[i]->attcacheoff = off;
|
||||
off == att_align_nominal(off, att->attalign))
|
||||
att->attcacheoff = off;
|
||||
else
|
||||
{
|
||||
off = att_align_pointer(off, att[i]->attalign, -1,
|
||||
off = att_align_pointer(off, att->attalign, -1,
|
||||
tp + off);
|
||||
usecache = false;
|
||||
}
|
||||
@ -387,23 +391,23 @@ nocache_index_getattr(IndexTuple tup,
|
||||
else
|
||||
{
|
||||
/* not varlena, so safe to use att_align_nominal */
|
||||
off = att_align_nominal(off, att[i]->attalign);
|
||||
off = att_align_nominal(off, att->attalign);
|
||||
|
||||
if (usecache)
|
||||
att[i]->attcacheoff = off;
|
||||
att->attcacheoff = off;
|
||||
}
|
||||
|
||||
if (i == attnum)
|
||||
break;
|
||||
|
||||
off = att_addlength_pointer(off, att[i]->attlen, tp + off);
|
||||
off = att_addlength_pointer(off, att->attlen, tp + off);
|
||||
|
||||
if (usecache && att[i]->attlen <= 0)
|
||||
if (usecache && att->attlen <= 0)
|
||||
usecache = false;
|
||||
}
|
||||
}
|
||||
|
||||
return fetchatt(att[attnum], tp + off);
|
||||
return fetchatt(TupleDescAttr(tupleDesc, attnum), tp + off);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -38,7 +38,7 @@ printsimple_startup(DestReceiver *self, int operation, TupleDesc tupdesc)
|
||||
|
||||
for (i = 0; i < tupdesc->natts; ++i)
|
||||
{
|
||||
Form_pg_attribute attr = tupdesc->attrs[i];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, i);
|
||||
|
||||
pq_sendstring(&buf, NameStr(attr->attname));
|
||||
pq_sendint(&buf, 0, 4); /* table oid */
|
||||
@ -71,7 +71,7 @@ printsimple(TupleTableSlot *slot, DestReceiver *self)
|
||||
|
||||
for (i = 0; i < tupdesc->natts; ++i)
|
||||
{
|
||||
Form_pg_attribute attr = tupdesc->attrs[i];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, i);
|
||||
Datum value;
|
||||
|
||||
if (slot->tts_isnull[i])
|
||||
|
@ -187,7 +187,6 @@ printtup_startup(DestReceiver *self, int operation, TupleDesc typeinfo)
|
||||
void
|
||||
SendRowDescriptionMessage(TupleDesc typeinfo, List *targetlist, int16 *formats)
|
||||
{
|
||||
Form_pg_attribute *attrs = typeinfo->attrs;
|
||||
int natts = typeinfo->natts;
|
||||
int proto = PG_PROTOCOL_MAJOR(FrontendProtocol);
|
||||
int i;
|
||||
@ -199,10 +198,11 @@ SendRowDescriptionMessage(TupleDesc typeinfo, List *targetlist, int16 *formats)
|
||||
|
||||
for (i = 0; i < natts; ++i)
|
||||
{
|
||||
Oid atttypid = attrs[i]->atttypid;
|
||||
int32 atttypmod = attrs[i]->atttypmod;
|
||||
Form_pg_attribute att = TupleDescAttr(typeinfo, i);
|
||||
Oid atttypid = att->atttypid;
|
||||
int32 atttypmod = att->atttypmod;
|
||||
|
||||
pq_sendstring(&buf, NameStr(attrs[i]->attname));
|
||||
pq_sendstring(&buf, NameStr(att->attname));
|
||||
/* column ID info appears in protocol 3.0 and up */
|
||||
if (proto >= 3)
|
||||
{
|
||||
@ -228,7 +228,7 @@ SendRowDescriptionMessage(TupleDesc typeinfo, List *targetlist, int16 *formats)
|
||||
/* If column is a domain, send the base type and typmod instead */
|
||||
atttypid = getBaseTypeAndTypmod(atttypid, &atttypmod);
|
||||
pq_sendint(&buf, (int) atttypid, sizeof(atttypid));
|
||||
pq_sendint(&buf, attrs[i]->attlen, sizeof(attrs[i]->attlen));
|
||||
pq_sendint(&buf, att->attlen, sizeof(att->attlen));
|
||||
pq_sendint(&buf, atttypmod, sizeof(atttypmod));
|
||||
/* format info appears in protocol 3.0 and up */
|
||||
if (proto >= 3)
|
||||
@ -268,18 +268,19 @@ printtup_prepare_info(DR_printtup *myState, TupleDesc typeinfo, int numAttrs)
|
||||
{
|
||||
PrinttupAttrInfo *thisState = myState->myinfo + i;
|
||||
int16 format = (formats ? formats[i] : 0);
|
||||
Form_pg_attribute attr = TupleDescAttr(typeinfo, i);
|
||||
|
||||
thisState->format = format;
|
||||
if (format == 0)
|
||||
{
|
||||
getTypeOutputInfo(typeinfo->attrs[i]->atttypid,
|
||||
getTypeOutputInfo(attr->atttypid,
|
||||
&thisState->typoutput,
|
||||
&thisState->typisvarlena);
|
||||
fmgr_info(thisState->typoutput, &thisState->finfo);
|
||||
}
|
||||
else if (format == 1)
|
||||
{
|
||||
getTypeBinaryOutputInfo(typeinfo->attrs[i]->atttypid,
|
||||
getTypeBinaryOutputInfo(attr->atttypid,
|
||||
&thisState->typsend,
|
||||
&thisState->typisvarlena);
|
||||
fmgr_info(thisState->typsend, &thisState->finfo);
|
||||
@ -513,14 +514,13 @@ void
|
||||
debugStartup(DestReceiver *self, int operation, TupleDesc typeinfo)
|
||||
{
|
||||
int natts = typeinfo->natts;
|
||||
Form_pg_attribute *attinfo = typeinfo->attrs;
|
||||
int i;
|
||||
|
||||
/*
|
||||
* show the return type of the tuples
|
||||
*/
|
||||
for (i = 0; i < natts; ++i)
|
||||
printatt((unsigned) i + 1, attinfo[i], NULL);
|
||||
printatt((unsigned) i + 1, TupleDescAttr(typeinfo, i), NULL);
|
||||
printf("\t----\n");
|
||||
}
|
||||
|
||||
@ -545,12 +545,12 @@ debugtup(TupleTableSlot *slot, DestReceiver *self)
|
||||
attr = slot_getattr(slot, i + 1, &isnull);
|
||||
if (isnull)
|
||||
continue;
|
||||
getTypeOutputInfo(typeinfo->attrs[i]->atttypid,
|
||||
getTypeOutputInfo(TupleDescAttr(typeinfo, i)->atttypid,
|
||||
&typoutput, &typisvarlena);
|
||||
|
||||
value = OidOutputFunctionCall(typoutput, attr);
|
||||
|
||||
printatt((unsigned) i + 1, typeinfo->attrs[i], value);
|
||||
printatt((unsigned) i + 1, TupleDescAttr(typeinfo, i), value);
|
||||
}
|
||||
printf("\t----\n");
|
||||
|
||||
|
@ -84,7 +84,7 @@ convert_tuples_by_position(TupleDesc indesc,
|
||||
same = true;
|
||||
for (i = 0; i < n; i++)
|
||||
{
|
||||
Form_pg_attribute att = outdesc->attrs[i];
|
||||
Form_pg_attribute att = TupleDescAttr(outdesc, i);
|
||||
Oid atttypid;
|
||||
int32 atttypmod;
|
||||
|
||||
@ -95,7 +95,7 @@ convert_tuples_by_position(TupleDesc indesc,
|
||||
atttypmod = att->atttypmod;
|
||||
for (; j < indesc->natts; j++)
|
||||
{
|
||||
att = indesc->attrs[j];
|
||||
att = TupleDescAttr(indesc, j);
|
||||
if (att->attisdropped)
|
||||
continue;
|
||||
nincols++;
|
||||
@ -122,7 +122,7 @@ convert_tuples_by_position(TupleDesc indesc,
|
||||
/* Check for unused input columns */
|
||||
for (; j < indesc->natts; j++)
|
||||
{
|
||||
if (indesc->attrs[j]->attisdropped)
|
||||
if (TupleDescAttr(indesc, j)->attisdropped)
|
||||
continue;
|
||||
nincols++;
|
||||
same = false; /* we'll complain below */
|
||||
@ -149,6 +149,9 @@ convert_tuples_by_position(TupleDesc indesc,
|
||||
{
|
||||
for (i = 0; i < n; i++)
|
||||
{
|
||||
Form_pg_attribute inatt;
|
||||
Form_pg_attribute outatt;
|
||||
|
||||
if (attrMap[i] == (i + 1))
|
||||
continue;
|
||||
|
||||
@ -157,10 +160,12 @@ convert_tuples_by_position(TupleDesc indesc,
|
||||
* also dropped, we needn't convert. However, attlen and attalign
|
||||
* must agree.
|
||||
*/
|
||||
inatt = TupleDescAttr(indesc, i);
|
||||
outatt = TupleDescAttr(outdesc, i);
|
||||
if (attrMap[i] == 0 &&
|
||||
indesc->attrs[i]->attisdropped &&
|
||||
indesc->attrs[i]->attlen == outdesc->attrs[i]->attlen &&
|
||||
indesc->attrs[i]->attalign == outdesc->attrs[i]->attalign)
|
||||
inatt->attisdropped &&
|
||||
inatt->attlen == outatt->attlen &&
|
||||
inatt->attalign == outatt->attalign)
|
||||
continue;
|
||||
|
||||
same = false;
|
||||
@ -228,6 +233,9 @@ convert_tuples_by_name(TupleDesc indesc,
|
||||
same = true;
|
||||
for (i = 0; i < n; i++)
|
||||
{
|
||||
Form_pg_attribute inatt;
|
||||
Form_pg_attribute outatt;
|
||||
|
||||
if (attrMap[i] == (i + 1))
|
||||
continue;
|
||||
|
||||
@ -236,10 +244,12 @@ convert_tuples_by_name(TupleDesc indesc,
|
||||
* also dropped, we needn't convert. However, attlen and attalign
|
||||
* must agree.
|
||||
*/
|
||||
inatt = TupleDescAttr(indesc, i);
|
||||
outatt = TupleDescAttr(outdesc, i);
|
||||
if (attrMap[i] == 0 &&
|
||||
indesc->attrs[i]->attisdropped &&
|
||||
indesc->attrs[i]->attlen == outdesc->attrs[i]->attlen &&
|
||||
indesc->attrs[i]->attalign == outdesc->attrs[i]->attalign)
|
||||
inatt->attisdropped &&
|
||||
inatt->attlen == outatt->attlen &&
|
||||
inatt->attalign == outatt->attalign)
|
||||
continue;
|
||||
|
||||
same = false;
|
||||
@ -292,26 +302,27 @@ convert_tuples_by_name_map(TupleDesc indesc,
|
||||
attrMap = (AttrNumber *) palloc0(n * sizeof(AttrNumber));
|
||||
for (i = 0; i < n; i++)
|
||||
{
|
||||
Form_pg_attribute att = outdesc->attrs[i];
|
||||
Form_pg_attribute outatt = TupleDescAttr(outdesc, i);
|
||||
char *attname;
|
||||
Oid atttypid;
|
||||
int32 atttypmod;
|
||||
int j;
|
||||
|
||||
if (att->attisdropped)
|
||||
if (outatt->attisdropped)
|
||||
continue; /* attrMap[i] is already 0 */
|
||||
attname = NameStr(att->attname);
|
||||
atttypid = att->atttypid;
|
||||
atttypmod = att->atttypmod;
|
||||
attname = NameStr(outatt->attname);
|
||||
atttypid = outatt->atttypid;
|
||||
atttypmod = outatt->atttypmod;
|
||||
for (j = 0; j < indesc->natts; j++)
|
||||
{
|
||||
att = indesc->attrs[j];
|
||||
if (att->attisdropped)
|
||||
Form_pg_attribute inatt = TupleDescAttr(indesc, j);
|
||||
|
||||
if (inatt->attisdropped)
|
||||
continue;
|
||||
if (strcmp(attname, NameStr(att->attname)) == 0)
|
||||
if (strcmp(attname, NameStr(inatt->attname)) == 0)
|
||||
{
|
||||
/* Found it, check type */
|
||||
if (atttypid != att->atttypid || atttypmod != att->atttypmod)
|
||||
if (atttypid != inatt->atttypid || atttypmod != inatt->atttypmod)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_DATATYPE_MISMATCH),
|
||||
errmsg_internal("%s", _(msg)),
|
||||
|
@ -175,7 +175,9 @@ CreateTupleDescCopyConstr(TupleDesc tupdesc)
|
||||
|
||||
for (i = 0; i < desc->natts; i++)
|
||||
{
|
||||
memcpy(desc->attrs[i], tupdesc->attrs[i], ATTRIBUTE_FIXED_PART_SIZE);
|
||||
memcpy(TupleDescAttr(desc, i),
|
||||
TupleDescAttr(tupdesc, i),
|
||||
ATTRIBUTE_FIXED_PART_SIZE);
|
||||
}
|
||||
|
||||
if (constr)
|
||||
@ -230,6 +232,9 @@ void
|
||||
TupleDescCopyEntry(TupleDesc dst, AttrNumber dstAttno,
|
||||
TupleDesc src, AttrNumber srcAttno)
|
||||
{
|
||||
Form_pg_attribute dstAtt = TupleDescAttr(dst, dstAttno - 1);
|
||||
Form_pg_attribute srcAtt = TupleDescAttr(src, srcAttno - 1);
|
||||
|
||||
/*
|
||||
* sanity checks
|
||||
*/
|
||||
@ -240,8 +245,7 @@ TupleDescCopyEntry(TupleDesc dst, AttrNumber dstAttno,
|
||||
AssertArg(dstAttno >= 1);
|
||||
AssertArg(dstAttno <= dst->natts);
|
||||
|
||||
memcpy(dst->attrs[dstAttno - 1], src->attrs[srcAttno - 1],
|
||||
ATTRIBUTE_FIXED_PART_SIZE);
|
||||
memcpy(dstAtt, srcAtt, ATTRIBUTE_FIXED_PART_SIZE);
|
||||
|
||||
/*
|
||||
* Aside from updating the attno, we'd better reset attcacheoff.
|
||||
@ -252,13 +256,13 @@ TupleDescCopyEntry(TupleDesc dst, AttrNumber dstAttno,
|
||||
* by other uses of this function or TupleDescInitEntry. So we cheat a
|
||||
* bit to avoid a useless O(N^2) penalty.
|
||||
*/
|
||||
dst->attrs[dstAttno - 1]->attnum = dstAttno;
|
||||
dst->attrs[dstAttno - 1]->attcacheoff = -1;
|
||||
dstAtt->attnum = dstAttno;
|
||||
dstAtt->attcacheoff = -1;
|
||||
|
||||
/* since we're not copying constraints or defaults, clear these */
|
||||
dst->attrs[dstAttno - 1]->attnotnull = false;
|
||||
dst->attrs[dstAttno - 1]->atthasdef = false;
|
||||
dst->attrs[dstAttno - 1]->attidentity = '\0';
|
||||
dstAtt->attnotnull = false;
|
||||
dstAtt->atthasdef = false;
|
||||
dstAtt->attidentity = '\0';
|
||||
}
|
||||
|
||||
/*
|
||||
@ -366,8 +370,8 @@ equalTupleDescs(TupleDesc tupdesc1, TupleDesc tupdesc2)
|
||||
|
||||
for (i = 0; i < tupdesc1->natts; i++)
|
||||
{
|
||||
Form_pg_attribute attr1 = tupdesc1->attrs[i];
|
||||
Form_pg_attribute attr2 = tupdesc2->attrs[i];
|
||||
Form_pg_attribute attr1 = TupleDescAttr(tupdesc1, i);
|
||||
Form_pg_attribute attr2 = TupleDescAttr(tupdesc2, i);
|
||||
|
||||
/*
|
||||
* We do not need to check every single field here: we can disregard
|
||||
@ -515,7 +519,7 @@ TupleDescInitEntry(TupleDesc desc,
|
||||
/*
|
||||
* initialize the attribute fields
|
||||
*/
|
||||
att = desc->attrs[attributeNumber - 1];
|
||||
att = TupleDescAttr(desc, attributeNumber - 1);
|
||||
|
||||
att->attrelid = 0; /* dummy value */
|
||||
|
||||
@ -580,7 +584,7 @@ TupleDescInitBuiltinEntry(TupleDesc desc,
|
||||
AssertArg(attributeNumber <= desc->natts);
|
||||
|
||||
/* initialize the attribute fields */
|
||||
att = desc->attrs[attributeNumber - 1];
|
||||
att = TupleDescAttr(desc, attributeNumber - 1);
|
||||
att->attrelid = 0; /* dummy value */
|
||||
|
||||
/* unlike TupleDescInitEntry, we require an attribute name */
|
||||
@ -664,7 +668,7 @@ TupleDescInitEntryCollation(TupleDesc desc,
|
||||
AssertArg(attributeNumber >= 1);
|
||||
AssertArg(attributeNumber <= desc->natts);
|
||||
|
||||
desc->attrs[attributeNumber - 1]->attcollation = collationid;
|
||||
TupleDescAttr(desc, attributeNumber - 1)->attcollation = collationid;
|
||||
}
|
||||
|
||||
|
||||
@ -704,6 +708,7 @@ BuildDescForRelation(List *schema)
|
||||
{
|
||||
ColumnDef *entry = lfirst(l);
|
||||
AclResult aclresult;
|
||||
Form_pg_attribute att;
|
||||
|
||||
/*
|
||||
* for each entry in the list, get the name and type information from
|
||||
@ -730,17 +735,18 @@ BuildDescForRelation(List *schema)
|
||||
|
||||
TupleDescInitEntry(desc, attnum, attname,
|
||||
atttypid, atttypmod, attdim);
|
||||
att = TupleDescAttr(desc, attnum - 1);
|
||||
|
||||
/* Override TupleDescInitEntry's settings as requested */
|
||||
TupleDescInitEntryCollation(desc, attnum, attcollation);
|
||||
if (entry->storage)
|
||||
desc->attrs[attnum - 1]->attstorage = entry->storage;
|
||||
att->attstorage = entry->storage;
|
||||
|
||||
/* Fill in additional stuff not handled by TupleDescInitEntry */
|
||||
desc->attrs[attnum - 1]->attnotnull = entry->is_not_null;
|
||||
att->attnotnull = entry->is_not_null;
|
||||
has_not_null |= entry->is_not_null;
|
||||
desc->attrs[attnum - 1]->attislocal = entry->is_local;
|
||||
desc->attrs[attnum - 1]->attinhcount = entry->inhcount;
|
||||
att->attislocal = entry->is_local;
|
||||
att->attinhcount = entry->inhcount;
|
||||
}
|
||||
|
||||
if (has_not_null)
|
||||
|
@ -127,9 +127,10 @@ ginInitBA(BuildAccumulator *accum)
|
||||
static Datum
|
||||
getDatumCopy(BuildAccumulator *accum, OffsetNumber attnum, Datum value)
|
||||
{
|
||||
Form_pg_attribute att = accum->ginstate->origTupdesc->attrs[attnum - 1];
|
||||
Form_pg_attribute att;
|
||||
Datum res;
|
||||
|
||||
att = TupleDescAttr(accum->ginstate->origTupdesc, attnum - 1);
|
||||
if (att->attbyval)
|
||||
res = value;
|
||||
else
|
||||
|
@ -129,7 +129,7 @@ collectMatchBitmap(GinBtreeData *btree, GinBtreeStack *stack,
|
||||
|
||||
/* Locate tupdesc entry for key column (for attbyval/attlen data) */
|
||||
attnum = scanEntry->attnum;
|
||||
attr = btree->ginstate->origTupdesc->attrs[attnum - 1];
|
||||
attr = TupleDescAttr(btree->ginstate->origTupdesc, attnum - 1);
|
||||
|
||||
for (;;)
|
||||
{
|
||||
|
@ -96,6 +96,8 @@ initGinState(GinState *state, Relation index)
|
||||
|
||||
for (i = 0; i < origTupdesc->natts; i++)
|
||||
{
|
||||
Form_pg_attribute attr = TupleDescAttr(origTupdesc, i);
|
||||
|
||||
if (state->oneCol)
|
||||
state->tupdesc[i] = state->origTupdesc;
|
||||
else
|
||||
@ -105,11 +107,11 @@ initGinState(GinState *state, Relation index)
|
||||
TupleDescInitEntry(state->tupdesc[i], (AttrNumber) 1, NULL,
|
||||
INT2OID, -1, 0);
|
||||
TupleDescInitEntry(state->tupdesc[i], (AttrNumber) 2, NULL,
|
||||
origTupdesc->attrs[i]->atttypid,
|
||||
origTupdesc->attrs[i]->atttypmod,
|
||||
origTupdesc->attrs[i]->attndims);
|
||||
attr->atttypid,
|
||||
attr->atttypmod,
|
||||
attr->attndims);
|
||||
TupleDescInitEntryCollation(state->tupdesc[i], (AttrNumber) 2,
|
||||
origTupdesc->attrs[i]->attcollation);
|
||||
attr->attcollation);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -126,13 +128,13 @@ initGinState(GinState *state, Relation index)
|
||||
{
|
||||
TypeCacheEntry *typentry;
|
||||
|
||||
typentry = lookup_type_cache(origTupdesc->attrs[i]->atttypid,
|
||||
typentry = lookup_type_cache(attr->atttypid,
|
||||
TYPECACHE_CMP_PROC_FINFO);
|
||||
if (!OidIsValid(typentry->cmp_proc_finfo.fn_oid))
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_UNDEFINED_FUNCTION),
|
||||
errmsg("could not identify a comparison function for type %s",
|
||||
format_type_be(origTupdesc->attrs[i]->atttypid))));
|
||||
format_type_be(attr->atttypid))));
|
||||
fmgr_info_copy(&(state->compareFn[i]),
|
||||
&(typentry->cmp_proc_finfo),
|
||||
CurrentMemoryContext);
|
||||
|
@ -295,10 +295,10 @@ gistInitBuffering(GISTBuildState *buildstate)
|
||||
itupMinSize = (Size) MAXALIGN(sizeof(IndexTupleData));
|
||||
for (i = 0; i < index->rd_att->natts; i++)
|
||||
{
|
||||
if (index->rd_att->attrs[i]->attlen < 0)
|
||||
if (TupleDescAttr(index->rd_att, i)->attlen < 0)
|
||||
itupMinSize += VARHDRSZ;
|
||||
else
|
||||
itupMinSize += index->rd_att->attrs[i]->attlen;
|
||||
itupMinSize += TupleDescAttr(index->rd_att, i)->attlen;
|
||||
}
|
||||
|
||||
/* Calculate average and maximal number of index tuples which fit to page */
|
||||
|
@ -1066,11 +1066,11 @@ fastgetattr(HeapTuple tup, int attnum, TupleDesc tupleDesc,
|
||||
(*(isnull) = false),
|
||||
HeapTupleNoNulls(tup) ?
|
||||
(
|
||||
(tupleDesc)->attrs[(attnum) - 1]->attcacheoff >= 0 ?
|
||||
TupleDescAttr((tupleDesc), (attnum) - 1)->attcacheoff >= 0 ?
|
||||
(
|
||||
fetchatt((tupleDesc)->attrs[(attnum) - 1],
|
||||
fetchatt(TupleDescAttr((tupleDesc), (attnum) - 1),
|
||||
(char *) (tup)->t_data + (tup)->t_data->t_hoff +
|
||||
(tupleDesc)->attrs[(attnum) - 1]->attcacheoff)
|
||||
TupleDescAttr((tupleDesc), (attnum) - 1)->attcacheoff)
|
||||
)
|
||||
:
|
||||
nocachegetattr((tup), (attnum), (tupleDesc))
|
||||
@ -4422,7 +4422,7 @@ heap_tuple_attr_equals(TupleDesc tupdesc, int attrnum,
|
||||
else
|
||||
{
|
||||
Assert(attrnum <= tupdesc->natts);
|
||||
att = tupdesc->attrs[attrnum - 1];
|
||||
att = TupleDescAttr(tupdesc, attrnum - 1);
|
||||
return datumIsEqual(value1, value2, att->attbyval, att->attlen);
|
||||
}
|
||||
}
|
||||
|
@ -464,7 +464,6 @@ void
|
||||
toast_delete(Relation rel, HeapTuple oldtup, bool is_speculative)
|
||||
{
|
||||
TupleDesc tupleDesc;
|
||||
Form_pg_attribute *att;
|
||||
int numAttrs;
|
||||
int i;
|
||||
Datum toast_values[MaxHeapAttributeNumber];
|
||||
@ -489,7 +488,6 @@ toast_delete(Relation rel, HeapTuple oldtup, bool is_speculative)
|
||||
* least one varlena column, by the way.)
|
||||
*/
|
||||
tupleDesc = rel->rd_att;
|
||||
att = tupleDesc->attrs;
|
||||
numAttrs = tupleDesc->natts;
|
||||
|
||||
Assert(numAttrs <= MaxHeapAttributeNumber);
|
||||
@ -501,7 +499,7 @@ toast_delete(Relation rel, HeapTuple oldtup, bool is_speculative)
|
||||
*/
|
||||
for (i = 0; i < numAttrs; i++)
|
||||
{
|
||||
if (att[i]->attlen == -1)
|
||||
if (TupleDescAttr(tupleDesc, i)->attlen == -1)
|
||||
{
|
||||
Datum value = toast_values[i];
|
||||
|
||||
@ -538,7 +536,6 @@ toast_insert_or_update(Relation rel, HeapTuple newtup, HeapTuple oldtup,
|
||||
{
|
||||
HeapTuple result_tuple;
|
||||
TupleDesc tupleDesc;
|
||||
Form_pg_attribute *att;
|
||||
int numAttrs;
|
||||
int i;
|
||||
|
||||
@ -579,7 +576,6 @@ toast_insert_or_update(Relation rel, HeapTuple newtup, HeapTuple oldtup,
|
||||
* Get the tuple descriptor and break down the tuple(s) into fields.
|
||||
*/
|
||||
tupleDesc = rel->rd_att;
|
||||
att = tupleDesc->attrs;
|
||||
numAttrs = tupleDesc->natts;
|
||||
|
||||
Assert(numAttrs <= MaxHeapAttributeNumber);
|
||||
@ -606,6 +602,7 @@ toast_insert_or_update(Relation rel, HeapTuple newtup, HeapTuple oldtup,
|
||||
|
||||
for (i = 0; i < numAttrs; i++)
|
||||
{
|
||||
Form_pg_attribute att = TupleDescAttr(tupleDesc, i);
|
||||
struct varlena *old_value;
|
||||
struct varlena *new_value;
|
||||
|
||||
@ -621,7 +618,7 @@ toast_insert_or_update(Relation rel, HeapTuple newtup, HeapTuple oldtup,
|
||||
* If the old value is stored on disk, check if it has changed so
|
||||
* we have to delete it later.
|
||||
*/
|
||||
if (att[i]->attlen == -1 && !toast_oldisnull[i] &&
|
||||
if (att->attlen == -1 && !toast_oldisnull[i] &&
|
||||
VARATT_IS_EXTERNAL_ONDISK(old_value))
|
||||
{
|
||||
if (toast_isnull[i] || !VARATT_IS_EXTERNAL_ONDISK(new_value) ||
|
||||
@ -668,12 +665,12 @@ toast_insert_or_update(Relation rel, HeapTuple newtup, HeapTuple oldtup,
|
||||
/*
|
||||
* Now look at varlena attributes
|
||||
*/
|
||||
if (att[i]->attlen == -1)
|
||||
if (att->attlen == -1)
|
||||
{
|
||||
/*
|
||||
* If the table's attribute says PLAIN always, force it so.
|
||||
*/
|
||||
if (att[i]->attstorage == 'p')
|
||||
if (att->attstorage == 'p')
|
||||
toast_action[i] = 'p';
|
||||
|
||||
/*
|
||||
@ -687,7 +684,7 @@ toast_insert_or_update(Relation rel, HeapTuple newtup, HeapTuple oldtup,
|
||||
if (VARATT_IS_EXTERNAL(new_value))
|
||||
{
|
||||
toast_oldexternal[i] = new_value;
|
||||
if (att[i]->attstorage == 'p')
|
||||
if (att->attstorage == 'p')
|
||||
new_value = heap_tuple_untoast_attr(new_value);
|
||||
else
|
||||
new_value = heap_tuple_fetch_attr(new_value);
|
||||
@ -749,13 +746,15 @@ toast_insert_or_update(Relation rel, HeapTuple newtup, HeapTuple oldtup,
|
||||
*/
|
||||
for (i = 0; i < numAttrs; i++)
|
||||
{
|
||||
Form_pg_attribute att = TupleDescAttr(tupleDesc, i);
|
||||
|
||||
if (toast_action[i] != ' ')
|
||||
continue;
|
||||
if (VARATT_IS_EXTERNAL(DatumGetPointer(toast_values[i])))
|
||||
continue; /* can't happen, toast_action would be 'p' */
|
||||
if (VARATT_IS_COMPRESSED(DatumGetPointer(toast_values[i])))
|
||||
continue;
|
||||
if (att[i]->attstorage != 'x' && att[i]->attstorage != 'e')
|
||||
if (att->attstorage != 'x' && att->attstorage != 'e')
|
||||
continue;
|
||||
if (toast_sizes[i] > biggest_size)
|
||||
{
|
||||
@ -771,7 +770,7 @@ toast_insert_or_update(Relation rel, HeapTuple newtup, HeapTuple oldtup,
|
||||
* Attempt to compress it inline, if it has attstorage 'x'
|
||||
*/
|
||||
i = biggest_attno;
|
||||
if (att[i]->attstorage == 'x')
|
||||
if (TupleDescAttr(tupleDesc, i)->attstorage == 'x')
|
||||
{
|
||||
old_value = toast_values[i];
|
||||
new_value = toast_compress_datum(old_value);
|
||||
@ -841,11 +840,13 @@ toast_insert_or_update(Relation rel, HeapTuple newtup, HeapTuple oldtup,
|
||||
*/
|
||||
for (i = 0; i < numAttrs; i++)
|
||||
{
|
||||
Form_pg_attribute att = TupleDescAttr(tupleDesc, i);
|
||||
|
||||
if (toast_action[i] == 'p')
|
||||
continue;
|
||||
if (VARATT_IS_EXTERNAL(DatumGetPointer(toast_values[i])))
|
||||
continue; /* can't happen, toast_action would be 'p' */
|
||||
if (att[i]->attstorage != 'x' && att[i]->attstorage != 'e')
|
||||
if (att->attstorage != 'x' && att->attstorage != 'e')
|
||||
continue;
|
||||
if (toast_sizes[i] > biggest_size)
|
||||
{
|
||||
@ -896,7 +897,7 @@ toast_insert_or_update(Relation rel, HeapTuple newtup, HeapTuple oldtup,
|
||||
continue; /* can't happen, toast_action would be 'p' */
|
||||
if (VARATT_IS_COMPRESSED(DatumGetPointer(toast_values[i])))
|
||||
continue;
|
||||
if (att[i]->attstorage != 'm')
|
||||
if (TupleDescAttr(tupleDesc, i)->attstorage != 'm')
|
||||
continue;
|
||||
if (toast_sizes[i] > biggest_size)
|
||||
{
|
||||
@ -959,7 +960,7 @@ toast_insert_or_update(Relation rel, HeapTuple newtup, HeapTuple oldtup,
|
||||
continue;
|
||||
if (VARATT_IS_EXTERNAL(DatumGetPointer(toast_values[i])))
|
||||
continue; /* can't happen, toast_action would be 'p' */
|
||||
if (att[i]->attstorage != 'm')
|
||||
if (TupleDescAttr(tupleDesc, i)->attstorage != 'm')
|
||||
continue;
|
||||
if (toast_sizes[i] > biggest_size)
|
||||
{
|
||||
@ -1084,7 +1085,6 @@ HeapTuple
|
||||
toast_flatten_tuple(HeapTuple tup, TupleDesc tupleDesc)
|
||||
{
|
||||
HeapTuple new_tuple;
|
||||
Form_pg_attribute *att = tupleDesc->attrs;
|
||||
int numAttrs = tupleDesc->natts;
|
||||
int i;
|
||||
Datum toast_values[MaxTupleAttributeNumber];
|
||||
@ -1104,7 +1104,7 @@ toast_flatten_tuple(HeapTuple tup, TupleDesc tupleDesc)
|
||||
/*
|
||||
* Look at non-null varlena attributes
|
||||
*/
|
||||
if (!toast_isnull[i] && att[i]->attlen == -1)
|
||||
if (!toast_isnull[i] && TupleDescAttr(tupleDesc, i)->attlen == -1)
|
||||
{
|
||||
struct varlena *new_value;
|
||||
|
||||
@ -1193,7 +1193,6 @@ toast_flatten_tuple_to_datum(HeapTupleHeader tup,
|
||||
int32 new_data_len;
|
||||
int32 new_tuple_len;
|
||||
HeapTupleData tmptup;
|
||||
Form_pg_attribute *att = tupleDesc->attrs;
|
||||
int numAttrs = tupleDesc->natts;
|
||||
int i;
|
||||
bool has_nulls = false;
|
||||
@ -1222,7 +1221,7 @@ toast_flatten_tuple_to_datum(HeapTupleHeader tup,
|
||||
*/
|
||||
if (toast_isnull[i])
|
||||
has_nulls = true;
|
||||
else if (att[i]->attlen == -1)
|
||||
else if (TupleDescAttr(tupleDesc, i)->attlen == -1)
|
||||
{
|
||||
struct varlena *new_value;
|
||||
|
||||
@ -1307,7 +1306,6 @@ toast_build_flattened_tuple(TupleDesc tupleDesc,
|
||||
bool *isnull)
|
||||
{
|
||||
HeapTuple new_tuple;
|
||||
Form_pg_attribute *att = tupleDesc->attrs;
|
||||
int numAttrs = tupleDesc->natts;
|
||||
int num_to_free;
|
||||
int i;
|
||||
@ -1327,7 +1325,7 @@ toast_build_flattened_tuple(TupleDesc tupleDesc,
|
||||
/*
|
||||
* Look at non-null varlena attributes
|
||||
*/
|
||||
if (!isnull[i] && att[i]->attlen == -1)
|
||||
if (!isnull[i] && TupleDescAttr(tupleDesc, i)->attlen == -1)
|
||||
{
|
||||
struct varlena *new_value;
|
||||
|
||||
|
@ -112,7 +112,7 @@ spgGetCache(Relation index)
|
||||
* tupdesc. We pass this to the opclass config function so that
|
||||
* polymorphic opclasses are possible.
|
||||
*/
|
||||
atttype = index->rd_att->attrs[0]->atttypid;
|
||||
atttype = TupleDescAttr(index->rd_att, 0)->atttypid;
|
||||
|
||||
/* Call the config function to get config info for the opclass */
|
||||
in.attType = atttype;
|
||||
|
@ -609,7 +609,7 @@ boot_openrel(char *relname)
|
||||
if (attrtypes[i] == NULL)
|
||||
attrtypes[i] = AllocateAttribute();
|
||||
memmove((char *) attrtypes[i],
|
||||
(char *) boot_reldesc->rd_att->attrs[i],
|
||||
(char *) TupleDescAttr(boot_reldesc->rd_att, i),
|
||||
ATTRIBUTE_FIXED_PART_SIZE);
|
||||
|
||||
{
|
||||
@ -816,7 +816,7 @@ InsertOneValue(char *value, int i)
|
||||
|
||||
elog(DEBUG4, "inserting column %d value \"%s\"", i, value);
|
||||
|
||||
typoid = boot_reldesc->rd_att->attrs[i]->atttypid;
|
||||
typoid = TupleDescAttr(boot_reldesc->rd_att, i)->atttypid;
|
||||
|
||||
boot_get_type_io_data(typoid,
|
||||
&typlen, &typbyval, &typalign,
|
||||
@ -843,10 +843,10 @@ InsertOneNull(int i)
|
||||
{
|
||||
elog(DEBUG4, "inserting column %d NULL", i);
|
||||
Assert(i >= 0 && i < MAXATTR);
|
||||
if (boot_reldesc->rd_att->attrs[i]->attnotnull)
|
||||
if (TupleDescAttr(boot_reldesc->rd_att, i)->attnotnull)
|
||||
elog(ERROR,
|
||||
"NULL value specified for not-null column \"%s\" of relation \"%s\"",
|
||||
NameStr(boot_reldesc->rd_att->attrs[i]->attname),
|
||||
NameStr(TupleDescAttr(boot_reldesc->rd_att, i)->attname),
|
||||
RelationGetRelationName(boot_reldesc));
|
||||
values[i] = PointerGetDatum(NULL);
|
||||
Nulls[i] = true;
|
||||
|
@ -431,12 +431,14 @@ CheckAttributeNamesTypes(TupleDesc tupdesc, char relkind,
|
||||
{
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
if (SystemAttributeByName(NameStr(tupdesc->attrs[i]->attname),
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, i);
|
||||
|
||||
if (SystemAttributeByName(NameStr(attr->attname),
|
||||
tupdesc->tdhasoid) != NULL)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_DUPLICATE_COLUMN),
|
||||
errmsg("column name \"%s\" conflicts with a system column name",
|
||||
NameStr(tupdesc->attrs[i]->attname))));
|
||||
NameStr(attr->attname))));
|
||||
}
|
||||
}
|
||||
|
||||
@ -447,12 +449,12 @@ CheckAttributeNamesTypes(TupleDesc tupdesc, char relkind,
|
||||
{
|
||||
for (j = 0; j < i; j++)
|
||||
{
|
||||
if (strcmp(NameStr(tupdesc->attrs[j]->attname),
|
||||
NameStr(tupdesc->attrs[i]->attname)) == 0)
|
||||
if (strcmp(NameStr(TupleDescAttr(tupdesc, j)->attname),
|
||||
NameStr(TupleDescAttr(tupdesc, i)->attname)) == 0)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_DUPLICATE_COLUMN),
|
||||
errmsg("column name \"%s\" specified more than once",
|
||||
NameStr(tupdesc->attrs[j]->attname))));
|
||||
NameStr(TupleDescAttr(tupdesc, j)->attname))));
|
||||
}
|
||||
}
|
||||
|
||||
@ -461,9 +463,9 @@ CheckAttributeNamesTypes(TupleDesc tupdesc, char relkind,
|
||||
*/
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
CheckAttributeType(NameStr(tupdesc->attrs[i]->attname),
|
||||
tupdesc->attrs[i]->atttypid,
|
||||
tupdesc->attrs[i]->attcollation,
|
||||
CheckAttributeType(NameStr(TupleDescAttr(tupdesc, i)->attname),
|
||||
TupleDescAttr(tupdesc, i)->atttypid,
|
||||
TupleDescAttr(tupdesc, i)->attcollation,
|
||||
NIL, /* assume we're creating a new rowtype */
|
||||
allow_system_table_mods);
|
||||
}
|
||||
@ -545,7 +547,7 @@ CheckAttributeType(const char *attname,
|
||||
|
||||
for (i = 0; i < tupdesc->natts; i++)
|
||||
{
|
||||
Form_pg_attribute attr = tupdesc->attrs[i];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, i);
|
||||
|
||||
if (attr->attisdropped)
|
||||
continue;
|
||||
@ -678,7 +680,7 @@ AddNewAttributeTuples(Oid new_rel_oid,
|
||||
*/
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
attr = tupdesc->attrs[i];
|
||||
attr = TupleDescAttr(tupdesc, i);
|
||||
/* Fill in the correct relation OID */
|
||||
attr->attrelid = new_rel_oid;
|
||||
/* Make sure these are OK, too */
|
||||
@ -2245,7 +2247,7 @@ AddRelationNewConstraints(Relation rel,
|
||||
foreach(cell, newColDefaults)
|
||||
{
|
||||
RawColumnDefault *colDef = (RawColumnDefault *) lfirst(cell);
|
||||
Form_pg_attribute atp = rel->rd_att->attrs[colDef->attnum - 1];
|
||||
Form_pg_attribute atp = TupleDescAttr(rel->rd_att, colDef->attnum - 1);
|
||||
Oid defOid;
|
||||
|
||||
expr = cookDefault(pstate, colDef->raw_default,
|
||||
|
@ -307,7 +307,7 @@ ConstructTupleDescriptor(Relation heapRelation,
|
||||
for (i = 0; i < numatts; i++)
|
||||
{
|
||||
AttrNumber atnum = indexInfo->ii_KeyAttrNumbers[i];
|
||||
Form_pg_attribute to = indexTupDesc->attrs[i];
|
||||
Form_pg_attribute to = TupleDescAttr(indexTupDesc, i);
|
||||
HeapTuple tuple;
|
||||
Form_pg_type typeTup;
|
||||
Form_pg_opclass opclassTup;
|
||||
@ -333,7 +333,8 @@ ConstructTupleDescriptor(Relation heapRelation,
|
||||
*/
|
||||
if (atnum > natts) /* safety check */
|
||||
elog(ERROR, "invalid column number %d", atnum);
|
||||
from = heapTupDesc->attrs[AttrNumberGetAttrOffset(atnum)];
|
||||
from = TupleDescAttr(heapTupDesc,
|
||||
AttrNumberGetAttrOffset(atnum));
|
||||
}
|
||||
|
||||
/*
|
||||
@ -495,7 +496,7 @@ InitializeAttributeOids(Relation indexRelation,
|
||||
tupleDescriptor = RelationGetDescr(indexRelation);
|
||||
|
||||
for (i = 0; i < numatts; i += 1)
|
||||
tupleDescriptor->attrs[i]->attrelid = indexoid;
|
||||
TupleDescAttr(tupleDescriptor, i)->attrelid = indexoid;
|
||||
}
|
||||
|
||||
/* ----------------------------------------------------------------
|
||||
@ -524,14 +525,16 @@ AppendAttributeTuples(Relation indexRelation, int numatts)
|
||||
|
||||
for (i = 0; i < numatts; i++)
|
||||
{
|
||||
Form_pg_attribute attr = TupleDescAttr(indexTupDesc, i);
|
||||
|
||||
/*
|
||||
* There used to be very grotty code here to set these fields, but I
|
||||
* think it's unnecessary. They should be set already.
|
||||
*/
|
||||
Assert(indexTupDesc->attrs[i]->attnum == i + 1);
|
||||
Assert(indexTupDesc->attrs[i]->attcacheoff == -1);
|
||||
Assert(attr->attnum == i + 1);
|
||||
Assert(attr->attcacheoff == -1);
|
||||
|
||||
InsertPgAttributeTuple(pg_attribute, indexTupDesc->attrs[i], indstate);
|
||||
InsertPgAttributeTuple(pg_attribute, attr, indstate);
|
||||
}
|
||||
|
||||
CatalogCloseIndexes(indstate);
|
||||
|
@ -235,9 +235,9 @@ create_toast_table(Relation rel, Oid toastOid, Oid toastIndexOid,
|
||||
* toast :-(. This is essential for chunk_data because type bytea is
|
||||
* toastable; hit the other two just to be sure.
|
||||
*/
|
||||
tupdesc->attrs[0]->attstorage = 'p';
|
||||
tupdesc->attrs[1]->attstorage = 'p';
|
||||
tupdesc->attrs[2]->attstorage = 'p';
|
||||
TupleDescAttr(tupdesc, 0)->attstorage = 'p';
|
||||
TupleDescAttr(tupdesc, 1)->attstorage = 'p';
|
||||
TupleDescAttr(tupdesc, 2)->attstorage = 'p';
|
||||
|
||||
/*
|
||||
* Toast tables for regular relations go in pg_toast; those for temp
|
||||
@ -402,33 +402,33 @@ needs_toast_table(Relation rel)
|
||||
bool maxlength_unknown = false;
|
||||
bool has_toastable_attrs = false;
|
||||
TupleDesc tupdesc;
|
||||
Form_pg_attribute *att;
|
||||
int32 tuple_length;
|
||||
int i;
|
||||
|
||||
tupdesc = rel->rd_att;
|
||||
att = tupdesc->attrs;
|
||||
|
||||
for (i = 0; i < tupdesc->natts; i++)
|
||||
{
|
||||
if (att[i]->attisdropped)
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
|
||||
if (att->attisdropped)
|
||||
continue;
|
||||
data_length = att_align_nominal(data_length, att[i]->attalign);
|
||||
if (att[i]->attlen > 0)
|
||||
data_length = att_align_nominal(data_length, att->attalign);
|
||||
if (att->attlen > 0)
|
||||
{
|
||||
/* Fixed-length types are never toastable */
|
||||
data_length += att[i]->attlen;
|
||||
data_length += att->attlen;
|
||||
}
|
||||
else
|
||||
{
|
||||
int32 maxlen = type_maximum_size(att[i]->atttypid,
|
||||
att[i]->atttypmod);
|
||||
int32 maxlen = type_maximum_size(att->atttypid,
|
||||
att->atttypmod);
|
||||
|
||||
if (maxlen < 0)
|
||||
maxlength_unknown = true;
|
||||
else
|
||||
data_length += maxlen;
|
||||
if (att[i]->attstorage != 'p')
|
||||
if (att->attstorage != 'p')
|
||||
has_toastable_attrs = true;
|
||||
}
|
||||
}
|
||||
|
@ -871,7 +871,7 @@ compute_index_stats(Relation onerel, double totalrows,
|
||||
static VacAttrStats *
|
||||
examine_attribute(Relation onerel, int attnum, Node *index_expr)
|
||||
{
|
||||
Form_pg_attribute attr = onerel->rd_att->attrs[attnum - 1];
|
||||
Form_pg_attribute attr = TupleDescAttr(onerel->rd_att, attnum - 1);
|
||||
HeapTuple typtuple;
|
||||
VacAttrStats *stats;
|
||||
int i;
|
||||
|
@ -1714,7 +1714,7 @@ reform_and_rewrite_tuple(HeapTuple tuple,
|
||||
/* Be sure to null out any dropped columns */
|
||||
for (i = 0; i < newTupDesc->natts; i++)
|
||||
{
|
||||
if (newTupDesc->attrs[i]->attisdropped)
|
||||
if (TupleDescAttr(newTupDesc, i)->attisdropped)
|
||||
isnull[i] = true;
|
||||
}
|
||||
|
||||
|
@ -1583,12 +1583,13 @@ BeginCopy(ParseState *pstate,
|
||||
foreach(cur, attnums)
|
||||
{
|
||||
int attnum = lfirst_int(cur);
|
||||
Form_pg_attribute attr = TupleDescAttr(tupDesc, attnum - 1);
|
||||
|
||||
if (!list_member_int(cstate->attnumlist, attnum))
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_INVALID_COLUMN_REFERENCE),
|
||||
errmsg("FORCE_QUOTE column \"%s\" not referenced by COPY",
|
||||
NameStr(tupDesc->attrs[attnum - 1]->attname))));
|
||||
NameStr(attr->attname))));
|
||||
cstate->force_quote_flags[attnum - 1] = true;
|
||||
}
|
||||
}
|
||||
@ -1605,12 +1606,13 @@ BeginCopy(ParseState *pstate,
|
||||
foreach(cur, attnums)
|
||||
{
|
||||
int attnum = lfirst_int(cur);
|
||||
Form_pg_attribute attr = TupleDescAttr(tupDesc, attnum - 1);
|
||||
|
||||
if (!list_member_int(cstate->attnumlist, attnum))
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_INVALID_COLUMN_REFERENCE),
|
||||
errmsg("FORCE_NOT_NULL column \"%s\" not referenced by COPY",
|
||||
NameStr(tupDesc->attrs[attnum - 1]->attname))));
|
||||
NameStr(attr->attname))));
|
||||
cstate->force_notnull_flags[attnum - 1] = true;
|
||||
}
|
||||
}
|
||||
@ -1627,12 +1629,13 @@ BeginCopy(ParseState *pstate,
|
||||
foreach(cur, attnums)
|
||||
{
|
||||
int attnum = lfirst_int(cur);
|
||||
Form_pg_attribute attr = TupleDescAttr(tupDesc, attnum - 1);
|
||||
|
||||
if (!list_member_int(cstate->attnumlist, attnum))
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_INVALID_COLUMN_REFERENCE),
|
||||
errmsg("FORCE_NULL column \"%s\" not referenced by COPY",
|
||||
NameStr(tupDesc->attrs[attnum - 1]->attname))));
|
||||
NameStr(attr->attname))));
|
||||
cstate->force_null_flags[attnum - 1] = true;
|
||||
}
|
||||
}
|
||||
@ -1650,12 +1653,13 @@ BeginCopy(ParseState *pstate,
|
||||
foreach(cur, attnums)
|
||||
{
|
||||
int attnum = lfirst_int(cur);
|
||||
Form_pg_attribute attr = TupleDescAttr(tupDesc, attnum - 1);
|
||||
|
||||
if (!list_member_int(cstate->attnumlist, attnum))
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_INVALID_COLUMN_REFERENCE),
|
||||
errmsg_internal("selected column \"%s\" not referenced by COPY",
|
||||
NameStr(tupDesc->attrs[attnum - 1]->attname))));
|
||||
NameStr(attr->attname))));
|
||||
cstate->convert_select_flags[attnum - 1] = true;
|
||||
}
|
||||
}
|
||||
@ -1919,7 +1923,6 @@ CopyTo(CopyState cstate)
|
||||
{
|
||||
TupleDesc tupDesc;
|
||||
int num_phys_attrs;
|
||||
Form_pg_attribute *attr;
|
||||
ListCell *cur;
|
||||
uint64 processed;
|
||||
|
||||
@ -1927,7 +1930,6 @@ CopyTo(CopyState cstate)
|
||||
tupDesc = RelationGetDescr(cstate->rel);
|
||||
else
|
||||
tupDesc = cstate->queryDesc->tupDesc;
|
||||
attr = tupDesc->attrs;
|
||||
num_phys_attrs = tupDesc->natts;
|
||||
cstate->null_print_client = cstate->null_print; /* default */
|
||||
|
||||
@ -1941,13 +1943,14 @@ CopyTo(CopyState cstate)
|
||||
int attnum = lfirst_int(cur);
|
||||
Oid out_func_oid;
|
||||
bool isvarlena;
|
||||
Form_pg_attribute attr = TupleDescAttr(tupDesc, attnum - 1);
|
||||
|
||||
if (cstate->binary)
|
||||
getTypeBinaryOutputInfo(attr[attnum - 1]->atttypid,
|
||||
getTypeBinaryOutputInfo(attr->atttypid,
|
||||
&out_func_oid,
|
||||
&isvarlena);
|
||||
else
|
||||
getTypeOutputInfo(attr[attnum - 1]->atttypid,
|
||||
getTypeOutputInfo(attr->atttypid,
|
||||
&out_func_oid,
|
||||
&isvarlena);
|
||||
fmgr_info(out_func_oid, &cstate->out_functions[attnum - 1]);
|
||||
@ -2004,7 +2007,7 @@ CopyTo(CopyState cstate)
|
||||
CopySendChar(cstate, cstate->delim[0]);
|
||||
hdr_delim = true;
|
||||
|
||||
colname = NameStr(attr[attnum - 1]->attname);
|
||||
colname = NameStr(TupleDescAttr(tupDesc, attnum - 1)->attname);
|
||||
|
||||
CopyAttributeOutCSV(cstate, colname, false,
|
||||
list_length(cstate->attnumlist) == 1);
|
||||
@ -2969,7 +2972,6 @@ BeginCopyFrom(ParseState *pstate,
|
||||
CopyState cstate;
|
||||
bool pipe = (filename == NULL);
|
||||
TupleDesc tupDesc;
|
||||
Form_pg_attribute *attr;
|
||||
AttrNumber num_phys_attrs,
|
||||
num_defaults;
|
||||
FmgrInfo *in_functions;
|
||||
@ -3004,7 +3006,6 @@ BeginCopyFrom(ParseState *pstate,
|
||||
cstate->range_table = pstate->p_rtable;
|
||||
|
||||
tupDesc = RelationGetDescr(cstate->rel);
|
||||
attr = tupDesc->attrs;
|
||||
num_phys_attrs = tupDesc->natts;
|
||||
num_defaults = 0;
|
||||
volatile_defexprs = false;
|
||||
@ -3022,16 +3023,18 @@ BeginCopyFrom(ParseState *pstate,
|
||||
|
||||
for (attnum = 1; attnum <= num_phys_attrs; attnum++)
|
||||
{
|
||||
Form_pg_attribute att = TupleDescAttr(tupDesc, attnum - 1);
|
||||
|
||||
/* We don't need info for dropped attributes */
|
||||
if (attr[attnum - 1]->attisdropped)
|
||||
if (att->attisdropped)
|
||||
continue;
|
||||
|
||||
/* Fetch the input function and typioparam info */
|
||||
if (cstate->binary)
|
||||
getTypeBinaryInputInfo(attr[attnum - 1]->atttypid,
|
||||
getTypeBinaryInputInfo(att->atttypid,
|
||||
&in_func_oid, &typioparams[attnum - 1]);
|
||||
else
|
||||
getTypeInputInfo(attr[attnum - 1]->atttypid,
|
||||
getTypeInputInfo(att->atttypid,
|
||||
&in_func_oid, &typioparams[attnum - 1]);
|
||||
fmgr_info(in_func_oid, &in_functions[attnum - 1]);
|
||||
|
||||
@ -3273,7 +3276,6 @@ NextCopyFrom(CopyState cstate, ExprContext *econtext,
|
||||
Datum *values, bool *nulls, Oid *tupleOid)
|
||||
{
|
||||
TupleDesc tupDesc;
|
||||
Form_pg_attribute *attr;
|
||||
AttrNumber num_phys_attrs,
|
||||
attr_count,
|
||||
num_defaults = cstate->num_defaults;
|
||||
@ -3287,7 +3289,6 @@ NextCopyFrom(CopyState cstate, ExprContext *econtext,
|
||||
ExprState **defexprs = cstate->defexprs;
|
||||
|
||||
tupDesc = RelationGetDescr(cstate->rel);
|
||||
attr = tupDesc->attrs;
|
||||
num_phys_attrs = tupDesc->natts;
|
||||
attr_count = list_length(cstate->attnumlist);
|
||||
nfields = file_has_oids ? (attr_count + 1) : attr_count;
|
||||
@ -3349,12 +3350,13 @@ NextCopyFrom(CopyState cstate, ExprContext *econtext,
|
||||
{
|
||||
int attnum = lfirst_int(cur);
|
||||
int m = attnum - 1;
|
||||
Form_pg_attribute att = TupleDescAttr(tupDesc, m);
|
||||
|
||||
if (fieldno >= fldct)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_BAD_COPY_FILE_FORMAT),
|
||||
errmsg("missing data for column \"%s\"",
|
||||
NameStr(attr[m]->attname))));
|
||||
NameStr(att->attname))));
|
||||
string = field_strings[fieldno++];
|
||||
|
||||
if (cstate->convert_select_flags &&
|
||||
@ -3388,12 +3390,12 @@ NextCopyFrom(CopyState cstate, ExprContext *econtext,
|
||||
}
|
||||
}
|
||||
|
||||
cstate->cur_attname = NameStr(attr[m]->attname);
|
||||
cstate->cur_attname = NameStr(att->attname);
|
||||
cstate->cur_attval = string;
|
||||
values[m] = InputFunctionCall(&in_functions[m],
|
||||
string,
|
||||
typioparams[m],
|
||||
attr[m]->atttypmod);
|
||||
att->atttypmod);
|
||||
if (string != NULL)
|
||||
nulls[m] = false;
|
||||
cstate->cur_attname = NULL;
|
||||
@ -3472,14 +3474,15 @@ NextCopyFrom(CopyState cstate, ExprContext *econtext,
|
||||
{
|
||||
int attnum = lfirst_int(cur);
|
||||
int m = attnum - 1;
|
||||
Form_pg_attribute att = TupleDescAttr(tupDesc, m);
|
||||
|
||||
cstate->cur_attname = NameStr(attr[m]->attname);
|
||||
cstate->cur_attname = NameStr(att->attname);
|
||||
i++;
|
||||
values[m] = CopyReadBinaryAttribute(cstate,
|
||||
i,
|
||||
&in_functions[m],
|
||||
typioparams[m],
|
||||
attr[m]->atttypmod,
|
||||
att->atttypmod,
|
||||
&nulls[m]);
|
||||
cstate->cur_attname = NULL;
|
||||
}
|
||||
@ -4709,13 +4712,12 @@ CopyGetAttnums(TupleDesc tupDesc, Relation rel, List *attnamelist)
|
||||
if (attnamelist == NIL)
|
||||
{
|
||||
/* Generate default column list */
|
||||
Form_pg_attribute *attr = tupDesc->attrs;
|
||||
int attr_count = tupDesc->natts;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < attr_count; i++)
|
||||
{
|
||||
if (attr[i]->attisdropped)
|
||||
if (TupleDescAttr(tupDesc, i)->attisdropped)
|
||||
continue;
|
||||
attnums = lappend_int(attnums, i + 1);
|
||||
}
|
||||
@ -4735,11 +4737,13 @@ CopyGetAttnums(TupleDesc tupDesc, Relation rel, List *attnamelist)
|
||||
attnum = InvalidAttrNumber;
|
||||
for (i = 0; i < tupDesc->natts; i++)
|
||||
{
|
||||
if (tupDesc->attrs[i]->attisdropped)
|
||||
Form_pg_attribute att = TupleDescAttr(tupDesc, i);
|
||||
|
||||
if (att->attisdropped)
|
||||
continue;
|
||||
if (namestrcmp(&(tupDesc->attrs[i]->attname), name) == 0)
|
||||
if (namestrcmp(&(att->attname), name) == 0)
|
||||
{
|
||||
attnum = tupDesc->attrs[i]->attnum;
|
||||
attnum = att->attnum;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -468,7 +468,7 @@ intorel_startup(DestReceiver *self, int operation, TupleDesc typeinfo)
|
||||
lc = list_head(into->colNames);
|
||||
for (attnum = 0; attnum < typeinfo->natts; attnum++)
|
||||
{
|
||||
Form_pg_attribute attribute = typeinfo->attrs[attnum];
|
||||
Form_pg_attribute attribute = TupleDescAttr(typeinfo, attnum);
|
||||
ColumnDef *col;
|
||||
char *colname;
|
||||
|
||||
|
@ -242,7 +242,7 @@ CheckIndexCompatible(Oid oldId,
|
||||
for (i = 0; i < old_natts; i++)
|
||||
{
|
||||
if (IsPolymorphicType(get_opclass_input_type(classObjectId[i])) &&
|
||||
irel->rd_att->attrs[i]->atttypid != typeObjectId[i])
|
||||
TupleDescAttr(irel->rd_att, i)->atttypid != typeObjectId[i])
|
||||
{
|
||||
ret = false;
|
||||
break;
|
||||
@ -270,7 +270,7 @@ CheckIndexCompatible(Oid oldId,
|
||||
|
||||
op_input_types(indexInfo->ii_ExclusionOps[i], &left, &right);
|
||||
if ((IsPolymorphicType(left) || IsPolymorphicType(right)) &&
|
||||
irel->rd_att->attrs[i]->atttypid != typeObjectId[i])
|
||||
TupleDescAttr(irel->rd_att, i)->atttypid != typeObjectId[i])
|
||||
{
|
||||
ret = false;
|
||||
break;
|
||||
|
@ -727,6 +727,7 @@ refresh_by_match_merge(Oid matviewOid, Oid tempOid, Oid relowner,
|
||||
for (i = 0; i < numatts; i++)
|
||||
{
|
||||
int attnum = indexStruct->indkey.values[i];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, attnum - 1);
|
||||
Oid type;
|
||||
Oid op;
|
||||
const char *colname;
|
||||
@ -745,7 +746,7 @@ refresh_by_match_merge(Oid matviewOid, Oid tempOid, Oid relowner,
|
||||
if (foundUniqueIndex)
|
||||
appendStringInfoString(&querybuf, " AND ");
|
||||
|
||||
colname = quote_identifier(NameStr((tupdesc->attrs[attnum - 1])->attname));
|
||||
colname = quote_identifier(NameStr(attr->attname));
|
||||
appendStringInfo(&querybuf, "newdata.%s ", colname);
|
||||
type = attnumTypeId(matviewRel, attnum);
|
||||
op = lookup_type_cache(type, TYPECACHE_EQ_OPR)->eq_opr;
|
||||
|
@ -685,8 +685,10 @@ DefineRelation(CreateStmt *stmt, char relkind, Oid ownerId,
|
||||
foreach(listptr, stmt->tableElts)
|
||||
{
|
||||
ColumnDef *colDef = lfirst(listptr);
|
||||
Form_pg_attribute attr;
|
||||
|
||||
attnum++;
|
||||
attr = TupleDescAttr(descriptor, attnum - 1);
|
||||
|
||||
if (colDef->raw_default != NULL)
|
||||
{
|
||||
@ -698,7 +700,7 @@ DefineRelation(CreateStmt *stmt, char relkind, Oid ownerId,
|
||||
rawEnt->attnum = attnum;
|
||||
rawEnt->raw_default = colDef->raw_default;
|
||||
rawDefaults = lappend(rawDefaults, rawEnt);
|
||||
descriptor->attrs[attnum - 1]->atthasdef = true;
|
||||
attr->atthasdef = true;
|
||||
}
|
||||
else if (colDef->cooked_default != NULL)
|
||||
{
|
||||
@ -715,11 +717,11 @@ DefineRelation(CreateStmt *stmt, char relkind, Oid ownerId,
|
||||
cooked->inhcount = 0; /* ditto */
|
||||
cooked->is_no_inherit = false;
|
||||
cookedDefaults = lappend(cookedDefaults, cooked);
|
||||
descriptor->attrs[attnum - 1]->atthasdef = true;
|
||||
attr->atthasdef = true;
|
||||
}
|
||||
|
||||
if (colDef->identity)
|
||||
descriptor->attrs[attnum - 1]->attidentity = colDef->identity;
|
||||
attr->attidentity = colDef->identity;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -1833,7 +1835,8 @@ MergeAttributes(List *schema, List *supers, char relpersistence,
|
||||
for (parent_attno = 1; parent_attno <= tupleDesc->natts;
|
||||
parent_attno++)
|
||||
{
|
||||
Form_pg_attribute attribute = tupleDesc->attrs[parent_attno - 1];
|
||||
Form_pg_attribute attribute = TupleDescAttr(tupleDesc,
|
||||
parent_attno - 1);
|
||||
char *attributeName = NameStr(attribute->attname);
|
||||
int exist_attno;
|
||||
ColumnDef *def;
|
||||
@ -4417,8 +4420,9 @@ ATRewriteTable(AlteredTableInfo *tab, Oid OIDNewHeap, LOCKMODE lockmode)
|
||||
*/
|
||||
for (i = 0; i < newTupDesc->natts; i++)
|
||||
{
|
||||
if (newTupDesc->attrs[i]->attnotnull &&
|
||||
!newTupDesc->attrs[i]->attisdropped)
|
||||
Form_pg_attribute attr = TupleDescAttr(newTupDesc, i);
|
||||
|
||||
if (attr->attnotnull && !attr->attisdropped)
|
||||
notnull_attrs = lappend_int(notnull_attrs, i);
|
||||
}
|
||||
if (notnull_attrs)
|
||||
@ -4482,7 +4486,7 @@ ATRewriteTable(AlteredTableInfo *tab, Oid OIDNewHeap, LOCKMODE lockmode)
|
||||
*/
|
||||
for (i = 0; i < newTupDesc->natts; i++)
|
||||
{
|
||||
if (newTupDesc->attrs[i]->attisdropped)
|
||||
if (TupleDescAttr(newTupDesc, i)->attisdropped)
|
||||
dropped_attrs = lappend_int(dropped_attrs, i);
|
||||
}
|
||||
|
||||
@ -4556,11 +4560,15 @@ ATRewriteTable(AlteredTableInfo *tab, Oid OIDNewHeap, LOCKMODE lockmode)
|
||||
int attn = lfirst_int(l);
|
||||
|
||||
if (heap_attisnull(tuple, attn + 1))
|
||||
{
|
||||
Form_pg_attribute attr = TupleDescAttr(newTupDesc, attn);
|
||||
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_NOT_NULL_VIOLATION),
|
||||
errmsg("column \"%s\" contains null values",
|
||||
NameStr(newTupDesc->attrs[attn]->attname)),
|
||||
NameStr(attr->attname)),
|
||||
errtablecol(oldrel, attn + 1)));
|
||||
}
|
||||
}
|
||||
|
||||
foreach(l, tab->constraints)
|
||||
@ -4927,7 +4935,7 @@ find_composite_type_dependencies(Oid typeOid, Relation origRelation,
|
||||
continue;
|
||||
|
||||
rel = relation_open(pg_depend->objid, AccessShareLock);
|
||||
att = rel->rd_att->attrs[pg_depend->objsubid - 1];
|
||||
att = TupleDescAttr(rel->rd_att, pg_depend->objsubid - 1);
|
||||
|
||||
if (rel->rd_rel->relkind == RELKIND_RELATION ||
|
||||
rel->rd_rel->relkind == RELKIND_MATVIEW ||
|
||||
@ -5693,7 +5701,7 @@ ATExecDropNotNull(Relation rel, const char *colName, LOCKMODE lockmode)
|
||||
AttrNumber parent_attnum;
|
||||
|
||||
parent_attnum = get_attnum(parentId, colName);
|
||||
if (tupDesc->attrs[parent_attnum - 1]->attnotnull)
|
||||
if (TupleDescAttr(tupDesc, parent_attnum - 1)->attnotnull)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_INVALID_TABLE_DEFINITION),
|
||||
errmsg("column \"%s\" is marked NOT NULL in parent table",
|
||||
@ -7286,13 +7294,15 @@ ATAddForeignKeyConstraint(AlteredTableInfo *tab, Relation rel,
|
||||
CoercionPathType new_pathtype;
|
||||
Oid old_castfunc;
|
||||
Oid new_castfunc;
|
||||
Form_pg_attribute attr = TupleDescAttr(tab->oldDesc,
|
||||
fkattnum[i] - 1);
|
||||
|
||||
/*
|
||||
* Identify coercion pathways from each of the old and new FK-side
|
||||
* column types to the right (foreign) operand type of the pfeqop.
|
||||
* We may assume that pg_constraint.conkey is not changing.
|
||||
*/
|
||||
old_fktype = tab->oldDesc->attrs[fkattnum[i] - 1]->atttypid;
|
||||
old_fktype = attr->atttypid;
|
||||
new_fktype = fktype;
|
||||
old_pathtype = findFkeyCast(pfeqop_right, old_fktype,
|
||||
&old_castfunc);
|
||||
@ -8963,7 +8973,8 @@ ATExecAlterColumnType(AlteredTableInfo *tab, Relation rel,
|
||||
ColumnDef *def = (ColumnDef *) cmd->def;
|
||||
TypeName *typeName = def->typeName;
|
||||
HeapTuple heapTup;
|
||||
Form_pg_attribute attTup;
|
||||
Form_pg_attribute attTup,
|
||||
attOldTup;
|
||||
AttrNumber attnum;
|
||||
HeapTuple typeTuple;
|
||||
Form_pg_type tform;
|
||||
@ -8989,10 +9000,11 @@ ATExecAlterColumnType(AlteredTableInfo *tab, Relation rel,
|
||||
colName, RelationGetRelationName(rel))));
|
||||
attTup = (Form_pg_attribute) GETSTRUCT(heapTup);
|
||||
attnum = attTup->attnum;
|
||||
attOldTup = TupleDescAttr(tab->oldDesc, attnum - 1);
|
||||
|
||||
/* Check for multiple ALTER TYPE on same column --- can't cope */
|
||||
if (attTup->atttypid != tab->oldDesc->attrs[attnum - 1]->atttypid ||
|
||||
attTup->atttypmod != tab->oldDesc->attrs[attnum - 1]->atttypmod)
|
||||
if (attTup->atttypid != attOldTup->atttypid ||
|
||||
attTup->atttypmod != attOldTup->atttypmod)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
|
||||
errmsg("cannot alter type of column \"%s\" twice",
|
||||
@ -11209,7 +11221,8 @@ MergeAttributesIntoExisting(Relation child_rel, Relation parent_rel)
|
||||
|
||||
for (parent_attno = 1; parent_attno <= parent_natts; parent_attno++)
|
||||
{
|
||||
Form_pg_attribute attribute = tupleDesc->attrs[parent_attno - 1];
|
||||
Form_pg_attribute attribute = TupleDescAttr(tupleDesc,
|
||||
parent_attno - 1);
|
||||
char *attributeName = NameStr(attribute->attname);
|
||||
|
||||
/* Ignore dropped columns in the parent. */
|
||||
@ -11822,7 +11835,7 @@ ATExecAddOf(Relation rel, const TypeName *ofTypename, LOCKMODE lockmode)
|
||||
*table_attname;
|
||||
|
||||
/* Get the next non-dropped type attribute. */
|
||||
type_attr = typeTupleDesc->attrs[type_attno - 1];
|
||||
type_attr = TupleDescAttr(typeTupleDesc, type_attno - 1);
|
||||
if (type_attr->attisdropped)
|
||||
continue;
|
||||
type_attname = NameStr(type_attr->attname);
|
||||
@ -11835,7 +11848,8 @@ ATExecAddOf(Relation rel, const TypeName *ofTypename, LOCKMODE lockmode)
|
||||
(errcode(ERRCODE_DATATYPE_MISMATCH),
|
||||
errmsg("table is missing column \"%s\"",
|
||||
type_attname)));
|
||||
table_attr = tableTupleDesc->attrs[table_attno++ - 1];
|
||||
table_attr = TupleDescAttr(tableTupleDesc, table_attno - 1);
|
||||
table_attno++;
|
||||
} while (table_attr->attisdropped);
|
||||
table_attname = NameStr(table_attr->attname);
|
||||
|
||||
@ -11860,7 +11874,8 @@ ATExecAddOf(Relation rel, const TypeName *ofTypename, LOCKMODE lockmode)
|
||||
/* Any remaining columns at the end of the table had better be dropped. */
|
||||
for (; table_attno <= tableTupleDesc->natts; table_attno++)
|
||||
{
|
||||
Form_pg_attribute table_attr = tableTupleDesc->attrs[table_attno - 1];
|
||||
Form_pg_attribute table_attr = TupleDescAttr(tableTupleDesc,
|
||||
table_attno - 1);
|
||||
|
||||
if (!table_attr->attisdropped)
|
||||
ereport(ERROR,
|
||||
@ -12147,7 +12162,7 @@ ATExecReplicaIdentity(Relation rel, ReplicaIdentityStmt *stmt, LOCKMODE lockmode
|
||||
errmsg("index \"%s\" cannot be used as replica identity because column %d is a system column",
|
||||
RelationGetRelationName(indexRel), attno)));
|
||||
|
||||
attr = rel->rd_att->attrs[attno - 1];
|
||||
attr = TupleDescAttr(rel->rd_att, attno - 1);
|
||||
if (!attr->attnotnull)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_WRONG_OBJECT_TYPE),
|
||||
@ -13451,7 +13466,7 @@ PartConstraintImpliedByRelConstraint(Relation scanrel,
|
||||
|
||||
for (i = 1; i <= natts; i++)
|
||||
{
|
||||
Form_pg_attribute att = scanrel->rd_att->attrs[i - 1];
|
||||
Form_pg_attribute att = TupleDescAttr(scanrel->rd_att, i - 1);
|
||||
|
||||
if (att->attnotnull && !att->attisdropped)
|
||||
{
|
||||
@ -13733,7 +13748,7 @@ ATExecAttachPartition(List **wqueue, Relation rel, PartitionCmd *cmd)
|
||||
natts = tupleDesc->natts;
|
||||
for (attno = 1; attno <= natts; attno++)
|
||||
{
|
||||
Form_pg_attribute attribute = tupleDesc->attrs[attno - 1];
|
||||
Form_pg_attribute attribute = TupleDescAttr(tupleDesc, attno - 1);
|
||||
char *attributeName = NameStr(attribute->attname);
|
||||
|
||||
/* Ignore dropped */
|
||||
|
@ -2324,6 +2324,7 @@ AlterDomainNotNull(List *names, bool notNull)
|
||||
for (i = 0; i < rtc->natts; i++)
|
||||
{
|
||||
int attnum = rtc->atts[i];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, attnum - 1);
|
||||
|
||||
if (heap_attisnull(tuple, attnum))
|
||||
{
|
||||
@ -2338,7 +2339,7 @@ AlterDomainNotNull(List *names, bool notNull)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_NOT_NULL_VIOLATION),
|
||||
errmsg("column \"%s\" of table \"%s\" contains null values",
|
||||
NameStr(tupdesc->attrs[attnum - 1]->attname),
|
||||
NameStr(attr->attname),
|
||||
RelationGetRelationName(testrel)),
|
||||
errtablecol(testrel, attnum)));
|
||||
}
|
||||
@ -2722,6 +2723,7 @@ validateDomainConstraint(Oid domainoid, char *ccbin)
|
||||
Datum d;
|
||||
bool isNull;
|
||||
Datum conResult;
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, attnum - 1);
|
||||
|
||||
d = heap_getattr(tuple, attnum, tupdesc, &isNull);
|
||||
|
||||
@ -2745,7 +2747,7 @@ validateDomainConstraint(Oid domainoid, char *ccbin)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_CHECK_VIOLATION),
|
||||
errmsg("column \"%s\" of table \"%s\" contains values that violate the new constraint",
|
||||
NameStr(tupdesc->attrs[attnum - 1]->attname),
|
||||
NameStr(attr->attname),
|
||||
RelationGetRelationName(testrel)),
|
||||
errtablecol(testrel, attnum)));
|
||||
}
|
||||
@ -2930,7 +2932,7 @@ get_rels_with_domain(Oid domainOid, LOCKMODE lockmode)
|
||||
*/
|
||||
if (pg_depend->objsubid > RelationGetNumberOfAttributes(rtc->rel))
|
||||
continue;
|
||||
pg_att = rtc->rel->rd_att->attrs[pg_depend->objsubid - 1];
|
||||
pg_att = TupleDescAttr(rtc->rel->rd_att, pg_depend->objsubid - 1);
|
||||
if (pg_att->attisdropped || pg_att->atttypid != domainOid)
|
||||
continue;
|
||||
|
||||
|
@ -283,8 +283,8 @@ checkViewTupleDesc(TupleDesc newdesc, TupleDesc olddesc)
|
||||
|
||||
for (i = 0; i < olddesc->natts; i++)
|
||||
{
|
||||
Form_pg_attribute newattr = newdesc->attrs[i];
|
||||
Form_pg_attribute oldattr = olddesc->attrs[i];
|
||||
Form_pg_attribute newattr = TupleDescAttr(newdesc, i);
|
||||
Form_pg_attribute oldattr = TupleDescAttr(olddesc, i);
|
||||
|
||||
/* XXX msg not right, but we don't support DROP COL on view anyway */
|
||||
if (newattr->attisdropped != oldattr->attisdropped)
|
||||
|
@ -347,7 +347,7 @@ ExecBuildProjectionInfo(List *targetList,
|
||||
isSafeVar = true; /* can't check, just assume OK */
|
||||
else if (attnum <= inputDesc->natts)
|
||||
{
|
||||
Form_pg_attribute attr = inputDesc->attrs[attnum - 1];
|
||||
Form_pg_attribute attr = TupleDescAttr(inputDesc, attnum - 1);
|
||||
|
||||
/*
|
||||
* If user attribute is dropped or has a type mismatch, don't
|
||||
@ -1492,7 +1492,6 @@ ExecInitExprRec(Expr *node, PlanState *parent, ExprState *state,
|
||||
RowExpr *rowexpr = (RowExpr *) node;
|
||||
int nelems = list_length(rowexpr->args);
|
||||
TupleDesc tupdesc;
|
||||
Form_pg_attribute *attrs;
|
||||
int i;
|
||||
ListCell *l;
|
||||
|
||||
@ -1539,13 +1538,13 @@ ExecInitExprRec(Expr *node, PlanState *parent, ExprState *state,
|
||||
memset(scratch.d.row.elemnulls, true, sizeof(bool) * nelems);
|
||||
|
||||
/* Set up evaluation, skipping any deleted columns */
|
||||
attrs = tupdesc->attrs;
|
||||
i = 0;
|
||||
foreach(l, rowexpr->args)
|
||||
{
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
Expr *e = (Expr *) lfirst(l);
|
||||
|
||||
if (!attrs[i]->attisdropped)
|
||||
if (!att->attisdropped)
|
||||
{
|
||||
/*
|
||||
* Guard against ALTER COLUMN TYPE on rowtype since
|
||||
@ -1553,12 +1552,12 @@ ExecInitExprRec(Expr *node, PlanState *parent, ExprState *state,
|
||||
* typmod too? Not sure we can be sure it'll be the
|
||||
* same.
|
||||
*/
|
||||
if (exprType((Node *) e) != attrs[i]->atttypid)
|
||||
if (exprType((Node *) e) != att->atttypid)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_DATATYPE_MISMATCH),
|
||||
errmsg("ROW() column has type %s instead of type %s",
|
||||
format_type_be(exprType((Node *) e)),
|
||||
format_type_be(attrs[i]->atttypid))));
|
||||
format_type_be(att->atttypid))));
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -1553,7 +1553,7 @@ CheckVarSlotCompatibility(TupleTableSlot *slot, int attnum, Oid vartype)
|
||||
elog(ERROR, "attribute number %d exceeds number of columns %d",
|
||||
attnum, slot_tupdesc->natts);
|
||||
|
||||
attr = slot_tupdesc->attrs[attnum - 1];
|
||||
attr = TupleDescAttr(slot_tupdesc, attnum - 1);
|
||||
|
||||
if (attr->attisdropped)
|
||||
ereport(ERROR,
|
||||
@ -2081,7 +2081,7 @@ ExecEvalRowNullInt(ExprState *state, ExprEvalStep *op,
|
||||
for (att = 1; att <= tupDesc->natts; att++)
|
||||
{
|
||||
/* ignore dropped columns */
|
||||
if (tupDesc->attrs[att - 1]->attisdropped)
|
||||
if (TupleDescAttr(tupDesc, att - 1)->attisdropped)
|
||||
continue;
|
||||
if (heap_attisnull(&tmptup, att))
|
||||
{
|
||||
@ -2494,7 +2494,7 @@ ExecEvalFieldSelect(ExprState *state, ExprEvalStep *op, ExprContext *econtext)
|
||||
if (fieldnum > tupDesc->natts) /* should never happen */
|
||||
elog(ERROR, "attribute number %d exceeds number of columns %d",
|
||||
fieldnum, tupDesc->natts);
|
||||
attr = tupDesc->attrs[fieldnum - 1];
|
||||
attr = TupleDescAttr(tupDesc, fieldnum - 1);
|
||||
|
||||
/* Check for dropped column, and force a NULL result if so */
|
||||
if (attr->attisdropped)
|
||||
@ -3441,8 +3441,8 @@ ExecEvalWholeRowVar(ExprState *state, ExprEvalStep *op, ExprContext *econtext)
|
||||
|
||||
for (i = 0; i < var_tupdesc->natts; i++)
|
||||
{
|
||||
Form_pg_attribute vattr = var_tupdesc->attrs[i];
|
||||
Form_pg_attribute sattr = slot_tupdesc->attrs[i];
|
||||
Form_pg_attribute vattr = TupleDescAttr(var_tupdesc, i);
|
||||
Form_pg_attribute sattr = TupleDescAttr(slot_tupdesc, i);
|
||||
|
||||
if (vattr->atttypid == sattr->atttypid)
|
||||
continue; /* no worries */
|
||||
@ -3540,8 +3540,8 @@ ExecEvalWholeRowVar(ExprState *state, ExprEvalStep *op, ExprContext *econtext)
|
||||
|
||||
for (i = 0; i < var_tupdesc->natts; i++)
|
||||
{
|
||||
Form_pg_attribute vattr = var_tupdesc->attrs[i];
|
||||
Form_pg_attribute sattr = tupleDesc->attrs[i];
|
||||
Form_pg_attribute vattr = TupleDescAttr(var_tupdesc, i);
|
||||
Form_pg_attribute sattr = TupleDescAttr(tupleDesc, i);
|
||||
|
||||
if (!vattr->attisdropped)
|
||||
continue; /* already checked non-dropped cols */
|
||||
|
@ -168,7 +168,7 @@ ExecInitJunkFilterConversion(List *targetList,
|
||||
t = list_head(targetList);
|
||||
for (i = 0; i < cleanLength; i++)
|
||||
{
|
||||
if (cleanTupType->attrs[i]->attisdropped)
|
||||
if (TupleDescAttr(cleanTupType, i)->attisdropped)
|
||||
continue; /* map entry is already zero */
|
||||
for (;;)
|
||||
{
|
||||
|
@ -1950,8 +1950,9 @@ ExecConstraints(ResultRelInfo *resultRelInfo,
|
||||
|
||||
for (attrChk = 1; attrChk <= natts; attrChk++)
|
||||
{
|
||||
if (tupdesc->attrs[attrChk - 1]->attnotnull &&
|
||||
slot_attisnull(slot, attrChk))
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, attrChk - 1);
|
||||
|
||||
if (att->attnotnull && slot_attisnull(slot, attrChk))
|
||||
{
|
||||
char *val_desc;
|
||||
Relation orig_rel = rel;
|
||||
@ -1994,7 +1995,7 @@ ExecConstraints(ResultRelInfo *resultRelInfo,
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_NOT_NULL_VIOLATION),
|
||||
errmsg("null value in column \"%s\" violates not-null constraint",
|
||||
NameStr(orig_tupdesc->attrs[attrChk - 1]->attname)),
|
||||
NameStr(att->attname)),
|
||||
val_desc ? errdetail("Failing row contains %s.", val_desc) : 0,
|
||||
errtablecol(orig_rel, attrChk)));
|
||||
}
|
||||
@ -2261,9 +2262,10 @@ ExecBuildSlotValueDescription(Oid reloid,
|
||||
bool column_perm = false;
|
||||
char *val;
|
||||
int vallen;
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
|
||||
/* ignore dropped columns */
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
if (att->attisdropped)
|
||||
continue;
|
||||
|
||||
if (!table_perm)
|
||||
@ -2274,9 +2276,9 @@ ExecBuildSlotValueDescription(Oid reloid,
|
||||
* for the column. If not, omit this column from the error
|
||||
* message.
|
||||
*/
|
||||
aclresult = pg_attribute_aclcheck(reloid, tupdesc->attrs[i]->attnum,
|
||||
aclresult = pg_attribute_aclcheck(reloid, att->attnum,
|
||||
GetUserId(), ACL_SELECT);
|
||||
if (bms_is_member(tupdesc->attrs[i]->attnum - FirstLowInvalidHeapAttributeNumber,
|
||||
if (bms_is_member(att->attnum - FirstLowInvalidHeapAttributeNumber,
|
||||
modifiedCols) || aclresult == ACLCHECK_OK)
|
||||
{
|
||||
column_perm = any_perm = true;
|
||||
@ -2286,7 +2288,7 @@ ExecBuildSlotValueDescription(Oid reloid,
|
||||
else
|
||||
write_comma_collist = true;
|
||||
|
||||
appendStringInfoString(&collist, NameStr(tupdesc->attrs[i]->attname));
|
||||
appendStringInfoString(&collist, NameStr(att->attname));
|
||||
}
|
||||
}
|
||||
|
||||
@ -2299,7 +2301,7 @@ ExecBuildSlotValueDescription(Oid reloid,
|
||||
Oid foutoid;
|
||||
bool typisvarlena;
|
||||
|
||||
getTypeOutputInfo(tupdesc->attrs[i]->atttypid,
|
||||
getTypeOutputInfo(att->atttypid,
|
||||
&foutoid, &typisvarlena);
|
||||
val = OidOutputFunctionCall(foutoid, slot->tts_values[i]);
|
||||
}
|
||||
|
@ -247,7 +247,7 @@ tuple_equals_slot(TupleDesc desc, HeapTuple tup, TupleTableSlot *slot)
|
||||
if (isnull[attrnum])
|
||||
continue;
|
||||
|
||||
att = desc->attrs[attrnum];
|
||||
att = TupleDescAttr(desc, attrnum);
|
||||
|
||||
typentry = lookup_type_cache(att->atttypid, TYPECACHE_EQ_OPR_FINFO);
|
||||
if (!OidIsValid(typentry->eq_opr_finfo.fn_oid))
|
||||
|
@ -903,8 +903,8 @@ tupledesc_match(TupleDesc dst_tupdesc, TupleDesc src_tupdesc)
|
||||
|
||||
for (i = 0; i < dst_tupdesc->natts; i++)
|
||||
{
|
||||
Form_pg_attribute dattr = dst_tupdesc->attrs[i];
|
||||
Form_pg_attribute sattr = src_tupdesc->attrs[i];
|
||||
Form_pg_attribute dattr = TupleDescAttr(dst_tupdesc, i);
|
||||
Form_pg_attribute sattr = TupleDescAttr(src_tupdesc, i);
|
||||
|
||||
if (IsBinaryCoercible(sattr->atttypid, dattr->atttypid))
|
||||
continue; /* no worries */
|
||||
|
@ -269,7 +269,7 @@ tlist_matches_tupdesc(PlanState *ps, List *tlist, Index varno, TupleDesc tupdesc
|
||||
/* Check the tlist attributes */
|
||||
for (attrno = 1; attrno <= numattrs; attrno++)
|
||||
{
|
||||
Form_pg_attribute att_tup = tupdesc->attrs[attrno - 1];
|
||||
Form_pg_attribute att_tup = TupleDescAttr(tupdesc, attrno - 1);
|
||||
Var *var;
|
||||
|
||||
if (tlist_item == NULL)
|
||||
|
@ -997,7 +997,8 @@ ExecTypeSetColNames(TupleDesc typeInfo, List *namesList)
|
||||
/* Guard against too-long names list */
|
||||
if (colno >= typeInfo->natts)
|
||||
break;
|
||||
attr = typeInfo->attrs[colno++];
|
||||
attr = TupleDescAttr(typeInfo, colno);
|
||||
colno++;
|
||||
|
||||
/* Ignore empty aliases (these must be for dropped columns) */
|
||||
if (cname[0] == '\0')
|
||||
@ -1090,13 +1091,15 @@ TupleDescGetAttInMetadata(TupleDesc tupdesc)
|
||||
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
|
||||
/* Ignore dropped attributes */
|
||||
if (!tupdesc->attrs[i]->attisdropped)
|
||||
if (!att->attisdropped)
|
||||
{
|
||||
atttypeid = tupdesc->attrs[i]->atttypid;
|
||||
atttypeid = att->atttypid;
|
||||
getTypeInputInfo(atttypeid, &attinfuncid, &attioparams[i]);
|
||||
fmgr_info(attinfuncid, &attinfuncinfo[i]);
|
||||
atttypmods[i] = tupdesc->attrs[i]->atttypmod;
|
||||
atttypmods[i] = att->atttypmod;
|
||||
}
|
||||
}
|
||||
attinmeta->attinfuncs = attinfuncinfo;
|
||||
@ -1127,7 +1130,7 @@ BuildTupleFromCStrings(AttInMetadata *attinmeta, char **values)
|
||||
/* Call the "in" function for each non-dropped attribute */
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
if (!tupdesc->attrs[i]->attisdropped)
|
||||
if (!TupleDescAttr(tupdesc, i)->attisdropped)
|
||||
{
|
||||
/* Non-dropped attributes */
|
||||
dvalues[i] = InputFunctionCall(&attinmeta->attinfuncs[i],
|
||||
|
@ -917,9 +917,11 @@ GetAttributeByName(HeapTupleHeader tuple, const char *attname, bool *isNull)
|
||||
attrno = InvalidAttrNumber;
|
||||
for (i = 0; i < tupDesc->natts; i++)
|
||||
{
|
||||
if (namestrcmp(&(tupDesc->attrs[i]->attname), attname) == 0)
|
||||
Form_pg_attribute att = TupleDescAttr(tupDesc, i);
|
||||
|
||||
if (namestrcmp(&(att->attname), attname) == 0)
|
||||
{
|
||||
attrno = tupDesc->attrs[i]->attnum;
|
||||
attrno = att->attnum;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -1759,7 +1759,7 @@ check_sql_fn_retval(Oid func_id, Oid rettype, List *queryTreeList,
|
||||
errmsg("return type mismatch in function declared to return %s",
|
||||
format_type_be(rettype)),
|
||||
errdetail("Final statement returns too many columns.")));
|
||||
attr = tupdesc->attrs[colindex - 1];
|
||||
attr = TupleDescAttr(tupdesc, colindex - 1);
|
||||
if (attr->attisdropped && modifyTargetList)
|
||||
{
|
||||
Expr *null_expr;
|
||||
@ -1816,7 +1816,7 @@ check_sql_fn_retval(Oid func_id, Oid rettype, List *queryTreeList,
|
||||
/* remaining columns in tupdesc had better all be dropped */
|
||||
for (colindex++; colindex <= tupnatts; colindex++)
|
||||
{
|
||||
if (!tupdesc->attrs[colindex - 1]->attisdropped)
|
||||
if (!TupleDescAttr(tupdesc, colindex - 1)->attisdropped)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_INVALID_FUNCTION_DEFINITION),
|
||||
errmsg("return type mismatch in function declared to return %s",
|
||||
|
@ -724,12 +724,16 @@ initialize_aggregate(AggState *aggstate, AggStatePerTrans pertrans,
|
||||
* process_ordered_aggregate_single.)
|
||||
*/
|
||||
if (pertrans->numInputs == 1)
|
||||
{
|
||||
Form_pg_attribute attr = TupleDescAttr(pertrans->sortdesc, 0);
|
||||
|
||||
pertrans->sortstates[aggstate->current_set] =
|
||||
tuplesort_begin_datum(pertrans->sortdesc->attrs[0]->atttypid,
|
||||
tuplesort_begin_datum(attr->atttypid,
|
||||
pertrans->sortOperators[0],
|
||||
pertrans->sortCollations[0],
|
||||
pertrans->sortNullsFirst[0],
|
||||
work_mem, false);
|
||||
}
|
||||
else
|
||||
pertrans->sortstates[aggstate->current_set] =
|
||||
tuplesort_begin_heap(pertrans->sortdesc,
|
||||
|
@ -95,7 +95,8 @@ ExecCheckPlanOutput(Relation resultRel, List *targetList)
|
||||
(errcode(ERRCODE_DATATYPE_MISMATCH),
|
||||
errmsg("table row type and query-specified row type do not match"),
|
||||
errdetail("Query has too many columns.")));
|
||||
attr = resultDesc->attrs[attno++];
|
||||
attr = TupleDescAttr(resultDesc, attno);
|
||||
attno++;
|
||||
|
||||
if (!attr->attisdropped)
|
||||
{
|
||||
|
@ -360,7 +360,7 @@ ExecScanSubPlan(SubPlanState *node,
|
||||
|
||||
found = true;
|
||||
/* stash away current value */
|
||||
Assert(subplan->firstColType == tdesc->attrs[0]->atttypid);
|
||||
Assert(subplan->firstColType == TupleDescAttr(tdesc, 0)->atttypid);
|
||||
dvalue = slot_getattr(slot, 1, &disnull);
|
||||
astate = accumArrayResultAny(astate, dvalue, disnull,
|
||||
subplan->firstColType, oldcontext);
|
||||
@ -992,7 +992,7 @@ ExecSetParamPlan(SubPlanState *node, ExprContext *econtext)
|
||||
|
||||
found = true;
|
||||
/* stash away current value */
|
||||
Assert(subplan->firstColType == tdesc->attrs[0]->atttypid);
|
||||
Assert(subplan->firstColType == TupleDescAttr(tdesc, 0)->atttypid);
|
||||
dvalue = slot_getattr(slot, 1, &disnull);
|
||||
astate = accumArrayResultAny(astate, dvalue, disnull,
|
||||
subplan->firstColType, oldcontext);
|
||||
|
@ -202,7 +202,7 @@ ExecInitTableFuncScan(TableFuncScan *node, EState *estate, int eflags)
|
||||
{
|
||||
Oid in_funcid;
|
||||
|
||||
getTypeInputInfo(tupdesc->attrs[i]->atttypid,
|
||||
getTypeInputInfo(TupleDescAttr(tupdesc, i)->atttypid,
|
||||
&in_funcid, &scanstate->typioparams[i]);
|
||||
fmgr_info(in_funcid, &scanstate->in_functions[i]);
|
||||
}
|
||||
@ -390,6 +390,7 @@ tfuncInitialize(TableFuncScanState *tstate, ExprContext *econtext, Datum doc)
|
||||
foreach(lc1, tstate->colexprs)
|
||||
{
|
||||
char *colfilter;
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, colno);
|
||||
|
||||
if (colno != ordinalitycol)
|
||||
{
|
||||
@ -403,11 +404,11 @@ tfuncInitialize(TableFuncScanState *tstate, ExprContext *econtext, Datum doc)
|
||||
(errcode(ERRCODE_NULL_VALUE_NOT_ALLOWED),
|
||||
errmsg("column filter expression must not be null"),
|
||||
errdetail("Filter for column \"%s\" is null.",
|
||||
NameStr(tupdesc->attrs[colno]->attname))));
|
||||
NameStr(att->attname))));
|
||||
colfilter = TextDatumGetCString(value);
|
||||
}
|
||||
else
|
||||
colfilter = NameStr(tupdesc->attrs[colno]->attname);
|
||||
colfilter = NameStr(att->attname);
|
||||
|
||||
routine->SetColumnFilter(tstate, colfilter, colno);
|
||||
}
|
||||
@ -453,6 +454,8 @@ tfuncLoadRows(TableFuncScanState *tstate, ExprContext *econtext)
|
||||
*/
|
||||
for (colno = 0; colno < natts; colno++)
|
||||
{
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, colno);
|
||||
|
||||
if (colno == ordinalitycol)
|
||||
{
|
||||
/* Fast path for ordinality column */
|
||||
@ -465,8 +468,8 @@ tfuncLoadRows(TableFuncScanState *tstate, ExprContext *econtext)
|
||||
|
||||
values[colno] = routine->GetValue(tstate,
|
||||
colno,
|
||||
tupdesc->attrs[colno]->atttypid,
|
||||
tupdesc->attrs[colno]->atttypmod,
|
||||
att->atttypid,
|
||||
att->atttypmod,
|
||||
&isnull);
|
||||
|
||||
/* No value? Evaluate and apply the default, if any */
|
||||
@ -484,7 +487,7 @@ tfuncLoadRows(TableFuncScanState *tstate, ExprContext *econtext)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_NULL_VALUE_NOT_ALLOWED),
|
||||
errmsg("null is not allowed in column \"%s\"",
|
||||
NameStr(tupdesc->attrs[colno]->attname))));
|
||||
NameStr(att->attname))));
|
||||
|
||||
nulls[colno] = isnull;
|
||||
}
|
||||
|
@ -95,7 +95,6 @@ ValuesNext(ValuesScanState *node)
|
||||
List *exprstatelist;
|
||||
Datum *values;
|
||||
bool *isnull;
|
||||
Form_pg_attribute *att;
|
||||
ListCell *lc;
|
||||
int resind;
|
||||
|
||||
@ -131,12 +130,13 @@ ValuesNext(ValuesScanState *node)
|
||||
*/
|
||||
values = slot->tts_values;
|
||||
isnull = slot->tts_isnull;
|
||||
att = slot->tts_tupleDescriptor->attrs;
|
||||
|
||||
resind = 0;
|
||||
foreach(lc, exprstatelist)
|
||||
{
|
||||
ExprState *estate = (ExprState *) lfirst(lc);
|
||||
Form_pg_attribute attr = TupleDescAttr(slot->tts_tupleDescriptor,
|
||||
resind);
|
||||
|
||||
values[resind] = ExecEvalExpr(estate,
|
||||
econtext,
|
||||
@ -150,7 +150,7 @@ ValuesNext(ValuesScanState *node)
|
||||
*/
|
||||
values[resind] = MakeExpandedObjectReadOnly(values[resind],
|
||||
isnull[resind],
|
||||
att[resind]->attlen);
|
||||
attr->attlen);
|
||||
|
||||
resind++;
|
||||
}
|
||||
|
@ -765,8 +765,10 @@ SPI_fnumber(TupleDesc tupdesc, const char *fname)
|
||||
|
||||
for (res = 0; res < tupdesc->natts; res++)
|
||||
{
|
||||
if (namestrcmp(&tupdesc->attrs[res]->attname, fname) == 0 &&
|
||||
!tupdesc->attrs[res]->attisdropped)
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, res);
|
||||
|
||||
if (namestrcmp(&attr->attname, fname) == 0 &&
|
||||
!attr->attisdropped)
|
||||
return res + 1;
|
||||
}
|
||||
|
||||
@ -793,7 +795,7 @@ SPI_fname(TupleDesc tupdesc, int fnumber)
|
||||
}
|
||||
|
||||
if (fnumber > 0)
|
||||
att = tupdesc->attrs[fnumber - 1];
|
||||
att = TupleDescAttr(tupdesc, fnumber - 1);
|
||||
else
|
||||
att = SystemAttributeDefinition(fnumber, true);
|
||||
|
||||
@ -823,7 +825,7 @@ SPI_getvalue(HeapTuple tuple, TupleDesc tupdesc, int fnumber)
|
||||
return NULL;
|
||||
|
||||
if (fnumber > 0)
|
||||
typoid = tupdesc->attrs[fnumber - 1]->atttypid;
|
||||
typoid = TupleDescAttr(tupdesc, fnumber - 1)->atttypid;
|
||||
else
|
||||
typoid = (SystemAttributeDefinition(fnumber, true))->atttypid;
|
||||
|
||||
@ -865,7 +867,7 @@ SPI_gettype(TupleDesc tupdesc, int fnumber)
|
||||
}
|
||||
|
||||
if (fnumber > 0)
|
||||
typoid = tupdesc->attrs[fnumber - 1]->atttypid;
|
||||
typoid = TupleDescAttr(tupdesc, fnumber - 1)->atttypid;
|
||||
else
|
||||
typoid = (SystemAttributeDefinition(fnumber, true))->atttypid;
|
||||
|
||||
@ -901,7 +903,7 @@ SPI_gettypeid(TupleDesc tupdesc, int fnumber)
|
||||
}
|
||||
|
||||
if (fnumber > 0)
|
||||
return tupdesc->attrs[fnumber - 1]->atttypid;
|
||||
return TupleDescAttr(tupdesc, fnumber - 1)->atttypid;
|
||||
else
|
||||
return (SystemAttributeDefinition(fnumber, true))->atttypid;
|
||||
}
|
||||
|
@ -551,7 +551,7 @@ TQSendRecordInfo(TQueueDestReceiver *tqueue, int32 typmod, TupleDesc tupledesc)
|
||||
appendBinaryStringInfo(&buf, (char *) &tupledesc->tdhasoid, sizeof(bool));
|
||||
for (i = 0; i < tupledesc->natts; i++)
|
||||
{
|
||||
appendBinaryStringInfo(&buf, (char *) tupledesc->attrs[i],
|
||||
appendBinaryStringInfo(&buf, (char *) TupleDescAttr(tupledesc, i),
|
||||
sizeof(FormData_pg_attribute));
|
||||
}
|
||||
|
||||
@ -1253,7 +1253,7 @@ BuildFieldRemapInfo(TupleDesc tupledesc, MemoryContext mycontext)
|
||||
tupledesc->natts * sizeof(TupleRemapInfo *));
|
||||
for (i = 0; i < tupledesc->natts; i++)
|
||||
{
|
||||
Form_pg_attribute attr = tupledesc->attrs[i];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupledesc, i);
|
||||
|
||||
if (attr->attisdropped)
|
||||
{
|
||||
|
@ -49,7 +49,6 @@ tstoreStartupReceiver(DestReceiver *self, int operation, TupleDesc typeinfo)
|
||||
{
|
||||
TStoreState *myState = (TStoreState *) self;
|
||||
bool needtoast = false;
|
||||
Form_pg_attribute *attrs = typeinfo->attrs;
|
||||
int natts = typeinfo->natts;
|
||||
int i;
|
||||
|
||||
@ -58,9 +57,11 @@ tstoreStartupReceiver(DestReceiver *self, int operation, TupleDesc typeinfo)
|
||||
{
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
if (attrs[i]->attisdropped)
|
||||
Form_pg_attribute attr = TupleDescAttr(typeinfo, i);
|
||||
|
||||
if (attr->attisdropped)
|
||||
continue;
|
||||
if (attrs[i]->attlen == -1)
|
||||
if (attr->attlen == -1)
|
||||
{
|
||||
needtoast = true;
|
||||
break;
|
||||
@ -109,7 +110,6 @@ tstoreReceiveSlot_detoast(TupleTableSlot *slot, DestReceiver *self)
|
||||
{
|
||||
TStoreState *myState = (TStoreState *) self;
|
||||
TupleDesc typeinfo = slot->tts_tupleDescriptor;
|
||||
Form_pg_attribute *attrs = typeinfo->attrs;
|
||||
int natts = typeinfo->natts;
|
||||
int nfree;
|
||||
int i;
|
||||
@ -127,10 +127,9 @@ tstoreReceiveSlot_detoast(TupleTableSlot *slot, DestReceiver *self)
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
Datum val = slot->tts_values[i];
|
||||
Form_pg_attribute attr = TupleDescAttr(typeinfo, i);
|
||||
|
||||
if (!attrs[i]->attisdropped &&
|
||||
attrs[i]->attlen == -1 &&
|
||||
!slot->tts_isnull[i])
|
||||
if (!attr->attisdropped && attr->attlen == -1 && !slot->tts_isnull[i])
|
||||
{
|
||||
if (VARATT_IS_EXTERNAL(DatumGetPointer(val)))
|
||||
{
|
||||
|
@ -248,7 +248,7 @@ expand_targetlist(List *tlist, int command_type,
|
||||
|
||||
for (attrno = 1; attrno <= numattrs; attrno++)
|
||||
{
|
||||
Form_pg_attribute att_tup = rel->rd_att->attrs[attrno - 1];
|
||||
Form_pg_attribute att_tup = TupleDescAttr(rel->rd_att, attrno - 1);
|
||||
TargetEntry *new_tle = NULL;
|
||||
|
||||
if (tlist_item != NULL)
|
||||
|
@ -1648,7 +1648,7 @@ make_inh_translation_list(Relation oldrelation, Relation newrelation,
|
||||
Oid attcollation;
|
||||
int new_attno;
|
||||
|
||||
att = old_tupdesc->attrs[old_attno];
|
||||
att = TupleDescAttr(old_tupdesc, old_attno);
|
||||
if (att->attisdropped)
|
||||
{
|
||||
/* Just put NULL into this list entry */
|
||||
@ -1686,7 +1686,7 @@ make_inh_translation_list(Relation oldrelation, Relation newrelation,
|
||||
* notational device to include the assignment into the if-clause.
|
||||
*/
|
||||
if (old_attno < newnatts &&
|
||||
(att = new_tupdesc->attrs[old_attno]) != NULL &&
|
||||
(att = TupleDescAttr(new_tupdesc, old_attno)) != NULL &&
|
||||
!att->attisdropped && att->attinhcount != 0 &&
|
||||
strcmp(attname, NameStr(att->attname)) == 0)
|
||||
new_attno = old_attno;
|
||||
@ -1694,7 +1694,7 @@ make_inh_translation_list(Relation oldrelation, Relation newrelation,
|
||||
{
|
||||
for (new_attno = 0; new_attno < newnatts; new_attno++)
|
||||
{
|
||||
att = new_tupdesc->attrs[new_attno];
|
||||
att = TupleDescAttr(new_tupdesc, new_attno);
|
||||
if (!att->attisdropped && att->attinhcount != 0 &&
|
||||
strcmp(attname, NameStr(att->attname)) == 0)
|
||||
break;
|
||||
|
@ -2366,7 +2366,7 @@ rowtype_field_matches(Oid rowtypeid, int fieldnum,
|
||||
ReleaseTupleDesc(tupdesc);
|
||||
return false;
|
||||
}
|
||||
attr = tupdesc->attrs[fieldnum - 1];
|
||||
attr = TupleDescAttr(tupdesc, fieldnum - 1);
|
||||
if (attr->attisdropped ||
|
||||
attr->atttypid != expectedtype ||
|
||||
attr->atttypmod != expectedtypmod ||
|
||||
|
@ -1072,7 +1072,7 @@ get_rel_data_width(Relation rel, int32 *attr_widths)
|
||||
|
||||
for (i = 1; i <= RelationGetNumberOfAttributes(rel); i++)
|
||||
{
|
||||
Form_pg_attribute att = rel->rd_att->attrs[i - 1];
|
||||
Form_pg_attribute att = TupleDescAttr(rel->rd_att, i - 1);
|
||||
int32 item_width;
|
||||
|
||||
if (att->attisdropped)
|
||||
@ -1208,7 +1208,7 @@ get_relation_constraints(PlannerInfo *root,
|
||||
|
||||
for (i = 1; i <= natts; i++)
|
||||
{
|
||||
Form_pg_attribute att = relation->rd_att->attrs[i - 1];
|
||||
Form_pg_attribute att = TupleDescAttr(relation->rd_att, i - 1);
|
||||
|
||||
if (att->attnotnull && !att->attisdropped)
|
||||
{
|
||||
@ -1489,7 +1489,8 @@ build_physical_tlist(PlannerInfo *root, RelOptInfo *rel)
|
||||
numattrs = RelationGetNumberOfAttributes(relation);
|
||||
for (attrno = 1; attrno <= numattrs; attrno++)
|
||||
{
|
||||
Form_pg_attribute att_tup = relation->rd_att->attrs[attrno - 1];
|
||||
Form_pg_attribute att_tup = TupleDescAttr(relation->rd_att,
|
||||
attrno - 1);
|
||||
|
||||
if (att_tup->attisdropped)
|
||||
{
|
||||
@ -1609,7 +1610,7 @@ build_index_tlist(PlannerInfo *root, IndexOptInfo *index,
|
||||
att_tup = SystemAttributeDefinition(indexkey,
|
||||
heapRelation->rd_rel->relhasoids);
|
||||
else
|
||||
att_tup = heapRelation->rd_att->attrs[indexkey - 1];
|
||||
att_tup = TupleDescAttr(heapRelation->rd_att, indexkey - 1);
|
||||
|
||||
indexvar = (Expr *) makeVar(varno,
|
||||
indexkey,
|
||||
|
@ -1050,7 +1050,7 @@ transformOnConflictClause(ParseState *pstate,
|
||||
*/
|
||||
for (attno = 0; attno < targetrel->rd_rel->relnatts; attno++)
|
||||
{
|
||||
Form_pg_attribute attr = targetrel->rd_att->attrs[attno];
|
||||
Form_pg_attribute attr = TupleDescAttr(targetrel->rd_att, attno);
|
||||
char *name;
|
||||
|
||||
if (attr->attisdropped)
|
||||
|
@ -982,9 +982,10 @@ coerce_record_to_complex(ParseState *pstate, Node *node,
|
||||
Node *expr;
|
||||
Node *cexpr;
|
||||
Oid exprtype;
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, i);
|
||||
|
||||
/* Fill in NULLs for dropped columns in rowtype */
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
if (attr->attisdropped)
|
||||
{
|
||||
/*
|
||||
* can't use atttypid here, but it doesn't really matter what type
|
||||
@ -1008,8 +1009,8 @@ coerce_record_to_complex(ParseState *pstate, Node *node,
|
||||
|
||||
cexpr = coerce_to_target_type(pstate,
|
||||
expr, exprtype,
|
||||
tupdesc->attrs[i]->atttypid,
|
||||
tupdesc->attrs[i]->atttypmod,
|
||||
attr->atttypid,
|
||||
attr->atttypmod,
|
||||
ccontext,
|
||||
COERCE_IMPLICIT_CAST,
|
||||
-1);
|
||||
@ -1021,7 +1022,7 @@ coerce_record_to_complex(ParseState *pstate, Node *node,
|
||||
format_type_be(targetTypeId)),
|
||||
errdetail("Cannot cast type %s to %s in column %d.",
|
||||
format_type_be(exprtype),
|
||||
format_type_be(tupdesc->attrs[i]->atttypid),
|
||||
format_type_be(attr->atttypid),
|
||||
ucolno),
|
||||
parser_coercion_errposition(pstate, location, expr)));
|
||||
newargs = lappend(newargs, cexpr);
|
||||
|
@ -1834,7 +1834,7 @@ ParseComplexProjection(ParseState *pstate, char *funcname, Node *first_arg,
|
||||
|
||||
for (i = 0; i < tupdesc->natts; i++)
|
||||
{
|
||||
Form_pg_attribute att = tupdesc->attrs[i];
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
|
||||
if (strcmp(funcname, NameStr(att->attname)) == 0 &&
|
||||
!att->attisdropped)
|
||||
|
@ -1052,7 +1052,7 @@ buildRelationAliases(TupleDesc tupdesc, Alias *alias, Alias *eref)
|
||||
|
||||
for (varattno = 0; varattno < maxattrs; varattno++)
|
||||
{
|
||||
Form_pg_attribute attr = tupdesc->attrs[varattno];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, varattno);
|
||||
Value *attrname;
|
||||
|
||||
if (attr->attisdropped)
|
||||
@ -2026,19 +2026,18 @@ addRangeTableEntryForENR(ParseState *pstate,
|
||||
rte->colcollations = NIL;
|
||||
for (attno = 1; attno <= tupdesc->natts; ++attno)
|
||||
{
|
||||
if (tupdesc->attrs[attno - 1]->atttypid == InvalidOid &&
|
||||
!(tupdesc->attrs[attno - 1]->attisdropped))
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, attno - 1);
|
||||
|
||||
if (att->atttypid == InvalidOid &&
|
||||
!(att->attisdropped))
|
||||
elog(ERROR, "atttypid was invalid for column which has not been dropped from \"%s\"",
|
||||
rv->relname);
|
||||
rte->coltypes =
|
||||
lappend_oid(rte->coltypes,
|
||||
tupdesc->attrs[attno - 1]->atttypid);
|
||||
lappend_oid(rte->coltypes, att->atttypid);
|
||||
rte->coltypmods =
|
||||
lappend_int(rte->coltypmods,
|
||||
tupdesc->attrs[attno - 1]->atttypmod);
|
||||
lappend_int(rte->coltypmods, att->atttypmod);
|
||||
rte->colcollations =
|
||||
lappend_oid(rte->colcollations,
|
||||
tupdesc->attrs[attno - 1]->attcollation);
|
||||
lappend_oid(rte->colcollations, att->attcollation);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -2514,7 +2513,7 @@ expandTupleDesc(TupleDesc tupdesc, Alias *eref, int count, int offset,
|
||||
Assert(count <= tupdesc->natts);
|
||||
for (varattno = 0; varattno < count; varattno++)
|
||||
{
|
||||
Form_pg_attribute attr = tupdesc->attrs[varattno];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, varattno);
|
||||
|
||||
if (attr->attisdropped)
|
||||
{
|
||||
@ -2749,7 +2748,7 @@ get_rte_attribute_type(RangeTblEntry *rte, AttrNumber attnum,
|
||||
|
||||
Assert(tupdesc);
|
||||
Assert(attnum <= tupdesc->natts);
|
||||
att_tup = tupdesc->attrs[attnum - 1];
|
||||
att_tup = TupleDescAttr(tupdesc, attnum - 1);
|
||||
|
||||
/*
|
||||
* If dropped column, pretend it ain't there. See
|
||||
@ -2953,7 +2952,8 @@ get_rte_attribute_is_dropped(RangeTblEntry *rte, AttrNumber attnum)
|
||||
|
||||
Assert(tupdesc);
|
||||
Assert(attnum - atts_done <= tupdesc->natts);
|
||||
att_tup = tupdesc->attrs[attnum - atts_done - 1];
|
||||
att_tup = TupleDescAttr(tupdesc,
|
||||
attnum - atts_done - 1);
|
||||
return att_tup->attisdropped;
|
||||
}
|
||||
/* Otherwise, it can't have any dropped columns */
|
||||
@ -3042,7 +3042,7 @@ attnameAttNum(Relation rd, const char *attname, bool sysColOK)
|
||||
|
||||
for (i = 0; i < rd->rd_rel->relnatts; i++)
|
||||
{
|
||||
Form_pg_attribute att = rd->rd_att->attrs[i];
|
||||
Form_pg_attribute att = TupleDescAttr(rd->rd_att, i);
|
||||
|
||||
if (namestrcmp(&(att->attname), attname) == 0 && !att->attisdropped)
|
||||
return i + 1;
|
||||
@ -3102,7 +3102,7 @@ attnumAttName(Relation rd, int attid)
|
||||
}
|
||||
if (attid > rd->rd_att->natts)
|
||||
elog(ERROR, "invalid attribute number %d", attid);
|
||||
return &rd->rd_att->attrs[attid - 1]->attname;
|
||||
return &TupleDescAttr(rd->rd_att, attid - 1)->attname;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -3124,7 +3124,7 @@ attnumTypeId(Relation rd, int attid)
|
||||
}
|
||||
if (attid > rd->rd_att->natts)
|
||||
elog(ERROR, "invalid attribute number %d", attid);
|
||||
return rd->rd_att->attrs[attid - 1]->atttypid;
|
||||
return TupleDescAttr(rd->rd_att, attid - 1)->atttypid;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -3142,7 +3142,7 @@ attnumCollationId(Relation rd, int attid)
|
||||
}
|
||||
if (attid > rd->rd_att->natts)
|
||||
elog(ERROR, "invalid attribute number %d", attid);
|
||||
return rd->rd_att->attrs[attid - 1]->attcollation;
|
||||
return TupleDescAttr(rd->rd_att, attid - 1)->attcollation;
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -484,8 +484,8 @@ transformAssignedExpr(ParseState *pstate,
|
||||
colname),
|
||||
parser_errposition(pstate, location)));
|
||||
attrtype = attnumTypeId(rd, attrno);
|
||||
attrtypmod = rd->rd_att->attrs[attrno - 1]->atttypmod;
|
||||
attrcollation = rd->rd_att->attrs[attrno - 1]->attcollation;
|
||||
attrtypmod = TupleDescAttr(rd->rd_att, attrno - 1)->atttypmod;
|
||||
attrcollation = TupleDescAttr(rd->rd_att, attrno - 1)->attcollation;
|
||||
|
||||
/*
|
||||
* If the expression is a DEFAULT placeholder, insert the attribute's
|
||||
@ -959,19 +959,21 @@ checkInsertTargets(ParseState *pstate, List *cols, List **attrnos)
|
||||
/*
|
||||
* Generate default column list for INSERT.
|
||||
*/
|
||||
Form_pg_attribute *attr = pstate->p_target_relation->rd_att->attrs;
|
||||
int numcol = pstate->p_target_relation->rd_rel->relnatts;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < numcol; i++)
|
||||
{
|
||||
ResTarget *col;
|
||||
Form_pg_attribute attr;
|
||||
|
||||
if (attr[i]->attisdropped)
|
||||
attr = TupleDescAttr(pstate->p_target_relation->rd_att, i);
|
||||
|
||||
if (attr->attisdropped)
|
||||
continue;
|
||||
|
||||
col = makeNode(ResTarget);
|
||||
col->name = pstrdup(NameStr(attr[i]->attname));
|
||||
col->name = pstrdup(NameStr(attr->attname));
|
||||
col->indirection = NIL;
|
||||
col->val = NULL;
|
||||
col->location = -1;
|
||||
@ -1407,7 +1409,7 @@ ExpandRowReference(ParseState *pstate, Node *expr,
|
||||
numAttrs = tupleDesc->natts;
|
||||
for (i = 0; i < numAttrs; i++)
|
||||
{
|
||||
Form_pg_attribute att = tupleDesc->attrs[i];
|
||||
Form_pg_attribute att = TupleDescAttr(tupleDesc, i);
|
||||
FieldSelect *fselect;
|
||||
|
||||
if (att->attisdropped)
|
||||
|
@ -969,7 +969,8 @@ transformTableLikeClause(CreateStmtContext *cxt, TableLikeClause *table_like_cla
|
||||
for (parent_attno = 1; parent_attno <= tupleDesc->natts;
|
||||
parent_attno++)
|
||||
{
|
||||
Form_pg_attribute attribute = tupleDesc->attrs[parent_attno - 1];
|
||||
Form_pg_attribute attribute = TupleDescAttr(tupleDesc,
|
||||
parent_attno - 1);
|
||||
char *attributeName = NameStr(attribute->attname);
|
||||
ColumnDef *def;
|
||||
|
||||
@ -1219,7 +1220,7 @@ transformOfType(CreateStmtContext *cxt, TypeName *ofTypename)
|
||||
tupdesc = lookup_rowtype_tupdesc(ofTypeId, -1);
|
||||
for (i = 0; i < tupdesc->natts; i++)
|
||||
{
|
||||
Form_pg_attribute attr = tupdesc->attrs[i];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, i);
|
||||
ColumnDef *n;
|
||||
|
||||
if (attr->attisdropped)
|
||||
@ -1256,7 +1257,6 @@ generateClonedIndexStmt(CreateStmtContext *cxt, Relation source_idx,
|
||||
const AttrNumber *attmap, int attmap_length)
|
||||
{
|
||||
Oid source_relid = RelationGetRelid(source_idx);
|
||||
Form_pg_attribute *attrs = RelationGetDescr(source_idx)->attrs;
|
||||
HeapTuple ht_idxrel;
|
||||
HeapTuple ht_idx;
|
||||
HeapTuple ht_am;
|
||||
@ -1434,6 +1434,8 @@ generateClonedIndexStmt(CreateStmtContext *cxt, Relation source_idx,
|
||||
{
|
||||
IndexElem *iparam;
|
||||
AttrNumber attnum = idxrec->indkey.values[keyno];
|
||||
Form_pg_attribute attr = TupleDescAttr(RelationGetDescr(source_idx),
|
||||
keyno);
|
||||
int16 opt = source_idx->rd_indoption[keyno];
|
||||
|
||||
iparam = makeNode(IndexElem);
|
||||
@ -1481,7 +1483,7 @@ generateClonedIndexStmt(CreateStmtContext *cxt, Relation source_idx,
|
||||
}
|
||||
|
||||
/* Copy the original index column name */
|
||||
iparam->indexcolname = pstrdup(NameStr(attrs[keyno]->attname));
|
||||
iparam->indexcolname = pstrdup(NameStr(attr->attname));
|
||||
|
||||
/* Add the collation name, if non-default */
|
||||
iparam->collation = get_collation(indcollation->values[keyno], keycoltype);
|
||||
@ -1921,7 +1923,7 @@ transformIndexConstraint(Constraint *constraint, CreateStmtContext *cxt)
|
||||
if (attnum > 0)
|
||||
{
|
||||
Assert(attnum <= heap_rel->rd_att->natts);
|
||||
attform = heap_rel->rd_att->attrs[attnum - 1];
|
||||
attform = TupleDescAttr(heap_rel->rd_att, attnum - 1);
|
||||
}
|
||||
else
|
||||
attform = SystemAttributeDefinition(attnum,
|
||||
@ -2040,7 +2042,8 @@ transformIndexConstraint(Constraint *constraint, CreateStmtContext *cxt)
|
||||
inh->relname)));
|
||||
for (count = 0; count < rel->rd_att->natts; count++)
|
||||
{
|
||||
Form_pg_attribute inhattr = rel->rd_att->attrs[count];
|
||||
Form_pg_attribute inhattr = TupleDescAttr(rel->rd_att,
|
||||
count);
|
||||
char *inhname = NameStr(inhattr->attname);
|
||||
|
||||
if (inhattr->attisdropped)
|
||||
|
@ -398,7 +398,7 @@ logicalrep_write_tuple(StringInfo out, Relation rel, HeapTuple tuple)
|
||||
|
||||
for (i = 0; i < desc->natts; i++)
|
||||
{
|
||||
if (desc->attrs[i]->attisdropped)
|
||||
if (TupleDescAttr(desc, i)->attisdropped)
|
||||
continue;
|
||||
nliveatts++;
|
||||
}
|
||||
@ -415,7 +415,7 @@ logicalrep_write_tuple(StringInfo out, Relation rel, HeapTuple tuple)
|
||||
{
|
||||
HeapTuple typtup;
|
||||
Form_pg_type typclass;
|
||||
Form_pg_attribute att = desc->attrs[i];
|
||||
Form_pg_attribute att = TupleDescAttr(desc, i);
|
||||
char *outputstr;
|
||||
|
||||
/* skip dropped columns */
|
||||
@ -518,7 +518,7 @@ logicalrep_write_attrs(StringInfo out, Relation rel)
|
||||
/* send number of live attributes */
|
||||
for (i = 0; i < desc->natts; i++)
|
||||
{
|
||||
if (desc->attrs[i]->attisdropped)
|
||||
if (TupleDescAttr(desc, i)->attisdropped)
|
||||
continue;
|
||||
nliveatts++;
|
||||
}
|
||||
@ -533,7 +533,7 @@ logicalrep_write_attrs(StringInfo out, Relation rel)
|
||||
/* send the attributes */
|
||||
for (i = 0; i < desc->natts; i++)
|
||||
{
|
||||
Form_pg_attribute att = desc->attrs[i];
|
||||
Form_pg_attribute att = TupleDescAttr(desc, i);
|
||||
uint8 flags = 0;
|
||||
|
||||
if (att->attisdropped)
|
||||
|
@ -278,15 +278,16 @@ logicalrep_rel_open(LogicalRepRelId remoteid, LOCKMODE lockmode)
|
||||
for (i = 0; i < desc->natts; i++)
|
||||
{
|
||||
int attnum;
|
||||
Form_pg_attribute attr = TupleDescAttr(desc, i);
|
||||
|
||||
if (desc->attrs[i]->attisdropped)
|
||||
if (attr->attisdropped)
|
||||
{
|
||||
entry->attrmap[i] = -1;
|
||||
continue;
|
||||
}
|
||||
|
||||
attnum = logicalrep_rel_att_by_name(remoterel,
|
||||
NameStr(desc->attrs[i]->attname));
|
||||
NameStr(attr->attname));
|
||||
|
||||
entry->attrmap[i] = attnum;
|
||||
if (attnum >= 0)
|
||||
|
@ -2800,7 +2800,7 @@ ReorderBufferToastReplace(ReorderBuffer *rb, ReorderBufferTXN *txn,
|
||||
|
||||
for (natt = 0; natt < desc->natts; natt++)
|
||||
{
|
||||
Form_pg_attribute attr = desc->attrs[natt];
|
||||
Form_pg_attribute attr = TupleDescAttr(desc, natt);
|
||||
ReorderBufferToastEnt *ent;
|
||||
struct varlena *varlena;
|
||||
|
||||
|
@ -247,7 +247,7 @@ slot_fill_defaults(LogicalRepRelMapEntry *rel, EState *estate,
|
||||
{
|
||||
Expr *defexpr;
|
||||
|
||||
if (desc->attrs[attnum]->attisdropped)
|
||||
if (TupleDescAttr(desc, attnum)->attisdropped)
|
||||
continue;
|
||||
|
||||
if (rel->attrmap[attnum] >= 0)
|
||||
@ -323,7 +323,7 @@ slot_store_cstrings(TupleTableSlot *slot, LogicalRepRelMapEntry *rel,
|
||||
/* Call the "in" function for each non-dropped attribute */
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
Form_pg_attribute att = slot->tts_tupleDescriptor->attrs[i];
|
||||
Form_pg_attribute att = TupleDescAttr(slot->tts_tupleDescriptor, i);
|
||||
int remoteattnum = rel->attrmap[i];
|
||||
|
||||
if (!att->attisdropped && remoteattnum >= 0 &&
|
||||
@ -388,7 +388,7 @@ slot_modify_cstrings(TupleTableSlot *slot, LogicalRepRelMapEntry *rel,
|
||||
/* Call the "in" function for each replaced attribute */
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
Form_pg_attribute att = slot->tts_tupleDescriptor->attrs[i];
|
||||
Form_pg_attribute att = TupleDescAttr(slot->tts_tupleDescriptor, i);
|
||||
int remoteattnum = rel->attrmap[i];
|
||||
|
||||
if (remoteattnum >= 0 && !replaces[remoteattnum])
|
||||
|
@ -303,7 +303,7 @@ pgoutput_change(LogicalDecodingContext *ctx, ReorderBufferTXN *txn,
|
||||
*/
|
||||
for (i = 0; i < desc->natts; i++)
|
||||
{
|
||||
Form_pg_attribute att = desc->attrs[i];
|
||||
Form_pg_attribute att = TupleDescAttr(desc, i);
|
||||
|
||||
if (att->attisdropped)
|
||||
continue;
|
||||
|
@ -676,7 +676,7 @@ checkRuleResultList(List *targetList, TupleDesc resultDesc, bool isSelect,
|
||||
errmsg("SELECT rule's target list has too many entries") :
|
||||
errmsg("RETURNING list has too many entries")));
|
||||
|
||||
attr = resultDesc->attrs[i - 1];
|
||||
attr = TupleDescAttr(resultDesc, i - 1);
|
||||
attname = NameStr(attr->attname);
|
||||
|
||||
/*
|
||||
|
@ -751,7 +751,7 @@ rewriteTargetListIU(List *targetList,
|
||||
attrno = old_tle->resno;
|
||||
if (attrno < 1 || attrno > numattrs)
|
||||
elog(ERROR, "bogus resno %d in targetlist", attrno);
|
||||
att_tup = target_relation->rd_att->attrs[attrno - 1];
|
||||
att_tup = TupleDescAttr(target_relation->rd_att, attrno - 1);
|
||||
|
||||
/* put attrno into attrno_list even if it's dropped */
|
||||
if (attrno_list)
|
||||
@ -794,7 +794,7 @@ rewriteTargetListIU(List *targetList,
|
||||
TargetEntry *new_tle = new_tles[attrno - 1];
|
||||
bool apply_default;
|
||||
|
||||
att_tup = target_relation->rd_att->attrs[attrno - 1];
|
||||
att_tup = TupleDescAttr(target_relation->rd_att, attrno - 1);
|
||||
|
||||
/* We can (and must) ignore deleted attributes */
|
||||
if (att_tup->attisdropped)
|
||||
@ -1112,7 +1112,7 @@ Node *
|
||||
build_column_default(Relation rel, int attrno)
|
||||
{
|
||||
TupleDesc rd_att = rel->rd_att;
|
||||
Form_pg_attribute att_tup = rd_att->attrs[attrno - 1];
|
||||
Form_pg_attribute att_tup = TupleDescAttr(rd_att, attrno - 1);
|
||||
Oid atttype = att_tup->atttypid;
|
||||
int32 atttypmod = att_tup->atttypmod;
|
||||
Node *expr = NULL;
|
||||
@ -1247,7 +1247,7 @@ rewriteValuesRTE(RangeTblEntry *rte, Relation target_relation, List *attrnos)
|
||||
Form_pg_attribute att_tup;
|
||||
Node *new_expr;
|
||||
|
||||
att_tup = target_relation->rd_att->attrs[attrno - 1];
|
||||
att_tup = TupleDescAttr(target_relation->rd_att, attrno - 1);
|
||||
|
||||
if (!att_tup->attisdropped)
|
||||
new_expr = build_column_default(target_relation, attrno);
|
||||
|
@ -1714,15 +1714,16 @@ composite_to_json(Datum composite, StringInfo result, bool use_line_feeds)
|
||||
char *attname;
|
||||
JsonTypeCategory tcategory;
|
||||
Oid outfuncoid;
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
if (att->attisdropped)
|
||||
continue;
|
||||
|
||||
if (needsep)
|
||||
appendStringInfoString(result, sep);
|
||||
needsep = true;
|
||||
|
||||
attname = NameStr(tupdesc->attrs[i]->attname);
|
||||
attname = NameStr(att->attname);
|
||||
escape_json(result, attname);
|
||||
appendStringInfoChar(result, ':');
|
||||
|
||||
@ -1734,8 +1735,7 @@ composite_to_json(Datum composite, StringInfo result, bool use_line_feeds)
|
||||
outfuncoid = InvalidOid;
|
||||
}
|
||||
else
|
||||
json_categorize_type(tupdesc->attrs[i]->atttypid,
|
||||
&tcategory, &outfuncoid);
|
||||
json_categorize_type(att->atttypid, &tcategory, &outfuncoid);
|
||||
|
||||
datum_to_json(val, isnull, result, tcategory, outfuncoid, false);
|
||||
}
|
||||
|
@ -1075,11 +1075,12 @@ composite_to_jsonb(Datum composite, JsonbInState *result)
|
||||
JsonbTypeCategory tcategory;
|
||||
Oid outfuncoid;
|
||||
JsonbValue v;
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
if (att->attisdropped)
|
||||
continue;
|
||||
|
||||
attname = NameStr(tupdesc->attrs[i]->attname);
|
||||
attname = NameStr(att->attname);
|
||||
|
||||
v.type = jbvString;
|
||||
/* don't need checkStringLen here - can't exceed maximum name length */
|
||||
@ -1096,8 +1097,7 @@ composite_to_jsonb(Datum composite, JsonbInState *result)
|
||||
outfuncoid = InvalidOid;
|
||||
}
|
||||
else
|
||||
jsonb_categorize_type(tupdesc->attrs[i]->atttypid,
|
||||
&tcategory, &outfuncoid);
|
||||
jsonb_categorize_type(att->atttypid, &tcategory, &outfuncoid);
|
||||
|
||||
datum_to_jsonb(val, isnull, result, tcategory, outfuncoid, false);
|
||||
}
|
||||
|
@ -3087,7 +3087,7 @@ populate_record(TupleDesc tupdesc,
|
||||
|
||||
for (i = 0; i < ncolumns; ++i)
|
||||
{
|
||||
Form_pg_attribute att = tupdesc->attrs[i];
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
char *colname = NameStr(att->attname);
|
||||
JsValue field = {0};
|
||||
bool found;
|
||||
|
@ -1125,13 +1125,15 @@ hypothetical_check_argtypes(FunctionCallInfo fcinfo, int nargs,
|
||||
/* check that we have an int4 flag column */
|
||||
if (!tupdesc ||
|
||||
(nargs + 1) != tupdesc->natts ||
|
||||
tupdesc->attrs[nargs]->atttypid != INT4OID)
|
||||
TupleDescAttr(tupdesc, nargs)->atttypid != INT4OID)
|
||||
elog(ERROR, "type mismatch in hypothetical-set function");
|
||||
|
||||
/* check that direct args match in type with aggregated args */
|
||||
for (i = 0; i < nargs; i++)
|
||||
{
|
||||
if (get_fn_expr_argtype(fcinfo->flinfo, i + 1) != tupdesc->attrs[i]->atttypid)
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, i);
|
||||
|
||||
if (get_fn_expr_argtype(fcinfo->flinfo, i + 1) != attr->atttypid)
|
||||
elog(ERROR, "type mismatch in hypothetical-set function");
|
||||
}
|
||||
}
|
||||
|
@ -159,12 +159,13 @@ record_in(PG_FUNCTION_ARGS)
|
||||
|
||||
for (i = 0; i < ncolumns; i++)
|
||||
{
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
ColumnIOData *column_info = &my_extra->columns[i];
|
||||
Oid column_type = tupdesc->attrs[i]->atttypid;
|
||||
Oid column_type = att->atttypid;
|
||||
char *column_data;
|
||||
|
||||
/* Ignore dropped columns in datatype, but fill with nulls */
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
if (att->attisdropped)
|
||||
{
|
||||
values[i] = (Datum) 0;
|
||||
nulls[i] = true;
|
||||
@ -252,7 +253,7 @@ record_in(PG_FUNCTION_ARGS)
|
||||
values[i] = InputFunctionCall(&column_info->proc,
|
||||
column_data,
|
||||
column_info->typioparam,
|
||||
tupdesc->attrs[i]->atttypmod);
|
||||
att->atttypmod);
|
||||
|
||||
/*
|
||||
* Prep for next column
|
||||
@ -367,15 +368,16 @@ record_out(PG_FUNCTION_ARGS)
|
||||
|
||||
for (i = 0; i < ncolumns; i++)
|
||||
{
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
ColumnIOData *column_info = &my_extra->columns[i];
|
||||
Oid column_type = tupdesc->attrs[i]->atttypid;
|
||||
Oid column_type = att->atttypid;
|
||||
Datum attr;
|
||||
char *value;
|
||||
char *tmp;
|
||||
bool nq;
|
||||
|
||||
/* Ignore dropped columns in datatype */
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
if (att->attisdropped)
|
||||
continue;
|
||||
|
||||
if (needComma)
|
||||
@ -519,7 +521,7 @@ record_recv(PG_FUNCTION_ARGS)
|
||||
validcols = 0;
|
||||
for (i = 0; i < ncolumns; i++)
|
||||
{
|
||||
if (!tupdesc->attrs[i]->attisdropped)
|
||||
if (!TupleDescAttr(tupdesc, i)->attisdropped)
|
||||
validcols++;
|
||||
}
|
||||
if (usercols != validcols)
|
||||
@ -531,8 +533,9 @@ record_recv(PG_FUNCTION_ARGS)
|
||||
/* Process each column */
|
||||
for (i = 0; i < ncolumns; i++)
|
||||
{
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
ColumnIOData *column_info = &my_extra->columns[i];
|
||||
Oid column_type = tupdesc->attrs[i]->atttypid;
|
||||
Oid column_type = att->atttypid;
|
||||
Oid coltypoid;
|
||||
int itemlen;
|
||||
StringInfoData item_buf;
|
||||
@ -540,7 +543,7 @@ record_recv(PG_FUNCTION_ARGS)
|
||||
char csave;
|
||||
|
||||
/* Ignore dropped columns in datatype, but fill with nulls */
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
if (att->attisdropped)
|
||||
{
|
||||
values[i] = (Datum) 0;
|
||||
nulls[i] = true;
|
||||
@ -605,7 +608,7 @@ record_recv(PG_FUNCTION_ARGS)
|
||||
values[i] = ReceiveFunctionCall(&column_info->proc,
|
||||
bufptr,
|
||||
column_info->typioparam,
|
||||
tupdesc->attrs[i]->atttypmod);
|
||||
att->atttypmod);
|
||||
|
||||
if (bufptr)
|
||||
{
|
||||
@ -712,20 +715,21 @@ record_send(PG_FUNCTION_ARGS)
|
||||
validcols = 0;
|
||||
for (i = 0; i < ncolumns; i++)
|
||||
{
|
||||
if (!tupdesc->attrs[i]->attisdropped)
|
||||
if (!TupleDescAttr(tupdesc, i)->attisdropped)
|
||||
validcols++;
|
||||
}
|
||||
pq_sendint(&buf, validcols, 4);
|
||||
|
||||
for (i = 0; i < ncolumns; i++)
|
||||
{
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
ColumnIOData *column_info = &my_extra->columns[i];
|
||||
Oid column_type = tupdesc->attrs[i]->atttypid;
|
||||
Oid column_type = att->atttypid;
|
||||
Datum attr;
|
||||
bytea *outputbytes;
|
||||
|
||||
/* Ignore dropped columns in datatype */
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
if (att->attisdropped)
|
||||
continue;
|
||||
|
||||
pq_sendint(&buf, column_type, sizeof(Oid));
|
||||
@ -873,18 +877,20 @@ record_cmp(FunctionCallInfo fcinfo)
|
||||
i1 = i2 = j = 0;
|
||||
while (i1 < ncolumns1 || i2 < ncolumns2)
|
||||
{
|
||||
Form_pg_attribute att1;
|
||||
Form_pg_attribute att2;
|
||||
TypeCacheEntry *typentry;
|
||||
Oid collation;
|
||||
|
||||
/*
|
||||
* Skip dropped columns
|
||||
*/
|
||||
if (i1 < ncolumns1 && tupdesc1->attrs[i1]->attisdropped)
|
||||
if (i1 < ncolumns1 && TupleDescAttr(tupdesc1, i1)->attisdropped)
|
||||
{
|
||||
i1++;
|
||||
continue;
|
||||
}
|
||||
if (i2 < ncolumns2 && tupdesc2->attrs[i2]->attisdropped)
|
||||
if (i2 < ncolumns2 && TupleDescAttr(tupdesc2, i2)->attisdropped)
|
||||
{
|
||||
i2++;
|
||||
continue;
|
||||
@ -892,24 +898,26 @@ record_cmp(FunctionCallInfo fcinfo)
|
||||
if (i1 >= ncolumns1 || i2 >= ncolumns2)
|
||||
break; /* we'll deal with mismatch below loop */
|
||||
|
||||
att1 = TupleDescAttr(tupdesc1, i1);
|
||||
att2 = TupleDescAttr(tupdesc2, i2);
|
||||
|
||||
/*
|
||||
* Have two matching columns, they must be same type
|
||||
*/
|
||||
if (tupdesc1->attrs[i1]->atttypid !=
|
||||
tupdesc2->attrs[i2]->atttypid)
|
||||
if (att1->atttypid != att2->atttypid)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_DATATYPE_MISMATCH),
|
||||
errmsg("cannot compare dissimilar column types %s and %s at record column %d",
|
||||
format_type_be(tupdesc1->attrs[i1]->atttypid),
|
||||
format_type_be(tupdesc2->attrs[i2]->atttypid),
|
||||
format_type_be(att1->atttypid),
|
||||
format_type_be(att2->atttypid),
|
||||
j + 1)));
|
||||
|
||||
/*
|
||||
* If they're not same collation, we don't complain here, but the
|
||||
* comparison function might.
|
||||
*/
|
||||
collation = tupdesc1->attrs[i1]->attcollation;
|
||||
if (collation != tupdesc2->attrs[i2]->attcollation)
|
||||
collation = att1->attcollation;
|
||||
if (collation != att2->attcollation)
|
||||
collation = InvalidOid;
|
||||
|
||||
/*
|
||||
@ -917,9 +925,9 @@ record_cmp(FunctionCallInfo fcinfo)
|
||||
*/
|
||||
typentry = my_extra->columns[j].typentry;
|
||||
if (typentry == NULL ||
|
||||
typentry->type_id != tupdesc1->attrs[i1]->atttypid)
|
||||
typentry->type_id != att1->atttypid)
|
||||
{
|
||||
typentry = lookup_type_cache(tupdesc1->attrs[i1]->atttypid,
|
||||
typentry = lookup_type_cache(att1->atttypid,
|
||||
TYPECACHE_CMP_PROC_FINFO);
|
||||
if (!OidIsValid(typentry->cmp_proc_finfo.fn_oid))
|
||||
ereport(ERROR,
|
||||
@ -1111,6 +1119,8 @@ record_eq(PG_FUNCTION_ARGS)
|
||||
i1 = i2 = j = 0;
|
||||
while (i1 < ncolumns1 || i2 < ncolumns2)
|
||||
{
|
||||
Form_pg_attribute att1;
|
||||
Form_pg_attribute att2;
|
||||
TypeCacheEntry *typentry;
|
||||
Oid collation;
|
||||
FunctionCallInfoData locfcinfo;
|
||||
@ -1119,12 +1129,12 @@ record_eq(PG_FUNCTION_ARGS)
|
||||
/*
|
||||
* Skip dropped columns
|
||||
*/
|
||||
if (i1 < ncolumns1 && tupdesc1->attrs[i1]->attisdropped)
|
||||
if (i1 < ncolumns1 && TupleDescAttr(tupdesc1, i1)->attisdropped)
|
||||
{
|
||||
i1++;
|
||||
continue;
|
||||
}
|
||||
if (i2 < ncolumns2 && tupdesc2->attrs[i2]->attisdropped)
|
||||
if (i2 < ncolumns2 && TupleDescAttr(tupdesc2, i2)->attisdropped)
|
||||
{
|
||||
i2++;
|
||||
continue;
|
||||
@ -1132,24 +1142,26 @@ record_eq(PG_FUNCTION_ARGS)
|
||||
if (i1 >= ncolumns1 || i2 >= ncolumns2)
|
||||
break; /* we'll deal with mismatch below loop */
|
||||
|
||||
att1 = TupleDescAttr(tupdesc1, i1);
|
||||
att2 = TupleDescAttr(tupdesc2, i2);
|
||||
|
||||
/*
|
||||
* Have two matching columns, they must be same type
|
||||
*/
|
||||
if (tupdesc1->attrs[i1]->atttypid !=
|
||||
tupdesc2->attrs[i2]->atttypid)
|
||||
if (att1->atttypid != att2->atttypid)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_DATATYPE_MISMATCH),
|
||||
errmsg("cannot compare dissimilar column types %s and %s at record column %d",
|
||||
format_type_be(tupdesc1->attrs[i1]->atttypid),
|
||||
format_type_be(tupdesc2->attrs[i2]->atttypid),
|
||||
format_type_be(att1->atttypid),
|
||||
format_type_be(att2->atttypid),
|
||||
j + 1)));
|
||||
|
||||
/*
|
||||
* If they're not same collation, we don't complain here, but the
|
||||
* equality function might.
|
||||
*/
|
||||
collation = tupdesc1->attrs[i1]->attcollation;
|
||||
if (collation != tupdesc2->attrs[i2]->attcollation)
|
||||
collation = att1->attcollation;
|
||||
if (collation != att2->attcollation)
|
||||
collation = InvalidOid;
|
||||
|
||||
/*
|
||||
@ -1157,9 +1169,9 @@ record_eq(PG_FUNCTION_ARGS)
|
||||
*/
|
||||
typentry = my_extra->columns[j].typentry;
|
||||
if (typentry == NULL ||
|
||||
typentry->type_id != tupdesc1->attrs[i1]->atttypid)
|
||||
typentry->type_id != att1->atttypid)
|
||||
{
|
||||
typentry = lookup_type_cache(tupdesc1->attrs[i1]->atttypid,
|
||||
typentry = lookup_type_cache(att1->atttypid,
|
||||
TYPECACHE_EQ_OPR_FINFO);
|
||||
if (!OidIsValid(typentry->eq_opr_finfo.fn_oid))
|
||||
ereport(ERROR,
|
||||
@ -1370,15 +1382,18 @@ record_image_cmp(FunctionCallInfo fcinfo)
|
||||
i1 = i2 = j = 0;
|
||||
while (i1 < ncolumns1 || i2 < ncolumns2)
|
||||
{
|
||||
Form_pg_attribute att1;
|
||||
Form_pg_attribute att2;
|
||||
|
||||
/*
|
||||
* Skip dropped columns
|
||||
*/
|
||||
if (i1 < ncolumns1 && tupdesc1->attrs[i1]->attisdropped)
|
||||
if (i1 < ncolumns1 && TupleDescAttr(tupdesc1, i1)->attisdropped)
|
||||
{
|
||||
i1++;
|
||||
continue;
|
||||
}
|
||||
if (i2 < ncolumns2 && tupdesc2->attrs[i2]->attisdropped)
|
||||
if (i2 < ncolumns2 && TupleDescAttr(tupdesc2, i2)->attisdropped)
|
||||
{
|
||||
i2++;
|
||||
continue;
|
||||
@ -1386,24 +1401,25 @@ record_image_cmp(FunctionCallInfo fcinfo)
|
||||
if (i1 >= ncolumns1 || i2 >= ncolumns2)
|
||||
break; /* we'll deal with mismatch below loop */
|
||||
|
||||
att1 = TupleDescAttr(tupdesc1, i1);
|
||||
att2 = TupleDescAttr(tupdesc2, i2);
|
||||
|
||||
/*
|
||||
* Have two matching columns, they must be same type
|
||||
*/
|
||||
if (tupdesc1->attrs[i1]->atttypid !=
|
||||
tupdesc2->attrs[i2]->atttypid)
|
||||
if (att1->atttypid != att2->atttypid)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_DATATYPE_MISMATCH),
|
||||
errmsg("cannot compare dissimilar column types %s and %s at record column %d",
|
||||
format_type_be(tupdesc1->attrs[i1]->atttypid),
|
||||
format_type_be(tupdesc2->attrs[i2]->atttypid),
|
||||
format_type_be(att1->atttypid),
|
||||
format_type_be(att2->atttypid),
|
||||
j + 1)));
|
||||
|
||||
/*
|
||||
* The same type should have the same length (or both should be
|
||||
* variable).
|
||||
*/
|
||||
Assert(tupdesc1->attrs[i1]->attlen ==
|
||||
tupdesc2->attrs[i2]->attlen);
|
||||
Assert(att1->attlen == att2->attlen);
|
||||
|
||||
/*
|
||||
* We consider two NULLs equal; NULL > not-NULL.
|
||||
@ -1426,7 +1442,7 @@ record_image_cmp(FunctionCallInfo fcinfo)
|
||||
}
|
||||
|
||||
/* Compare the pair of elements */
|
||||
if (tupdesc1->attrs[i1]->attlen == -1)
|
||||
if (att1->attlen == -1)
|
||||
{
|
||||
Size len1,
|
||||
len2;
|
||||
@ -1449,9 +1465,9 @@ record_image_cmp(FunctionCallInfo fcinfo)
|
||||
if ((Pointer) arg2val != (Pointer) values2[i2])
|
||||
pfree(arg2val);
|
||||
}
|
||||
else if (tupdesc1->attrs[i1]->attbyval)
|
||||
else if (att1->attbyval)
|
||||
{
|
||||
switch (tupdesc1->attrs[i1]->attlen)
|
||||
switch (att1->attlen)
|
||||
{
|
||||
case 1:
|
||||
if (GET_1_BYTE(values1[i1]) !=
|
||||
@ -1495,7 +1511,7 @@ record_image_cmp(FunctionCallInfo fcinfo)
|
||||
{
|
||||
cmpresult = memcmp(DatumGetPointer(values1[i1]),
|
||||
DatumGetPointer(values2[i2]),
|
||||
tupdesc1->attrs[i1]->attlen);
|
||||
att1->attlen);
|
||||
}
|
||||
|
||||
if (cmpresult < 0)
|
||||
@ -1647,15 +1663,18 @@ record_image_eq(PG_FUNCTION_ARGS)
|
||||
i1 = i2 = j = 0;
|
||||
while (i1 < ncolumns1 || i2 < ncolumns2)
|
||||
{
|
||||
Form_pg_attribute att1;
|
||||
Form_pg_attribute att2;
|
||||
|
||||
/*
|
||||
* Skip dropped columns
|
||||
*/
|
||||
if (i1 < ncolumns1 && tupdesc1->attrs[i1]->attisdropped)
|
||||
if (i1 < ncolumns1 && TupleDescAttr(tupdesc1, i1)->attisdropped)
|
||||
{
|
||||
i1++;
|
||||
continue;
|
||||
}
|
||||
if (i2 < ncolumns2 && tupdesc2->attrs[i2]->attisdropped)
|
||||
if (i2 < ncolumns2 && TupleDescAttr(tupdesc2, i2)->attisdropped)
|
||||
{
|
||||
i2++;
|
||||
continue;
|
||||
@ -1663,16 +1682,18 @@ record_image_eq(PG_FUNCTION_ARGS)
|
||||
if (i1 >= ncolumns1 || i2 >= ncolumns2)
|
||||
break; /* we'll deal with mismatch below loop */
|
||||
|
||||
att1 = TupleDescAttr(tupdesc1, i1);
|
||||
att2 = TupleDescAttr(tupdesc2, i2);
|
||||
|
||||
/*
|
||||
* Have two matching columns, they must be same type
|
||||
*/
|
||||
if (tupdesc1->attrs[i1]->atttypid !=
|
||||
tupdesc2->attrs[i2]->atttypid)
|
||||
if (att1->atttypid != att2->atttypid)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_DATATYPE_MISMATCH),
|
||||
errmsg("cannot compare dissimilar column types %s and %s at record column %d",
|
||||
format_type_be(tupdesc1->attrs[i1]->atttypid),
|
||||
format_type_be(tupdesc2->attrs[i2]->atttypid),
|
||||
format_type_be(att1->atttypid),
|
||||
format_type_be(att2->atttypid),
|
||||
j + 1)));
|
||||
|
||||
/*
|
||||
@ -1687,7 +1708,7 @@ record_image_eq(PG_FUNCTION_ARGS)
|
||||
}
|
||||
|
||||
/* Compare the pair of elements */
|
||||
if (tupdesc1->attrs[i1]->attlen == -1)
|
||||
if (att1->attlen == -1)
|
||||
{
|
||||
Size len1,
|
||||
len2;
|
||||
@ -1716,9 +1737,9 @@ record_image_eq(PG_FUNCTION_ARGS)
|
||||
pfree(arg2val);
|
||||
}
|
||||
}
|
||||
else if (tupdesc1->attrs[i1]->attbyval)
|
||||
else if (att1->attbyval)
|
||||
{
|
||||
switch (tupdesc1->attrs[i1]->attlen)
|
||||
switch (att1->attlen)
|
||||
{
|
||||
case 1:
|
||||
result = (GET_1_BYTE(values1[i1]) ==
|
||||
@ -1746,7 +1767,7 @@ record_image_eq(PG_FUNCTION_ARGS)
|
||||
{
|
||||
result = (memcmp(DatumGetPointer(values1[i1]),
|
||||
DatumGetPointer(values2[i2]),
|
||||
tupdesc1->attrs[i1]->attlen) == 0);
|
||||
att1->attlen) == 0);
|
||||
}
|
||||
if (!result)
|
||||
break;
|
||||
|
@ -3698,10 +3698,12 @@ set_relation_column_names(deparse_namespace *dpns, RangeTblEntry *rte,
|
||||
|
||||
for (i = 0; i < ncolumns; i++)
|
||||
{
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, i);
|
||||
|
||||
if (attr->attisdropped)
|
||||
real_colnames[i] = NULL;
|
||||
else
|
||||
real_colnames[i] = pstrdup(NameStr(tupdesc->attrs[i]->attname));
|
||||
real_colnames[i] = pstrdup(NameStr(attr->attname));
|
||||
}
|
||||
relation_close(rel, AccessShareLock);
|
||||
}
|
||||
@ -5391,7 +5393,7 @@ get_target_list(List *targetList, deparse_context *context,
|
||||
* Otherwise, just use what we can find in the TLE.
|
||||
*/
|
||||
if (resultDesc && colno <= resultDesc->natts)
|
||||
colname = NameStr(resultDesc->attrs[colno - 1]->attname);
|
||||
colname = NameStr(TupleDescAttr(resultDesc, colno - 1)->attname);
|
||||
else
|
||||
colname = tle->resname;
|
||||
|
||||
@ -6741,7 +6743,7 @@ get_name_for_var_field(Var *var, int fieldno,
|
||||
Assert(tupleDesc);
|
||||
/* Got the tupdesc, so we can extract the field name */
|
||||
Assert(fieldno >= 1 && fieldno <= tupleDesc->natts);
|
||||
return NameStr(tupleDesc->attrs[fieldno - 1]->attname);
|
||||
return NameStr(TupleDescAttr(tupleDesc, fieldno - 1)->attname);
|
||||
}
|
||||
|
||||
/* Find appropriate nesting depth */
|
||||
@ -7051,7 +7053,7 @@ get_name_for_var_field(Var *var, int fieldno,
|
||||
Assert(tupleDesc);
|
||||
/* Got the tupdesc, so we can extract the field name */
|
||||
Assert(fieldno >= 1 && fieldno <= tupleDesc->natts);
|
||||
return NameStr(tupleDesc->attrs[fieldno - 1]->attname);
|
||||
return NameStr(TupleDescAttr(tupleDesc, fieldno - 1)->attname);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -8180,7 +8182,7 @@ get_rule_expr(Node *node, deparse_context *context,
|
||||
Node *e = (Node *) lfirst(arg);
|
||||
|
||||
if (tupdesc == NULL ||
|
||||
!tupdesc->attrs[i]->attisdropped)
|
||||
!TupleDescAttr(tupdesc, i)->attisdropped)
|
||||
{
|
||||
appendStringInfoString(buf, sep);
|
||||
/* Whole-row Vars need special treatment here */
|
||||
@ -8193,7 +8195,7 @@ get_rule_expr(Node *node, deparse_context *context,
|
||||
{
|
||||
while (i < tupdesc->natts)
|
||||
{
|
||||
if (!tupdesc->attrs[i]->attisdropped)
|
||||
if (!TupleDescAttr(tupdesc, i)->attisdropped)
|
||||
{
|
||||
appendStringInfoString(buf, sep);
|
||||
appendStringInfoString(buf, "NULL");
|
||||
|
@ -273,9 +273,11 @@ currtid_for_view(Relation viewrel, ItemPointer tid)
|
||||
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
if (strcmp(NameStr(att->attrs[i]->attname), "ctid") == 0)
|
||||
Form_pg_attribute attr = TupleDescAttr(att, i);
|
||||
|
||||
if (strcmp(NameStr(attr->attname), "ctid") == 0)
|
||||
{
|
||||
if (att->attrs[i]->atttypid != TIDOID)
|
||||
if (attr->atttypid != TIDOID)
|
||||
elog(ERROR, "ctid isn't of type TID");
|
||||
tididx = i;
|
||||
break;
|
||||
|
@ -3099,13 +3099,15 @@ map_sql_table_to_xmlschema(TupleDesc tupdesc, Oid relid, bool nulls,
|
||||
|
||||
for (i = 0; i < tupdesc->natts; i++)
|
||||
{
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
|
||||
if (att->attisdropped)
|
||||
continue;
|
||||
appendStringInfo(&result,
|
||||
" <xsd:element name=\"%s\" type=\"%s\"%s></xsd:element>\n",
|
||||
map_sql_identifier_to_xml_name(NameStr(tupdesc->attrs[i]->attname),
|
||||
map_sql_identifier_to_xml_name(NameStr(att->attname),
|
||||
true, false),
|
||||
map_sql_type_to_xml_name(tupdesc->attrs[i]->atttypid, -1),
|
||||
map_sql_type_to_xml_name(att->atttypid, -1),
|
||||
nulls ? " nillable=\"true\"" : " minOccurs=\"0\"");
|
||||
}
|
||||
|
||||
@ -3392,10 +3394,11 @@ map_sql_typecoll_to_xmlschema_types(List *tupdesc_list)
|
||||
|
||||
for (i = 0; i < tupdesc->natts; i++)
|
||||
{
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
|
||||
if (att->attisdropped)
|
||||
continue;
|
||||
uniquetypes = list_append_unique_oid(uniquetypes,
|
||||
tupdesc->attrs[i]->atttypid);
|
||||
uniquetypes = list_append_unique_oid(uniquetypes, att->atttypid);
|
||||
}
|
||||
}
|
||||
|
||||
|
5
src/backend/utils/cache/catcache.c
vendored
5
src/backend/utils/cache/catcache.c
vendored
@ -797,7 +797,7 @@ do { \
|
||||
if (cache->cc_key[i] > 0) { \
|
||||
elog(DEBUG2, "CatalogCacheInitializeCache: load %d/%d w/%d, %u", \
|
||||
i+1, cache->cc_nkeys, cache->cc_key[i], \
|
||||
tupdesc->attrs[cache->cc_key[i] - 1]->atttypid); \
|
||||
TupleDescAttr(tupdesc, cache->cc_key[i] - 1)->atttypid); \
|
||||
} else { \
|
||||
elog(DEBUG2, "CatalogCacheInitializeCache: load %d/%d w/%d", \
|
||||
i+1, cache->cc_nkeys, cache->cc_key[i]); \
|
||||
@ -862,7 +862,8 @@ CatalogCacheInitializeCache(CatCache *cache)
|
||||
|
||||
if (cache->cc_key[i] > 0)
|
||||
{
|
||||
Form_pg_attribute attr = tupdesc->attrs[cache->cc_key[i] - 1];
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc,
|
||||
cache->cc_key[i] - 1);
|
||||
|
||||
keytype = attr->atttypid;
|
||||
/* cache key columns should always be NOT NULL */
|
||||
|
55
src/backend/utils/cache/relcache.c
vendored
55
src/backend/utils/cache/relcache.c
vendored
@ -546,7 +546,7 @@ RelationBuildTupleDesc(Relation relation)
|
||||
elog(ERROR, "invalid attribute number %d for %s",
|
||||
attp->attnum, RelationGetRelationName(relation));
|
||||
|
||||
memcpy(relation->rd_att->attrs[attp->attnum - 1],
|
||||
memcpy(TupleDescAttr(relation->rd_att, attp->attnum - 1),
|
||||
attp,
|
||||
ATTRIBUTE_FIXED_PART_SIZE);
|
||||
|
||||
@ -590,7 +590,7 @@ RelationBuildTupleDesc(Relation relation)
|
||||
int i;
|
||||
|
||||
for (i = 0; i < relation->rd_rel->relnatts; i++)
|
||||
Assert(relation->rd_att->attrs[i]->attcacheoff == -1);
|
||||
Assert(TupleDescAttr(relation->rd_att, i)->attcacheoff == -1);
|
||||
}
|
||||
#endif
|
||||
|
||||
@ -600,7 +600,7 @@ RelationBuildTupleDesc(Relation relation)
|
||||
* for attnum=1 that used to exist in fastgetattr() and index_getattr().
|
||||
*/
|
||||
if (relation->rd_rel->relnatts > 0)
|
||||
relation->rd_att->attrs[0]->attcacheoff = 0;
|
||||
TupleDescAttr(relation->rd_att, 0)->attcacheoff = 0;
|
||||
|
||||
/*
|
||||
* Set up constraint/default info
|
||||
@ -958,9 +958,11 @@ RelationBuildPartitionKey(Relation relation)
|
||||
/* Collect type information */
|
||||
if (attno != 0)
|
||||
{
|
||||
key->parttypid[i] = relation->rd_att->attrs[attno - 1]->atttypid;
|
||||
key->parttypmod[i] = relation->rd_att->attrs[attno - 1]->atttypmod;
|
||||
key->parttypcoll[i] = relation->rd_att->attrs[attno - 1]->attcollation;
|
||||
Form_pg_attribute att = TupleDescAttr(relation->rd_att, attno - 1);
|
||||
|
||||
key->parttypid[i] = att->atttypid;
|
||||
key->parttypmod[i] = att->atttypmod;
|
||||
key->parttypcoll[i] = att->attcollation;
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -1977,16 +1979,16 @@ formrdesc(const char *relationName, Oid relationReltype,
|
||||
has_not_null = false;
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
memcpy(relation->rd_att->attrs[i],
|
||||
memcpy(TupleDescAttr(relation->rd_att, i),
|
||||
&attrs[i],
|
||||
ATTRIBUTE_FIXED_PART_SIZE);
|
||||
has_not_null |= attrs[i].attnotnull;
|
||||
/* make sure attcacheoff is valid */
|
||||
relation->rd_att->attrs[i]->attcacheoff = -1;
|
||||
TupleDescAttr(relation->rd_att, i)->attcacheoff = -1;
|
||||
}
|
||||
|
||||
/* initialize first attribute's attcacheoff, cf RelationBuildTupleDesc */
|
||||
relation->rd_att->attrs[0]->attcacheoff = 0;
|
||||
TupleDescAttr(relation->rd_att, 0)->attcacheoff = 0;
|
||||
|
||||
/* mark not-null status */
|
||||
if (has_not_null)
|
||||
@ -2000,7 +2002,7 @@ formrdesc(const char *relationName, Oid relationReltype,
|
||||
/*
|
||||
* initialize relation id from info in att array (my, this is ugly)
|
||||
*/
|
||||
RelationGetRelid(relation) = relation->rd_att->attrs[0]->attrelid;
|
||||
RelationGetRelid(relation) = TupleDescAttr(relation->rd_att, 0)->attrelid;
|
||||
|
||||
/*
|
||||
* All relations made with formrdesc are mapped. This is necessarily so
|
||||
@ -3274,9 +3276,12 @@ RelationBuildLocalRelation(const char *relname,
|
||||
has_not_null = false;
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
rel->rd_att->attrs[i]->attidentity = tupDesc->attrs[i]->attidentity;
|
||||
rel->rd_att->attrs[i]->attnotnull = tupDesc->attrs[i]->attnotnull;
|
||||
has_not_null |= tupDesc->attrs[i]->attnotnull;
|
||||
Form_pg_attribute satt = TupleDescAttr(tupDesc, i);
|
||||
Form_pg_attribute datt = TupleDescAttr(rel->rd_att, i);
|
||||
|
||||
datt->attidentity = satt->attidentity;
|
||||
datt->attnotnull = satt->attnotnull;
|
||||
has_not_null |= satt->attnotnull;
|
||||
}
|
||||
|
||||
if (has_not_null)
|
||||
@ -3346,7 +3351,7 @@ RelationBuildLocalRelation(const char *relname,
|
||||
RelationGetRelid(rel) = relid;
|
||||
|
||||
for (i = 0; i < natts; i++)
|
||||
rel->rd_att->attrs[i]->attrelid = relid;
|
||||
TupleDescAttr(rel->rd_att, i)->attrelid = relid;
|
||||
|
||||
rel->rd_rel->reltablespace = reltablespace;
|
||||
|
||||
@ -3971,13 +3976,13 @@ BuildHardcodedDescriptor(int natts, const FormData_pg_attribute *attrs,
|
||||
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
memcpy(result->attrs[i], &attrs[i], ATTRIBUTE_FIXED_PART_SIZE);
|
||||
memcpy(TupleDescAttr(result, i), &attrs[i], ATTRIBUTE_FIXED_PART_SIZE);
|
||||
/* make sure attcacheoff is valid */
|
||||
result->attrs[i]->attcacheoff = -1;
|
||||
TupleDescAttr(result, i)->attcacheoff = -1;
|
||||
}
|
||||
|
||||
/* initialize first attribute's attcacheoff, cf RelationBuildTupleDesc */
|
||||
result->attrs[0]->attcacheoff = 0;
|
||||
TupleDescAttr(result, 0)->attcacheoff = 0;
|
||||
|
||||
/* Note: we don't bother to set up a TupleConstr entry */
|
||||
|
||||
@ -4044,6 +4049,7 @@ AttrDefaultFetch(Relation relation)
|
||||
while (HeapTupleIsValid(htup = systable_getnext(adscan)))
|
||||
{
|
||||
Form_pg_attrdef adform = (Form_pg_attrdef) GETSTRUCT(htup);
|
||||
Form_pg_attribute attr = TupleDescAttr(relation->rd_att, adform->adnum - 1);
|
||||
|
||||
for (i = 0; i < ndef; i++)
|
||||
{
|
||||
@ -4051,7 +4057,7 @@ AttrDefaultFetch(Relation relation)
|
||||
continue;
|
||||
if (attrdef[i].adbin != NULL)
|
||||
elog(WARNING, "multiple attrdef records found for attr %s of rel %s",
|
||||
NameStr(relation->rd_att->attrs[adform->adnum - 1]->attname),
|
||||
NameStr(attr->attname),
|
||||
RelationGetRelationName(relation));
|
||||
else
|
||||
found++;
|
||||
@ -4061,7 +4067,7 @@ AttrDefaultFetch(Relation relation)
|
||||
adrel->rd_att, &isnull);
|
||||
if (isnull)
|
||||
elog(WARNING, "null adbin for attr %s of rel %s",
|
||||
NameStr(relation->rd_att->attrs[adform->adnum - 1]->attname),
|
||||
NameStr(attr->attname),
|
||||
RelationGetRelationName(relation));
|
||||
else
|
||||
{
|
||||
@ -5270,7 +5276,7 @@ errtablecol(Relation rel, int attnum)
|
||||
|
||||
/* Use reldesc if it's a user attribute, else consult the catalogs */
|
||||
if (attnum > 0 && attnum <= reldesc->natts)
|
||||
colname = NameStr(reldesc->attrs[attnum - 1]->attname);
|
||||
colname = NameStr(TupleDescAttr(reldesc, attnum - 1)->attname);
|
||||
else
|
||||
colname = get_relid_attribute_name(RelationGetRelid(rel), attnum);
|
||||
|
||||
@ -5460,14 +5466,16 @@ load_relcache_init_file(bool shared)
|
||||
has_not_null = false;
|
||||
for (i = 0; i < relform->relnatts; i++)
|
||||
{
|
||||
Form_pg_attribute attr = TupleDescAttr(rel->rd_att, i);
|
||||
|
||||
if (fread(&len, 1, sizeof(len), fp) != sizeof(len))
|
||||
goto read_failed;
|
||||
if (len != ATTRIBUTE_FIXED_PART_SIZE)
|
||||
goto read_failed;
|
||||
if (fread(rel->rd_att->attrs[i], 1, len, fp) != len)
|
||||
if (fread(attr, 1, len, fp) != len)
|
||||
goto read_failed;
|
||||
|
||||
has_not_null |= rel->rd_att->attrs[i]->attnotnull;
|
||||
has_not_null |= attr->attnotnull;
|
||||
}
|
||||
|
||||
/* next read the access method specific field */
|
||||
@ -5848,7 +5856,8 @@ write_relcache_init_file(bool shared)
|
||||
/* next, do all the attribute tuple form data entries */
|
||||
for (i = 0; i < relform->relnatts; i++)
|
||||
{
|
||||
write_item(rel->rd_att->attrs[i], ATTRIBUTE_FIXED_PART_SIZE, fp);
|
||||
write_item(TupleDescAttr(rel->rd_att, i),
|
||||
ATTRIBUTE_FIXED_PART_SIZE, fp);
|
||||
}
|
||||
|
||||
/* next, do the access method specific field */
|
||||
|
7
src/backend/utils/cache/typcache.c
vendored
7
src/backend/utils/cache/typcache.c
vendored
@ -1176,11 +1176,12 @@ cache_record_field_properties(TypeCacheEntry *typentry)
|
||||
for (i = 0; i < tupdesc->natts; i++)
|
||||
{
|
||||
TypeCacheEntry *fieldentry;
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, i);
|
||||
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
if (attr->attisdropped)
|
||||
continue;
|
||||
|
||||
fieldentry = lookup_type_cache(tupdesc->attrs[i]->atttypid,
|
||||
fieldentry = lookup_type_cache(attr->atttypid,
|
||||
TYPECACHE_EQ_OPR |
|
||||
TYPECACHE_CMP_PROC);
|
||||
if (!OidIsValid(fieldentry->eq_opr))
|
||||
@ -1340,7 +1341,7 @@ assign_record_type_typmod(TupleDesc tupDesc)
|
||||
{
|
||||
if (i >= REC_HASH_KEYS)
|
||||
break;
|
||||
hashkey[i] = tupDesc->attrs[i]->atttypid;
|
||||
hashkey[i] = TupleDescAttr(tupDesc, i)->atttypid;
|
||||
}
|
||||
recentry = (RecordCacheEntry *) hash_search(RecordCacheHash,
|
||||
(void *) hashkey,
|
||||
|
@ -419,7 +419,7 @@ resolve_polymorphic_tupdesc(TupleDesc tupdesc, oidvector *declared_args,
|
||||
/* See if there are any polymorphic outputs; quick out if not */
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
switch (tupdesc->attrs[i]->atttypid)
|
||||
switch (TupleDescAttr(tupdesc, i)->atttypid)
|
||||
{
|
||||
case ANYELEMENTOID:
|
||||
have_anyelement_result = true;
|
||||
@ -548,13 +548,15 @@ resolve_polymorphic_tupdesc(TupleDesc tupdesc, oidvector *declared_args,
|
||||
/* And finally replace the tuple column types as needed */
|
||||
for (i = 0; i < natts; i++)
|
||||
{
|
||||
switch (tupdesc->attrs[i]->atttypid)
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
|
||||
switch (att->atttypid)
|
||||
{
|
||||
case ANYELEMENTOID:
|
||||
case ANYNONARRAYOID:
|
||||
case ANYENUMOID:
|
||||
TupleDescInitEntry(tupdesc, i + 1,
|
||||
NameStr(tupdesc->attrs[i]->attname),
|
||||
NameStr(att->attname),
|
||||
anyelement_type,
|
||||
-1,
|
||||
0);
|
||||
@ -562,7 +564,7 @@ resolve_polymorphic_tupdesc(TupleDesc tupdesc, oidvector *declared_args,
|
||||
break;
|
||||
case ANYARRAYOID:
|
||||
TupleDescInitEntry(tupdesc, i + 1,
|
||||
NameStr(tupdesc->attrs[i]->attname),
|
||||
NameStr(att->attname),
|
||||
anyarray_type,
|
||||
-1,
|
||||
0);
|
||||
@ -570,7 +572,7 @@ resolve_polymorphic_tupdesc(TupleDesc tupdesc, oidvector *declared_args,
|
||||
break;
|
||||
case ANYRANGEOID:
|
||||
TupleDescInitEntry(tupdesc, i + 1,
|
||||
NameStr(tupdesc->attrs[i]->attname),
|
||||
NameStr(att->attname),
|
||||
anyrange_type,
|
||||
-1,
|
||||
0);
|
||||
@ -1344,9 +1346,10 @@ TypeGetTupleDesc(Oid typeoid, List *colaliases)
|
||||
for (varattno = 0; varattno < natts; varattno++)
|
||||
{
|
||||
char *label = strVal(list_nth(colaliases, varattno));
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, varattno);
|
||||
|
||||
if (label != NULL)
|
||||
namestrcpy(&(tupdesc->attrs[varattno]->attname), label);
|
||||
namestrcpy(&(attr->attname), label);
|
||||
}
|
||||
|
||||
/* The tuple type is now an anonymous record type */
|
||||
|
@ -54,8 +54,8 @@ pg_config(PG_FUNCTION_ARGS)
|
||||
* Check to make sure we have a reasonable tuple descriptor
|
||||
*/
|
||||
if (tupdesc->natts != 2 ||
|
||||
tupdesc->attrs[0]->atttypid != TEXTOID ||
|
||||
tupdesc->attrs[1]->atttypid != TEXTOID)
|
||||
TupleDescAttr(tupdesc, 0)->atttypid != TEXTOID ||
|
||||
TupleDescAttr(tupdesc, 1)->atttypid != TEXTOID)
|
||||
ereport(ERROR,
|
||||
(errcode(ERRCODE_SYNTAX_ERROR),
|
||||
errmsg("query-specified return tuple and "
|
||||
|
@ -722,11 +722,11 @@ struct MinimalTupleData
|
||||
(*(isnull) = false), \
|
||||
HeapTupleNoNulls(tup) ? \
|
||||
( \
|
||||
(tupleDesc)->attrs[(attnum)-1]->attcacheoff >= 0 ? \
|
||||
TupleDescAttr((tupleDesc), (attnum)-1)->attcacheoff >= 0 ? \
|
||||
( \
|
||||
fetchatt((tupleDesc)->attrs[(attnum)-1], \
|
||||
fetchatt(TupleDescAttr((tupleDesc), (attnum)-1), \
|
||||
(char *) (tup)->t_data + (tup)->t_data->t_hoff + \
|
||||
(tupleDesc)->attrs[(attnum)-1]->attcacheoff) \
|
||||
TupleDescAttr((tupleDesc), (attnum)-1)->attcacheoff)\
|
||||
) \
|
||||
: \
|
||||
nocachegetattr((tup), (attnum), (tupleDesc)) \
|
||||
|
@ -103,11 +103,11 @@ typedef IndexAttributeBitMapData * IndexAttributeBitMap;
|
||||
*(isnull) = false, \
|
||||
!IndexTupleHasNulls(tup) ? \
|
||||
( \
|
||||
(tupleDesc)->attrs[(attnum)-1]->attcacheoff >= 0 ? \
|
||||
TupleDescAttr((tupleDesc), (attnum)-1)->attcacheoff >= 0 ? \
|
||||
( \
|
||||
fetchatt((tupleDesc)->attrs[(attnum)-1], \
|
||||
fetchatt(TupleDescAttr((tupleDesc), (attnum)-1), \
|
||||
(char *) (tup) + IndexInfoFindDataOffset((tup)->t_info) \
|
||||
+ (tupleDesc)->attrs[(attnum)-1]->attcacheoff) \
|
||||
+ TupleDescAttr((tupleDesc), (attnum)-1)->attcacheoff) \
|
||||
) \
|
||||
: \
|
||||
nocache_index_getattr((tup), (attnum), (tupleDesc)) \
|
||||
|
@ -80,6 +80,8 @@ typedef struct tupleDesc
|
||||
int tdrefcount; /* reference count, or -1 if not counting */
|
||||
} *TupleDesc;
|
||||
|
||||
/* Accessor for the i'th attribute of tupdesc. */
|
||||
#define TupleDescAttr(tupdesc, i) ((tupdesc)->attrs[(i)])
|
||||
|
||||
extern TupleDesc CreateTemplateTupleDesc(int natts, bool hasoid);
|
||||
|
||||
|
@ -1095,6 +1095,7 @@ plperl_build_tuple_result(HV *perlhash, TupleDesc td)
|
||||
SV *val = HeVAL(he);
|
||||
char *key = hek2cstr(he);
|
||||
int attn = SPI_fnumber(td, key);
|
||||
Form_pg_attribute attr = TupleDescAttr(td, attn - 1);
|
||||
|
||||
if (attn == SPI_ERROR_NOATTRIBUTE)
|
||||
ereport(ERROR,
|
||||
@ -1108,8 +1109,8 @@ plperl_build_tuple_result(HV *perlhash, TupleDesc td)
|
||||
key)));
|
||||
|
||||
values[attn - 1] = plperl_sv_to_datum(val,
|
||||
td->attrs[attn - 1]->atttypid,
|
||||
td->attrs[attn - 1]->atttypmod,
|
||||
attr->atttypid,
|
||||
attr->atttypmod,
|
||||
NULL,
|
||||
NULL,
|
||||
InvalidOid,
|
||||
@ -1757,6 +1758,7 @@ plperl_modify_tuple(HV *hvTD, TriggerData *tdata, HeapTuple otup)
|
||||
char *key = hek2cstr(he);
|
||||
SV *val = HeVAL(he);
|
||||
int attn = SPI_fnumber(tupdesc, key);
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, attn - 1);
|
||||
|
||||
if (attn == SPI_ERROR_NOATTRIBUTE)
|
||||
ereport(ERROR,
|
||||
@ -1770,8 +1772,8 @@ plperl_modify_tuple(HV *hvTD, TriggerData *tdata, HeapTuple otup)
|
||||
key)));
|
||||
|
||||
modvalues[attn - 1] = plperl_sv_to_datum(val,
|
||||
tupdesc->attrs[attn - 1]->atttypid,
|
||||
tupdesc->attrs[attn - 1]->atttypmod,
|
||||
attr->atttypid,
|
||||
attr->atttypmod,
|
||||
NULL,
|
||||
NULL,
|
||||
InvalidOid,
|
||||
@ -3014,11 +3016,12 @@ plperl_hash_from_tuple(HeapTuple tuple, TupleDesc tupdesc)
|
||||
typisvarlena;
|
||||
char *attname;
|
||||
Oid typoutput;
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
if (att->attisdropped)
|
||||
continue;
|
||||
|
||||
attname = NameStr(tupdesc->attrs[i]->attname);
|
||||
attname = NameStr(att->attname);
|
||||
attr = heap_getattr(tuple, i + 1, tupdesc, &isnull);
|
||||
|
||||
if (isnull)
|
||||
@ -3032,7 +3035,7 @@ plperl_hash_from_tuple(HeapTuple tuple, TupleDesc tupdesc)
|
||||
continue;
|
||||
}
|
||||
|
||||
if (type_is_rowtype(tupdesc->attrs[i]->atttypid))
|
||||
if (type_is_rowtype(att->atttypid))
|
||||
{
|
||||
SV *sv = plperl_hash_from_datum(attr);
|
||||
|
||||
@ -3043,17 +3046,16 @@ plperl_hash_from_tuple(HeapTuple tuple, TupleDesc tupdesc)
|
||||
SV *sv;
|
||||
Oid funcid;
|
||||
|
||||
if (OidIsValid(get_base_element_type(tupdesc->attrs[i]->atttypid)))
|
||||
sv = plperl_ref_from_pg_array(attr, tupdesc->attrs[i]->atttypid);
|
||||
else if ((funcid = get_transform_fromsql(tupdesc->attrs[i]->atttypid, current_call_data->prodesc->lang_oid, current_call_data->prodesc->trftypes)))
|
||||
if (OidIsValid(get_base_element_type(att->atttypid)))
|
||||
sv = plperl_ref_from_pg_array(attr, att->atttypid);
|
||||
else if ((funcid = get_transform_fromsql(att->atttypid, current_call_data->prodesc->lang_oid, current_call_data->prodesc->trftypes)))
|
||||
sv = (SV *) DatumGetPointer(OidFunctionCall1(funcid, attr));
|
||||
else
|
||||
{
|
||||
char *outputstr;
|
||||
|
||||
/* XXX should have a way to cache these lookups */
|
||||
getTypeOutputInfo(tupdesc->attrs[i]->atttypid,
|
||||
&typoutput, &typisvarlena);
|
||||
getTypeOutputInfo(att->atttypid, &typoutput, &typisvarlena);
|
||||
|
||||
outputstr = OidOutputFunctionCall(typoutput, attr);
|
||||
sv = cstr2sv(outputstr);
|
||||
|
@ -2012,7 +2012,7 @@ build_row_from_class(Oid classOid)
|
||||
/*
|
||||
* Get the attribute and check for dropped column
|
||||
*/
|
||||
attrStruct = row->rowtupdesc->attrs[i];
|
||||
attrStruct = TupleDescAttr(row->rowtupdesc, i);
|
||||
|
||||
if (!attrStruct->attisdropped)
|
||||
{
|
||||
|
@ -2841,6 +2841,7 @@ exec_stmt_return_next(PLpgSQL_execstate *estate,
|
||||
PLpgSQL_var *var = (PLpgSQL_var *) retvar;
|
||||
Datum retval = var->value;
|
||||
bool isNull = var->isnull;
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, 0);
|
||||
|
||||
if (natts != 1)
|
||||
ereport(ERROR,
|
||||
@ -2858,8 +2859,8 @@ exec_stmt_return_next(PLpgSQL_execstate *estate,
|
||||
&isNull,
|
||||
var->datatype->typoid,
|
||||
var->datatype->atttypmod,
|
||||
tupdesc->attrs[0]->atttypid,
|
||||
tupdesc->attrs[0]->atttypmod);
|
||||
attr->atttypid,
|
||||
attr->atttypmod);
|
||||
|
||||
tuplestore_putvalues(estate->tuple_store, tupdesc,
|
||||
&retval, &isNull);
|
||||
@ -2968,6 +2969,8 @@ exec_stmt_return_next(PLpgSQL_execstate *estate,
|
||||
}
|
||||
else
|
||||
{
|
||||
Form_pg_attribute attr = TupleDescAttr(tupdesc, 0);
|
||||
|
||||
/* Simple scalar result */
|
||||
if (natts != 1)
|
||||
ereport(ERROR,
|
||||
@ -2980,8 +2983,8 @@ exec_stmt_return_next(PLpgSQL_execstate *estate,
|
||||
&isNull,
|
||||
rettype,
|
||||
rettypmod,
|
||||
tupdesc->attrs[0]->atttypid,
|
||||
tupdesc->attrs[0]->atttypmod);
|
||||
attr->atttypid,
|
||||
attr->atttypmod);
|
||||
|
||||
tuplestore_putvalues(estate->tuple_store, tupdesc,
|
||||
&retval, &isNull);
|
||||
@ -4588,8 +4591,8 @@ exec_assign_value(PLpgSQL_execstate *estate,
|
||||
* Now insert the new value, being careful to cast it to the
|
||||
* right type.
|
||||
*/
|
||||
atttype = rec->tupdesc->attrs[fno - 1]->atttypid;
|
||||
atttypmod = rec->tupdesc->attrs[fno - 1]->atttypmod;
|
||||
atttype = TupleDescAttr(rec->tupdesc, fno - 1)->atttypid;
|
||||
atttypmod = TupleDescAttr(rec->tupdesc, fno - 1)->atttypmod;
|
||||
values[0] = exec_cast_value(estate,
|
||||
value,
|
||||
&isNull,
|
||||
@ -4913,7 +4916,11 @@ exec_eval_datum(PLpgSQL_execstate *estate,
|
||||
rec->refname, recfield->fieldname)));
|
||||
*typeid = SPI_gettypeid(rec->tupdesc, fno);
|
||||
if (fno > 0)
|
||||
*typetypmod = rec->tupdesc->attrs[fno - 1]->atttypmod;
|
||||
{
|
||||
Form_pg_attribute attr = TupleDescAttr(rec->tupdesc, fno - 1);
|
||||
|
||||
*typetypmod = attr->atttypmod;
|
||||
}
|
||||
else
|
||||
*typetypmod = -1;
|
||||
*value = SPI_getbinval(rec->tup, rec->tupdesc, fno, isnull);
|
||||
@ -5089,11 +5096,19 @@ plpgsql_exec_get_datum_type_info(PLpgSQL_execstate *estate,
|
||||
rec->refname, recfield->fieldname)));
|
||||
*typeid = SPI_gettypeid(rec->tupdesc, fno);
|
||||
if (fno > 0)
|
||||
*typmod = rec->tupdesc->attrs[fno - 1]->atttypmod;
|
||||
{
|
||||
Form_pg_attribute attr = TupleDescAttr(rec->tupdesc, fno - 1);
|
||||
|
||||
*typmod = attr->atttypmod;
|
||||
}
|
||||
else
|
||||
*typmod = -1;
|
||||
if (fno > 0)
|
||||
*collation = rec->tupdesc->attrs[fno - 1]->attcollation;
|
||||
{
|
||||
Form_pg_attribute attr = TupleDescAttr(rec->tupdesc, fno - 1);
|
||||
|
||||
*collation = attr->attcollation;
|
||||
}
|
||||
else /* no system column types have collation */
|
||||
*collation = InvalidOid;
|
||||
break;
|
||||
@ -5172,6 +5187,7 @@ exec_eval_expr(PLpgSQL_execstate *estate,
|
||||
{
|
||||
Datum result = 0;
|
||||
int rc;
|
||||
Form_pg_attribute attr;
|
||||
|
||||
/*
|
||||
* If first time through, create a plan for this expression.
|
||||
@ -5211,8 +5227,9 @@ exec_eval_expr(PLpgSQL_execstate *estate,
|
||||
/*
|
||||
* ... and get the column's datatype.
|
||||
*/
|
||||
*rettype = estate->eval_tuptable->tupdesc->attrs[0]->atttypid;
|
||||
*rettypmod = estate->eval_tuptable->tupdesc->attrs[0]->atttypmod;
|
||||
attr = TupleDescAttr(estate->eval_tuptable->tupdesc, 0);
|
||||
*rettype = attr->atttypid;
|
||||
*rettypmod = attr->atttypmod;
|
||||
|
||||
/*
|
||||
* If there are no rows selected, the result is a NULL of that type.
|
||||
@ -6030,7 +6047,8 @@ exec_move_row(PLpgSQL_execstate *estate,
|
||||
|
||||
var = (PLpgSQL_var *) (estate->datums[row->varnos[fnum]]);
|
||||
|
||||
while (anum < td_natts && tupdesc->attrs[anum]->attisdropped)
|
||||
while (anum < td_natts &&
|
||||
TupleDescAttr(tupdesc, anum)->attisdropped)
|
||||
anum++; /* skip dropped column in tuple */
|
||||
|
||||
if (anum < td_natts)
|
||||
@ -6042,8 +6060,8 @@ exec_move_row(PLpgSQL_execstate *estate,
|
||||
value = (Datum) 0;
|
||||
isnull = true;
|
||||
}
|
||||
valtype = tupdesc->attrs[anum]->atttypid;
|
||||
valtypmod = tupdesc->attrs[anum]->atttypmod;
|
||||
valtype = TupleDescAttr(tupdesc, anum)->atttypid;
|
||||
valtypmod = TupleDescAttr(tupdesc, anum)->atttypmod;
|
||||
anum++;
|
||||
}
|
||||
else
|
||||
@ -6095,7 +6113,7 @@ make_tuple_from_row(PLpgSQL_execstate *estate,
|
||||
Oid fieldtypeid;
|
||||
int32 fieldtypmod;
|
||||
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
if (TupleDescAttr(tupdesc, i)->attisdropped)
|
||||
{
|
||||
nulls[i] = true; /* leave the column as null */
|
||||
continue;
|
||||
@ -6106,7 +6124,7 @@ make_tuple_from_row(PLpgSQL_execstate *estate,
|
||||
exec_eval_datum(estate, estate->datums[row->varnos[i]],
|
||||
&fieldtypeid, &fieldtypmod,
|
||||
&dvalues[i], &nulls[i]);
|
||||
if (fieldtypeid != tupdesc->attrs[i]->atttypid)
|
||||
if (fieldtypeid != TupleDescAttr(tupdesc, i)->atttypid)
|
||||
return NULL;
|
||||
/* XXX should we insist on typmod match, too? */
|
||||
}
|
||||
|
@ -950,6 +950,7 @@ PLy_modify_tuple(PLyProcedure *proc, PyObject *pltd, TriggerData *tdata,
|
||||
char *plattstr;
|
||||
int attn;
|
||||
PLyObToDatum *att;
|
||||
Form_pg_attribute attr;
|
||||
|
||||
platt = PyList_GetItem(plkeys, i);
|
||||
if (PyString_Check(platt))
|
||||
@ -982,11 +983,12 @@ PLy_modify_tuple(PLyProcedure *proc, PyObject *pltd, TriggerData *tdata,
|
||||
|
||||
Py_INCREF(plval);
|
||||
|
||||
attr = TupleDescAttr(tupdesc, attn - 1);
|
||||
if (plval != Py_None)
|
||||
{
|
||||
modvalues[attn - 1] =
|
||||
(att->func) (att,
|
||||
tupdesc->attrs[attn - 1]->atttypmod,
|
||||
attr->atttypmod,
|
||||
plval,
|
||||
false);
|
||||
modnulls[attn - 1] = false;
|
||||
@ -997,7 +999,7 @@ PLy_modify_tuple(PLyProcedure *proc, PyObject *pltd, TriggerData *tdata,
|
||||
InputFunctionCall(&att->typfunc,
|
||||
NULL,
|
||||
att->typioparam,
|
||||
tupdesc->attrs[attn - 1]->atttypmod);
|
||||
attr->atttypmod);
|
||||
modnulls[attn - 1] = true;
|
||||
}
|
||||
modrepls[attn - 1] = true;
|
||||
|
@ -148,7 +148,11 @@ PLy_result_colnames(PyObject *self, PyObject *unused)
|
||||
|
||||
list = PyList_New(ob->tupdesc->natts);
|
||||
for (i = 0; i < ob->tupdesc->natts; i++)
|
||||
PyList_SET_ITEM(list, i, PyString_FromString(NameStr(ob->tupdesc->attrs[i]->attname)));
|
||||
{
|
||||
Form_pg_attribute attr = TupleDescAttr(ob->tupdesc, i);
|
||||
|
||||
PyList_SET_ITEM(list, i, PyString_FromString(NameStr(attr->attname)));
|
||||
}
|
||||
|
||||
return list;
|
||||
}
|
||||
@ -168,7 +172,11 @@ PLy_result_coltypes(PyObject *self, PyObject *unused)
|
||||
|
||||
list = PyList_New(ob->tupdesc->natts);
|
||||
for (i = 0; i < ob->tupdesc->natts; i++)
|
||||
PyList_SET_ITEM(list, i, PyInt_FromLong(ob->tupdesc->attrs[i]->atttypid));
|
||||
{
|
||||
Form_pg_attribute attr = TupleDescAttr(ob->tupdesc, i);
|
||||
|
||||
PyList_SET_ITEM(list, i, PyInt_FromLong(attr->atttypid));
|
||||
}
|
||||
|
||||
return list;
|
||||
}
|
||||
@ -188,7 +196,11 @@ PLy_result_coltypmods(PyObject *self, PyObject *unused)
|
||||
|
||||
list = PyList_New(ob->tupdesc->natts);
|
||||
for (i = 0; i < ob->tupdesc->natts; i++)
|
||||
PyList_SET_ITEM(list, i, PyInt_FromLong(ob->tupdesc->attrs[i]->atttypmod));
|
||||
{
|
||||
Form_pg_attribute attr = TupleDescAttr(ob->tupdesc, i);
|
||||
|
||||
PyList_SET_ITEM(list, i, PyInt_FromLong(attr->atttypmod));
|
||||
}
|
||||
|
||||
return list;
|
||||
}
|
||||
|
@ -152,21 +152,21 @@ PLy_input_tuple_funcs(PLyTypeInfo *arg, TupleDesc desc)
|
||||
for (i = 0; i < desc->natts; i++)
|
||||
{
|
||||
HeapTuple typeTup;
|
||||
Form_pg_attribute attr = TupleDescAttr(desc, i);
|
||||
|
||||
if (desc->attrs[i]->attisdropped)
|
||||
if (attr->attisdropped)
|
||||
continue;
|
||||
|
||||
if (arg->in.r.atts[i].typoid == desc->attrs[i]->atttypid)
|
||||
if (arg->in.r.atts[i].typoid == attr->atttypid)
|
||||
continue; /* already set up this entry */
|
||||
|
||||
typeTup = SearchSysCache1(TYPEOID,
|
||||
ObjectIdGetDatum(desc->attrs[i]->atttypid));
|
||||
typeTup = SearchSysCache1(TYPEOID, ObjectIdGetDatum(attr->atttypid));
|
||||
if (!HeapTupleIsValid(typeTup))
|
||||
elog(ERROR, "cache lookup failed for type %u",
|
||||
desc->attrs[i]->atttypid);
|
||||
attr->atttypid);
|
||||
|
||||
PLy_input_datum_func2(&(arg->in.r.atts[i]), arg->mcxt,
|
||||
desc->attrs[i]->atttypid,
|
||||
attr->atttypid,
|
||||
typeTup,
|
||||
exec_ctx->curr_proc->langid,
|
||||
exec_ctx->curr_proc->trftypes);
|
||||
@ -224,18 +224,18 @@ PLy_output_tuple_funcs(PLyTypeInfo *arg, TupleDesc desc)
|
||||
for (i = 0; i < desc->natts; i++)
|
||||
{
|
||||
HeapTuple typeTup;
|
||||
Form_pg_attribute attr = TupleDescAttr(desc, i);
|
||||
|
||||
if (desc->attrs[i]->attisdropped)
|
||||
if (attr->attisdropped)
|
||||
continue;
|
||||
|
||||
if (arg->out.r.atts[i].typoid == desc->attrs[i]->atttypid)
|
||||
if (arg->out.r.atts[i].typoid == attr->atttypid)
|
||||
continue; /* already set up this entry */
|
||||
|
||||
typeTup = SearchSysCache1(TYPEOID,
|
||||
ObjectIdGetDatum(desc->attrs[i]->atttypid));
|
||||
typeTup = SearchSysCache1(TYPEOID, ObjectIdGetDatum(attr->atttypid));
|
||||
if (!HeapTupleIsValid(typeTup))
|
||||
elog(ERROR, "cache lookup failed for type %u",
|
||||
desc->attrs[i]->atttypid);
|
||||
attr->atttypid);
|
||||
|
||||
PLy_output_datum_func2(&(arg->out.r.atts[i]), arg->mcxt, typeTup,
|
||||
exec_ctx->curr_proc->langid,
|
||||
@ -306,11 +306,12 @@ PLyDict_FromTuple(PLyTypeInfo *info, HeapTuple tuple, TupleDesc desc)
|
||||
Datum vattr;
|
||||
bool is_null;
|
||||
PyObject *value;
|
||||
Form_pg_attribute attr = TupleDescAttr(desc, i);
|
||||
|
||||
if (desc->attrs[i]->attisdropped)
|
||||
if (attr->attisdropped)
|
||||
continue;
|
||||
|
||||
key = NameStr(desc->attrs[i]->attname);
|
||||
key = NameStr(attr->attname);
|
||||
vattr = heap_getattr(tuple, (i + 1), desc, &is_null);
|
||||
|
||||
if (is_null || info->in.r.atts[i].func == NULL)
|
||||
@ -1183,15 +1184,16 @@ PLyMapping_ToComposite(PLyTypeInfo *info, TupleDesc desc, PyObject *mapping)
|
||||
char *key;
|
||||
PyObject *volatile value;
|
||||
PLyObToDatum *att;
|
||||
Form_pg_attribute attr = TupleDescAttr(desc, i);
|
||||
|
||||
if (desc->attrs[i]->attisdropped)
|
||||
if (attr->attisdropped)
|
||||
{
|
||||
values[i] = (Datum) 0;
|
||||
nulls[i] = true;
|
||||
continue;
|
||||
}
|
||||
|
||||
key = NameStr(desc->attrs[i]->attname);
|
||||
key = NameStr(attr->attname);
|
||||
value = NULL;
|
||||
att = &info->out.r.atts[i];
|
||||
PG_TRY();
|
||||
@ -1256,7 +1258,7 @@ PLySequence_ToComposite(PLyTypeInfo *info, TupleDesc desc, PyObject *sequence)
|
||||
idx = 0;
|
||||
for (i = 0; i < desc->natts; i++)
|
||||
{
|
||||
if (!desc->attrs[i]->attisdropped)
|
||||
if (!TupleDescAttr(desc, i)->attisdropped)
|
||||
idx++;
|
||||
}
|
||||
if (PySequence_Length(sequence) != idx)
|
||||
@ -1277,7 +1279,7 @@ PLySequence_ToComposite(PLyTypeInfo *info, TupleDesc desc, PyObject *sequence)
|
||||
PyObject *volatile value;
|
||||
PLyObToDatum *att;
|
||||
|
||||
if (desc->attrs[i]->attisdropped)
|
||||
if (TupleDescAttr(desc, i)->attisdropped)
|
||||
{
|
||||
values[i] = (Datum) 0;
|
||||
nulls[i] = true;
|
||||
@ -1346,15 +1348,16 @@ PLyGenericObject_ToComposite(PLyTypeInfo *info, TupleDesc desc, PyObject *object
|
||||
char *key;
|
||||
PyObject *volatile value;
|
||||
PLyObToDatum *att;
|
||||
Form_pg_attribute attr = TupleDescAttr(desc, i);
|
||||
|
||||
if (desc->attrs[i]->attisdropped)
|
||||
if (attr->attisdropped)
|
||||
{
|
||||
values[i] = (Datum) 0;
|
||||
nulls[i] = true;
|
||||
continue;
|
||||
}
|
||||
|
||||
key = NameStr(desc->attrs[i]->attname);
|
||||
key = NameStr(attr->attname);
|
||||
value = NULL;
|
||||
att = &info->out.r.atts[i];
|
||||
PG_TRY();
|
||||
|
@ -1106,11 +1106,13 @@ pltcl_trigger_handler(PG_FUNCTION_ARGS, pltcl_call_state *call_state,
|
||||
Tcl_ListObjAppendElement(NULL, tcl_trigtup, Tcl_NewObj());
|
||||
for (i = 0; i < tupdesc->natts; i++)
|
||||
{
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
|
||||
if (att->attisdropped)
|
||||
Tcl_ListObjAppendElement(NULL, tcl_trigtup, Tcl_NewObj());
|
||||
else
|
||||
Tcl_ListObjAppendElement(NULL, tcl_trigtup,
|
||||
Tcl_NewStringObj(utf_e2u(NameStr(tupdesc->attrs[i]->attname)), -1));
|
||||
Tcl_NewStringObj(utf_e2u(NameStr(att->attname)), -1));
|
||||
}
|
||||
Tcl_ListObjAppendElement(NULL, tcl_cmd, tcl_trigtup);
|
||||
|
||||
@ -2952,15 +2954,17 @@ pltcl_set_tuple_values(Tcl_Interp *interp, const char *arrayname,
|
||||
|
||||
for (i = 0; i < tupdesc->natts; i++)
|
||||
{
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
|
||||
/* ignore dropped attributes */
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
if (att->attisdropped)
|
||||
continue;
|
||||
|
||||
/************************************************************
|
||||
* Get the attribute name
|
||||
************************************************************/
|
||||
UTF_BEGIN;
|
||||
attname = pstrdup(UTF_E2U(NameStr(tupdesc->attrs[i]->attname)));
|
||||
attname = pstrdup(UTF_E2U(NameStr(att->attname)));
|
||||
UTF_END;
|
||||
|
||||
/************************************************************
|
||||
@ -2978,8 +2982,7 @@ pltcl_set_tuple_values(Tcl_Interp *interp, const char *arrayname,
|
||||
************************************************************/
|
||||
if (!isnull)
|
||||
{
|
||||
getTypeOutputInfo(tupdesc->attrs[i]->atttypid,
|
||||
&typoutput, &typisvarlena);
|
||||
getTypeOutputInfo(att->atttypid, &typoutput, &typisvarlena);
|
||||
outputstr = OidOutputFunctionCall(typoutput, attr);
|
||||
UTF_BEGIN;
|
||||
Tcl_SetVar2Ex(interp, *arrptr, *nameptr,
|
||||
@ -3013,14 +3016,16 @@ pltcl_build_tuple_argument(HeapTuple tuple, TupleDesc tupdesc)
|
||||
|
||||
for (i = 0; i < tupdesc->natts; i++)
|
||||
{
|
||||
Form_pg_attribute att = TupleDescAttr(tupdesc, i);
|
||||
|
||||
/* ignore dropped attributes */
|
||||
if (tupdesc->attrs[i]->attisdropped)
|
||||
if (att->attisdropped)
|
||||
continue;
|
||||
|
||||
/************************************************************
|
||||
* Get the attribute name
|
||||
************************************************************/
|
||||
attname = NameStr(tupdesc->attrs[i]->attname);
|
||||
attname = NameStr(att->attname);
|
||||
|
||||
/************************************************************
|
||||
* Get the attributes value
|
||||
@ -3037,7 +3042,7 @@ pltcl_build_tuple_argument(HeapTuple tuple, TupleDesc tupdesc)
|
||||
************************************************************/
|
||||
if (!isnull)
|
||||
{
|
||||
getTypeOutputInfo(tupdesc->attrs[i]->atttypid,
|
||||
getTypeOutputInfo(att->atttypid,
|
||||
&typoutput, &typisvarlena);
|
||||
outputstr = OidOutputFunctionCall(typoutput, attr);
|
||||
UTF_BEGIN;
|
||||
|
@ -770,9 +770,9 @@ make_tuple_indirect(PG_FUNCTION_ARGS)
|
||||
struct varatt_indirect redirect_pointer;
|
||||
|
||||
/* only work on existing, not-null varlenas */
|
||||
if (tupdesc->attrs[i]->attisdropped ||
|
||||
if (TupleDescAttr(tupdesc, i)->attisdropped ||
|
||||
nulls[i] ||
|
||||
tupdesc->attrs[i]->attlen != -1)
|
||||
TupleDescAttr(tupdesc, i)->attlen != -1)
|
||||
continue;
|
||||
|
||||
attr = (struct varlena *) DatumGetPointer(values[i]);
|
||||
|
Loading…
Reference in New Issue
Block a user