summaryrefslogtreecommitdiff
path: root/src/include/parser/parse_node.h
diff options
context:
space:
mode:
Diffstat (limited to 'src/include/parser/parse_node.h')
-rw-r--r--src/include/parser/parse_node.h57
1 files changed, 47 insertions, 10 deletions
diff --git a/src/include/parser/parse_node.h b/src/include/parser/parse_node.h
index 8e71b2ed5fc..d25819aa28b 100644
--- a/src/include/parser/parse_node.h
+++ b/src/include/parser/parse_node.h
@@ -19,6 +19,11 @@
#include "utils/relcache.h"
+/* Forward references for some structs declared below */
+typedef struct ParseState ParseState;
+typedef struct ParseNamespaceItem ParseNamespaceItem;
+typedef struct ParseNamespaceColumn ParseNamespaceColumn;
+
/*
* Expression kinds distinguished by transformExpr(). Many of these are not
* semantically distinct so far as expression transformation goes; rather,
@@ -79,8 +84,6 @@ typedef enum ParseExprKind
/*
* Function signatures for parser hooks
*/
-typedef struct ParseState ParseState;
-
typedef Node *(*PreParseColumnRefHook) (ParseState *pstate, ColumnRef *cref);
typedef Node *(*PostParseColumnRefHook) (ParseState *pstate, ColumnRef *cref, Node *var);
typedef Node *(*ParseParamRefHook) (ParseState *pstate, ParamRef *pref);
@@ -132,9 +135,7 @@ typedef Node *(*CoerceParamHook) (ParseState *pstate, Param *param,
*
* p_target_relation: target relation, if query is INSERT, UPDATE, or DELETE.
*
- * p_target_rangetblentry: target relation's entry in the rtable list.
- *
- * p_target_rtindex: target relation's index in the rtable list.
+ * p_target_nsitem: target relation's ParseNamespaceItem.
*
* p_is_insert: true to process assignment expressions like INSERT, false
* to process them like UPDATE. (Note this can change intra-statement, for
@@ -174,7 +175,7 @@ typedef Node *(*CoerceParamHook) (ParseState *pstate, Param *param,
*/
struct ParseState
{
- struct ParseState *parentParseState; /* stack link */
+ ParseState *parentParseState; /* stack link */
const char *p_sourcetext; /* source text, or NULL if not available */
List *p_rtable; /* range table so far */
List *p_joinexprs; /* JoinExprs for RTE_JOIN p_rtable entries */
@@ -187,8 +188,7 @@ struct ParseState
List *p_future_ctes; /* common table exprs not yet in namespace */
CommonTableExpr *p_parent_cte; /* this query's containing CTE */
Relation p_target_relation; /* INSERT/UPDATE/DELETE target rel */
- RangeTblEntry *p_target_rangetblentry; /* target rel's RTE, or NULL */
- int p_target_rtindex; /* target rel's RT index, or 0 */
+ ParseNamespaceItem *p_target_nsitem; /* target rel's NSItem, or NULL */
bool p_is_insert; /* process assignment like INSERT not UPDATE */
List *p_windowdefs; /* raw representations of window clauses */
ParseExprKind p_expr_kind; /* what kind of expression we're parsing */
@@ -225,6 +225,9 @@ struct ParseState
/*
* An element of a namespace list.
*
+ * The p_nscolumns array contains info showing how to construct Vars
+ * referencing corresponding elements of the RTE's colnames list.
+ *
* Namespace items with p_rel_visible set define which RTEs are accessible by
* qualified names, while those with p_cols_visible set define which RTEs are
* accessible by unqualified names. These sets are different because a JOIN
@@ -249,15 +252,49 @@ struct ParseState
* are more complicated than "must have different alias names", so in practice
* code searching a namespace list has to check for ambiguous references.
*/
-typedef struct ParseNamespaceItem
+struct ParseNamespaceItem
{
RangeTblEntry *p_rte; /* The relation's rangetable entry */
int p_rtindex; /* The relation's index in the rangetable */
+ /* array of same length as p_rte->eref->colnames: */
+ ParseNamespaceColumn *p_nscolumns; /* per-column data */
bool p_rel_visible; /* Relation name is visible? */
bool p_cols_visible; /* Column names visible as unqualified refs? */
bool p_lateral_only; /* Is only visible to LATERAL expressions? */
bool p_lateral_ok; /* If so, does join type allow use? */
-} ParseNamespaceItem;
+};
+
+/*
+ * Data about one column of a ParseNamespaceItem.
+ *
+ * We track the info needed to construct a Var referencing the column
+ * (but only for user-defined columns; system column references and
+ * whole-row references are handled separately).
+ *
+ * p_varno and p_varattno identify the semantic referent, which is a
+ * base-relation column unless the reference is to a join USING column that
+ * isn't semantically equivalent to either join input column (because it is a
+ * FULL join or the input column requires a type coercion). In those cases
+ * p_varno and p_varattno refer to the JOIN RTE.
+ *
+ * p_varnosyn and p_varattnosyn are either identical to p_varno/p_varattno,
+ * or they specify the column's position in an aliased JOIN RTE that hides
+ * the semantic referent RTE's refname. (That could be either the JOIN RTE
+ * in which this ParseNamespaceColumn entry exists, or some lower join level.)
+ *
+ * If an RTE contains a dropped column, its ParseNamespaceColumn struct
+ * is all-zeroes. (Conventionally, test for p_varno == 0 to detect this.)
+ */
+struct ParseNamespaceColumn
+{
+ Index p_varno; /* rangetable index */
+ AttrNumber p_varattno; /* attribute number of the column */
+ Oid p_vartype; /* pg_type OID */
+ int32 p_vartypmod; /* type modifier value */
+ Oid p_varcollid; /* OID of collation, or InvalidOid */
+ Index p_varnosyn; /* rangetable index of syntactic referent */
+ AttrNumber p_varattnosyn; /* attribute number of syntactic referent */
+};
/* Support for parser_errposition_callback function */
typedef struct ParseCallbackState