PostgreSQL Source Code  git master
parsetree.h File Reference
#include "nodes/parsenodes.h"
Include dependency graph for parsetree.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Macros

#define rt_fetch(rangetable_index, rangetable)   ((RangeTblEntry *) list_nth(rangetable, (rangetable_index)-1))
 

Functions

char * get_rte_attribute_name (RangeTblEntry *rte, AttrNumber attnum)
 
void get_rte_attribute_type (RangeTblEntry *rte, AttrNumber attnum, Oid *vartype, int32 *vartypmod, Oid *varcollid)
 
bool get_rte_attribute_is_dropped (RangeTblEntry *rte, AttrNumber attnum)
 
TargetEntryget_tle_by_resno (List *tlist, AttrNumber resno)
 
RowMarkClauseget_parse_rowmark (Query *qry, Index rtindex)
 

Macro Definition Documentation

◆ rt_fetch

#define rt_fetch (   rangetable_index,
  rangetable 
)    ((RangeTblEntry *) list_nth(rangetable, (rangetable_index)-1))

Function Documentation

◆ get_parse_rowmark()

RowMarkClause* get_parse_rowmark ( Query qry,
Index  rtindex 
)

Definition at line 3119 of file parse_relation.c.

References lfirst, Query::rowMarks, and RowMarkClause::rti.

Referenced by AcquireRewriteLocks(), applyLockingClause(), and ApplyRetrieveRule().

3120 {
3121  ListCell *l;
3122 
3123  foreach(l, qry->rowMarks)
3124  {
3125  RowMarkClause *rc = (RowMarkClause *) lfirst(l);
3126 
3127  if (rc->rti == rtindex)
3128  return rc;
3129  }
3130  return NULL;
3131 }
List * rowMarks
Definition: parsenodes.h:163
#define lfirst(lc)
Definition: pg_list.h:190

◆ get_rte_attribute_is_dropped()

bool get_rte_attribute_is_dropped ( RangeTblEntry rte,
AttrNumber  attnum 
)

Definition at line 2955 of file parse_relation.c.

References Alias::aliasname, Assert, ATTNUM, RangeTblEntry::coltypes, elog, RangeTblEntry::eref, ereport, errcode(), errmsg(), ERROR, RangeTblFunction::funccolcount, RangeTblFunction::funcexpr, RangeTblEntry::funcordinality, RangeTblEntry::functions, get_expr_result_tupdesc(), GETSTRUCT, HeapTupleIsValid, Int16GetDatum, RangeTblEntry::joinaliasvars, lfirst, list_length(), list_nth(), list_nth_oid(), ObjectIdGetDatum, OidIsValid, ReleaseSysCache(), RangeTblEntry::relid, RTE_CTE, RTE_FUNCTION, RTE_JOIN, RTE_NAMEDTUPLESTORE, RTE_RELATION, RTE_RESULT, RTE_SUBQUERY, RTE_TABLEFUNC, RTE_VALUES, RangeTblEntry::rtekind, SearchSysCache2(), and TupleDescAttr.

Referenced by AcquireRewriteLocks().

2956 {
2957  bool result;
2958 
2959  switch (rte->rtekind)
2960  {
2961  case RTE_RELATION:
2962  {
2963  /*
2964  * Plain relation RTE --- get the attribute's catalog entry
2965  */
2966  HeapTuple tp;
2967  Form_pg_attribute att_tup;
2968 
2969  tp = SearchSysCache2(ATTNUM,
2970  ObjectIdGetDatum(rte->relid),
2972  if (!HeapTupleIsValid(tp)) /* shouldn't happen */
2973  elog(ERROR, "cache lookup failed for attribute %d of relation %u",
2974  attnum, rte->relid);
2975  att_tup = (Form_pg_attribute) GETSTRUCT(tp);
2976  result = att_tup->attisdropped;
2977  ReleaseSysCache(tp);
2978  }
2979  break;
2980  case RTE_SUBQUERY:
2981  case RTE_TABLEFUNC:
2982  case RTE_VALUES:
2983  case RTE_CTE:
2984 
2985  /*
2986  * Subselect, Table Functions, Values, CTE RTEs never have dropped
2987  * columns
2988  */
2989  result = false;
2990  break;
2991  case RTE_NAMEDTUPLESTORE:
2992  {
2993  /* Check dropped-ness by testing for valid coltype */
2994  if (attnum <= 0 ||
2995  attnum > list_length(rte->coltypes))
2996  elog(ERROR, "invalid varattno %d", attnum);
2997  result = !OidIsValid((list_nth_oid(rte->coltypes, attnum - 1)));
2998  }
2999  break;
3000  case RTE_JOIN:
3001  {
3002  /*
3003  * A join RTE would not have dropped columns when constructed,
3004  * but one in a stored rule might contain columns that were
3005  * dropped from the underlying tables, if said columns are
3006  * nowhere explicitly referenced in the rule. This will be
3007  * signaled to us by a null pointer in the joinaliasvars list.
3008  */
3009  Var *aliasvar;
3010 
3011  if (attnum <= 0 ||
3013  elog(ERROR, "invalid varattno %d", attnum);
3014  aliasvar = (Var *) list_nth(rte->joinaliasvars, attnum - 1);
3015 
3016  result = (aliasvar == NULL);
3017  }
3018  break;
3019  case RTE_FUNCTION:
3020  {
3021  /* Function RTE */
3022  ListCell *lc;
3023  int atts_done = 0;
3024 
3025  /*
3026  * Dropped attributes are only possible with functions that
3027  * return named composite types. In such a case we have to
3028  * look up the result type to see if it currently has this
3029  * column dropped. So first, loop over the funcs until we
3030  * find the one that covers the requested column.
3031  */
3032  foreach(lc, rte->functions)
3033  {
3034  RangeTblFunction *rtfunc = (RangeTblFunction *) lfirst(lc);
3035 
3036  if (attnum > atts_done &&
3037  attnum <= atts_done + rtfunc->funccolcount)
3038  {
3039  TupleDesc tupdesc;
3040 
3041  tupdesc = get_expr_result_tupdesc(rtfunc->funcexpr,
3042  true);
3043  if (tupdesc)
3044  {
3045  /* Composite data type, e.g. a table's row type */
3046  Form_pg_attribute att_tup;
3047 
3048  Assert(tupdesc);
3049  Assert(attnum - atts_done <= tupdesc->natts);
3050  att_tup = TupleDescAttr(tupdesc,
3051  attnum - atts_done - 1);
3052  return att_tup->attisdropped;
3053  }
3054  /* Otherwise, it can't have any dropped columns */
3055  return false;
3056  }
3057  atts_done += rtfunc->funccolcount;
3058  }
3059 
3060  /* If we get here, must be looking for the ordinality column */
3061  if (rte->funcordinality && attnum == atts_done + 1)
3062  return false;
3063 
3064  /* this probably can't happen ... */
3065  ereport(ERROR,
3066  (errcode(ERRCODE_UNDEFINED_COLUMN),
3067  errmsg("column %d of relation \"%s\" does not exist",
3068  attnum,
3069  rte->eref->aliasname)));
3070  result = false; /* keep compiler quiet */
3071  }
3072  break;
3073  case RTE_RESULT:
3074  /* this probably can't happen ... */
3075  ereport(ERROR,
3076  (errcode(ERRCODE_UNDEFINED_COLUMN),
3077  errmsg("column %d of relation \"%s\" does not exist",
3078  attnum,
3079  rte->eref->aliasname)));
3080  result = false; /* keep compiler quiet */
3081  break;
3082  default:
3083  elog(ERROR, "unrecognized RTE kind: %d", (int) rte->rtekind);
3084  result = false; /* keep compiler quiet */
3085  }
3086 
3087  return result;
3088 }
List * joinaliasvars
Definition: parsenodes.h:1030
#define GETSTRUCT(TUP)
Definition: htup_details.h:655
#define TupleDescAttr(tupdesc, i)
Definition: tupdesc.h:92
#define Int16GetDatum(X)
Definition: postgres.h:451
int errcode(int sqlerrcode)
Definition: elog.c:570
bool funcordinality
Definition: parsenodes.h:1041
Definition: primnodes.h:167
#define OidIsValid(objectId)
Definition: c.h:638
static Oid list_nth_oid(const List *list, int n)
Definition: pg_list.h:299
#define ObjectIdGetDatum(X)
Definition: postgres.h:507
#define ERROR
Definition: elog.h:43
TupleDesc get_expr_result_tupdesc(Node *expr, bool noError)
Definition: funcapi.c:397
static void * list_nth(const List *list, int n)
Definition: pg_list.h:277
FormData_pg_attribute * Form_pg_attribute
Definition: pg_attribute.h:200
#define ereport(elevel, rest)
Definition: elog.h:141
void ReleaseSysCache(HeapTuple tuple)
Definition: syscache.c:1172
int16 attnum
Definition: pg_attribute.h:79
#define HeapTupleIsValid(tuple)
Definition: htup.h:78
#define Assert(condition)
Definition: c.h:732
#define lfirst(lc)
Definition: pg_list.h:190
char * aliasname
Definition: primnodes.h:42
List * functions
Definition: parsenodes.h:1040
static int list_length(const List *l)
Definition: pg_list.h:169
HeapTuple SearchSysCache2(int cacheId, Datum key1, Datum key2)
Definition: syscache.c:1135
RTEKind rtekind
Definition: parsenodes.h:974
int errmsg(const char *fmt,...)
Definition: elog.c:784
#define elog(elevel,...)
Definition: elog.h:226
Alias * eref
Definition: parsenodes.h:1092
List * coltypes
Definition: parsenodes.h:1078

◆ get_rte_attribute_name()

char* get_rte_attribute_name ( RangeTblEntry rte,
AttrNumber  attnum 
)

Definition at line 2719 of file parse_relation.c.

References RangeTblEntry::alias, Alias::aliasname, Alias::colnames, elog, RangeTblEntry::eref, ERROR, get_attname(), InvalidAttrNumber, list_length(), list_nth(), RangeTblEntry::relid, RTE_RELATION, RangeTblEntry::rtekind, and strVal.

Referenced by check_ungrouped_columns_walker(), get_name_for_var_field(), get_variable(), and print_expr().

2720 {
2721  if (attnum == InvalidAttrNumber)
2722  return "*";
2723 
2724  /*
2725  * If there is a user-written column alias, use it.
2726  */
2727  if (rte->alias &&
2728  attnum > 0 && attnum <= list_length(rte->alias->colnames))
2729  return strVal(list_nth(rte->alias->colnames, attnum - 1));
2730 
2731  /*
2732  * If the RTE is a relation, go to the system catalogs not the
2733  * eref->colnames list. This is a little slower but it will give the
2734  * right answer if the column has been renamed since the eref list was
2735  * built (which can easily happen for rules).
2736  */
2737  if (rte->rtekind == RTE_RELATION)
2738  return get_attname(rte->relid, attnum, false);
2739 
2740  /*
2741  * Otherwise use the column name from eref. There should always be one.
2742  */
2743  if (attnum > 0 && attnum <= list_length(rte->eref->colnames))
2744  return strVal(list_nth(rte->eref->colnames, attnum - 1));
2745 
2746  /* else caller gave us a bogus attnum */
2747  elog(ERROR, "invalid attnum %d for rangetable entry %s",
2748  attnum, rte->eref->aliasname);
2749  return NULL; /* keep compiler quiet */
2750 }
Alias * alias
Definition: parsenodes.h:1091
List * colnames
Definition: primnodes.h:43
#define strVal(v)
Definition: value.h:54
#define ERROR
Definition: elog.h:43
static void * list_nth(const List *list, int n)
Definition: pg_list.h:277
int16 attnum
Definition: pg_attribute.h:79
char * aliasname
Definition: primnodes.h:42
static int list_length(const List *l)
Definition: pg_list.h:169
#define InvalidAttrNumber
Definition: attnum.h:23
RTEKind rtekind
Definition: parsenodes.h:974
#define elog(elevel,...)
Definition: elog.h:226
char * get_attname(Oid relid, AttrNumber attnum, bool missing_ok)
Definition: lsyscache.c:775
Alias * eref
Definition: parsenodes.h:1092

◆ get_rte_attribute_type()

void get_rte_attribute_type ( RangeTblEntry rte,
AttrNumber  attnum,
Oid vartype,
int32 vartypmod,
Oid varcollid 
)

Definition at line 2757 of file parse_relation.c.

References Alias::aliasname, Assert, ATTNUM, RangeTblEntry::colcollations, RangeTblEntry::coltypes, RangeTblEntry::coltypmods, elog, RangeTblEntry::eref, ereport, errcode(), errmsg(), ERROR, TargetEntry::expr, exprCollation(), exprType(), exprTypmod(), RangeTblFunction::funccolcollations, RangeTblFunction::funccolcount, RangeTblFunction::funccoltypes, RangeTblFunction::funccoltypmods, RangeTblFunction::funcexpr, RangeTblEntry::funcordinality, RangeTblEntry::functions, get_expr_result_type(), get_rel_name(), get_tle_by_resno(), GETSTRUCT, HeapTupleIsValid, Int16GetDatum, InvalidOid, RangeTblEntry::joinaliasvars, lfirst, list_length(), list_nth(), list_nth_int(), list_nth_oid(), NameStr, ObjectIdGetDatum, OidIsValid, ReleaseSysCache(), RangeTblEntry::relid, TargetEntry::resjunk, RTE_CTE, RTE_FUNCTION, RTE_JOIN, RTE_NAMEDTUPLESTORE, RTE_RELATION, RTE_RESULT, RTE_SUBQUERY, RTE_TABLEFUNC, RTE_VALUES, RangeTblEntry::rtekind, SearchSysCache2(), RangeTblEntry::subquery, Query::targetList, TupleDescAttr, TYPEFUNC_COMPOSITE, TYPEFUNC_COMPOSITE_DOMAIN, TYPEFUNC_RECORD, and TYPEFUNC_SCALAR.

Referenced by make_var().

2759 {
2760  switch (rte->rtekind)
2761  {
2762  case RTE_RELATION:
2763  {
2764  /* Plain relation RTE --- get the attribute's type info */
2765  HeapTuple tp;
2766  Form_pg_attribute att_tup;
2767 
2768  tp = SearchSysCache2(ATTNUM,
2769  ObjectIdGetDatum(rte->relid),
2771  if (!HeapTupleIsValid(tp)) /* shouldn't happen */
2772  elog(ERROR, "cache lookup failed for attribute %d of relation %u",
2773  attnum, rte->relid);
2774  att_tup = (Form_pg_attribute) GETSTRUCT(tp);
2775 
2776  /*
2777  * If dropped column, pretend it ain't there. See notes in
2778  * scanRTEForColumn.
2779  */
2780  if (att_tup->attisdropped)
2781  ereport(ERROR,
2782  (errcode(ERRCODE_UNDEFINED_COLUMN),
2783  errmsg("column \"%s\" of relation \"%s\" does not exist",
2784  NameStr(att_tup->attname),
2785  get_rel_name(rte->relid))));
2786  *vartype = att_tup->atttypid;
2787  *vartypmod = att_tup->atttypmod;
2788  *varcollid = att_tup->attcollation;
2789  ReleaseSysCache(tp);
2790  }
2791  break;
2792  case RTE_SUBQUERY:
2793  {
2794  /* Subselect RTE --- get type info from subselect's tlist */
2796  attnum);
2797 
2798  if (te == NULL || te->resjunk)
2799  elog(ERROR, "subquery %s does not have attribute %d",
2800  rte->eref->aliasname, attnum);
2801  *vartype = exprType((Node *) te->expr);
2802  *vartypmod = exprTypmod((Node *) te->expr);
2803  *varcollid = exprCollation((Node *) te->expr);
2804  }
2805  break;
2806  case RTE_FUNCTION:
2807  {
2808  /* Function RTE */
2809  ListCell *lc;
2810  int atts_done = 0;
2811 
2812  /* Identify which function covers the requested column */
2813  foreach(lc, rte->functions)
2814  {
2815  RangeTblFunction *rtfunc = (RangeTblFunction *) lfirst(lc);
2816 
2817  if (attnum > atts_done &&
2818  attnum <= atts_done + rtfunc->funccolcount)
2819  {
2820  TypeFuncClass functypclass;
2821  Oid funcrettype;
2822  TupleDesc tupdesc;
2823 
2824  attnum -= atts_done; /* now relative to this func */
2825  functypclass = get_expr_result_type(rtfunc->funcexpr,
2826  &funcrettype,
2827  &tupdesc);
2828 
2829  if (functypclass == TYPEFUNC_COMPOSITE ||
2830  functypclass == TYPEFUNC_COMPOSITE_DOMAIN)
2831  {
2832  /* Composite data type, e.g. a table's row type */
2833  Form_pg_attribute att_tup;
2834 
2835  Assert(tupdesc);
2836  Assert(attnum <= tupdesc->natts);
2837  att_tup = TupleDescAttr(tupdesc, attnum - 1);
2838 
2839  /*
2840  * If dropped column, pretend it ain't there. See
2841  * notes in scanRTEForColumn.
2842  */
2843  if (att_tup->attisdropped)
2844  ereport(ERROR,
2845  (errcode(ERRCODE_UNDEFINED_COLUMN),
2846  errmsg("column \"%s\" of relation \"%s\" does not exist",
2847  NameStr(att_tup->attname),
2848  rte->eref->aliasname)));
2849  *vartype = att_tup->atttypid;
2850  *vartypmod = att_tup->atttypmod;
2851  *varcollid = att_tup->attcollation;
2852  }
2853  else if (functypclass == TYPEFUNC_SCALAR)
2854  {
2855  /* Base data type, i.e. scalar */
2856  *vartype = funcrettype;
2857  *vartypmod = -1;
2858  *varcollid = exprCollation(rtfunc->funcexpr);
2859  }
2860  else if (functypclass == TYPEFUNC_RECORD)
2861  {
2862  *vartype = list_nth_oid(rtfunc->funccoltypes,
2863  attnum - 1);
2864  *vartypmod = list_nth_int(rtfunc->funccoltypmods,
2865  attnum - 1);
2866  *varcollid = list_nth_oid(rtfunc->funccolcollations,
2867  attnum - 1);
2868  }
2869  else
2870  {
2871  /*
2872  * addRangeTableEntryForFunction should've caught
2873  * this
2874  */
2875  elog(ERROR, "function in FROM has unsupported return type");
2876  }
2877  return;
2878  }
2879  atts_done += rtfunc->funccolcount;
2880  }
2881 
2882  /* If we get here, must be looking for the ordinality column */
2883  if (rte->funcordinality && attnum == atts_done + 1)
2884  {
2885  *vartype = INT8OID;
2886  *vartypmod = -1;
2887  *varcollid = InvalidOid;
2888  return;
2889  }
2890 
2891  /* this probably can't happen ... */
2892  ereport(ERROR,
2893  (errcode(ERRCODE_UNDEFINED_COLUMN),
2894  errmsg("column %d of relation \"%s\" does not exist",
2895  attnum,
2896  rte->eref->aliasname)));
2897  }
2898  break;
2899  case RTE_JOIN:
2900  {
2901  /*
2902  * Join RTE --- get type info from join RTE's alias variable
2903  */
2904  Node *aliasvar;
2905 
2906  Assert(attnum > 0 && attnum <= list_length(rte->joinaliasvars));
2907  aliasvar = (Node *) list_nth(rte->joinaliasvars, attnum - 1);
2908  Assert(aliasvar != NULL);
2909  *vartype = exprType(aliasvar);
2910  *vartypmod = exprTypmod(aliasvar);
2911  *varcollid = exprCollation(aliasvar);
2912  }
2913  break;
2914  case RTE_TABLEFUNC:
2915  case RTE_VALUES:
2916  case RTE_CTE:
2917  case RTE_NAMEDTUPLESTORE:
2918  {
2919  /*
2920  * tablefunc, VALUES, CTE, or ENR RTE --- get type info from
2921  * lists in the RTE
2922  */
2923  Assert(attnum > 0 && attnum <= list_length(rte->coltypes));
2924  *vartype = list_nth_oid(rte->coltypes, attnum - 1);
2925  *vartypmod = list_nth_int(rte->coltypmods, attnum - 1);
2926  *varcollid = list_nth_oid(rte->colcollations, attnum - 1);
2927 
2928  /* For ENR, better check for dropped column */
2929  if (!OidIsValid(*vartype))
2930  ereport(ERROR,
2931  (errcode(ERRCODE_UNDEFINED_COLUMN),
2932  errmsg("column %d of relation \"%s\" does not exist",
2933  attnum,
2934  rte->eref->aliasname)));
2935  }
2936  break;
2937  case RTE_RESULT:
2938  /* this probably can't happen ... */
2939  ereport(ERROR,
2940  (errcode(ERRCODE_UNDEFINED_COLUMN),
2941  errmsg("column %d of relation \"%s\" does not exist",
2942  attnum,
2943  rte->eref->aliasname)));
2944  break;
2945  default:
2946  elog(ERROR, "unrecognized RTE kind: %d", (int) rte->rtekind);
2947  }
2948 }
List * joinaliasvars
Definition: parsenodes.h:1030
#define GETSTRUCT(TUP)
Definition: htup_details.h:655
int32 exprTypmod(const Node *expr)
Definition: nodeFuncs.c:276
#define TupleDescAttr(tupdesc, i)
Definition: tupdesc.h:92
List * coltypmods
Definition: parsenodes.h:1079
#define Int16GetDatum(X)
Definition: postgres.h:451
Definition: nodes.h:525
int errcode(int sqlerrcode)
Definition: elog.c:570
bool funcordinality
Definition: parsenodes.h:1041
unsigned int Oid
Definition: postgres_ext.h:31
TypeFuncClass get_expr_result_type(Node *expr, Oid *resultTypeId, TupleDesc *resultTupleDesc)
Definition: funcapi.c:212
#define OidIsValid(objectId)
Definition: c.h:638
static int list_nth_int(const List *list, int n)
Definition: pg_list.h:288
List * colcollations
Definition: parsenodes.h:1080
List * targetList
Definition: parsenodes.h:140
static Oid list_nth_oid(const List *list, int n)
Definition: pg_list.h:299
bool resjunk
Definition: primnodes.h:1400
#define ObjectIdGetDatum(X)
Definition: postgres.h:507
#define ERROR
Definition: elog.h:43
static void * list_nth(const List *list, int n)
Definition: pg_list.h:277
FormData_pg_attribute * Form_pg_attribute
Definition: pg_attribute.h:200
TypeFuncClass
Definition: funcapi.h:147
#define ereport(elevel, rest)
Definition: elog.h:141
void ReleaseSysCache(HeapTuple tuple)
Definition: syscache.c:1172
#define InvalidOid
Definition: postgres_ext.h:36
List * funccoltypmods
Definition: parsenodes.h:1130
int16 attnum
Definition: pg_attribute.h:79
List * funccolcollations
Definition: parsenodes.h:1131
#define HeapTupleIsValid(tuple)
Definition: htup.h:78
#define Assert(condition)
Definition: c.h:732
#define lfirst(lc)
Definition: pg_list.h:190
char * aliasname
Definition: primnodes.h:42
List * functions
Definition: parsenodes.h:1040
Expr * expr
Definition: primnodes.h:1393
Oid exprType(const Node *expr)
Definition: nodeFuncs.c:42
static int list_length(const List *l)
Definition: pg_list.h:169
Oid exprCollation(const Node *expr)
Definition: nodeFuncs.c:720
HeapTuple SearchSysCache2(int cacheId, Datum key1, Datum key2)
Definition: syscache.c:1135
RTEKind rtekind
Definition: parsenodes.h:974
Query * subquery
Definition: parsenodes.h:1009
int errmsg(const char *fmt,...)
Definition: elog.c:784
#define elog(elevel,...)
Definition: elog.h:226
TargetEntry * get_tle_by_resno(List *tlist, AttrNumber resno)
#define NameStr(name)
Definition: c.h:609
Alias * eref
Definition: parsenodes.h:1092
List * coltypes
Definition: parsenodes.h:1078
char * get_rel_name(Oid relid)
Definition: lsyscache.c:1730

◆ get_tle_by_resno()