aboutsummaryrefslogtreecommitdiff
path: root/src/include/parser/parse_node.h
diff options
context:
space:
mode:
authorTom Lane <tgl@sss.pgh.pa.us>2012-08-07 19:02:54 -0400
committerTom Lane <tgl@sss.pgh.pa.us>2012-08-07 19:02:54 -0400
commit5ebaaa49445eb1ba7b299bbea3a477d4e4c0430b (patch)
tree1a72c939a655e9acbba1c71a1831dd38ee41db95 /src/include/parser/parse_node.h
parent5078be480412790e4f1b2aeda04f8c65fc7a3b93 (diff)
downloadpostgresql-5ebaaa49445eb1ba7b299bbea3a477d4e4c0430b.tar.gz
postgresql-5ebaaa49445eb1ba7b299bbea3a477d4e4c0430b.zip
Implement SQL-standard LATERAL subqueries.
This patch implements the standard syntax of LATERAL attached to a sub-SELECT in FROM, and also allows LATERAL attached to a function in FROM, since set-returning function calls are expected to be one of the principal use-cases. The main change here is a rewrite of the mechanism for keeping track of which relations are visible for column references while the FROM clause is being scanned. The parser "namespace" lists are no longer lists of bare RTEs, but are lists of ParseNamespaceItem structs, which carry an RTE pointer as well as some visibility-controlling flags. Aside from supporting LATERAL correctly, this lets us get rid of the ancient hacks that required rechecking subqueries and JOIN/ON and function-in-FROM expressions for invalid references after they were initially parsed. Invalid column references are now always correctly detected on sight. In passing, remove assorted parser error checks that are now dead code by virtue of our having gotten rid of add_missing_from, as well as some comments that are obsolete for the same reason. (It was mainly add_missing_from that caused so much fudging here in the first place.) The planner support for this feature is very minimal, and will be improved in future patches. It works well enough for testing purposes, though. catversion bump forced due to new field in RangeTblEntry.
Diffstat (limited to 'src/include/parser/parse_node.h')
-rw-r--r--src/include/parser/parse_node.h40
1 files changed, 26 insertions, 14 deletions
diff --git a/src/include/parser/parse_node.h b/src/include/parser/parse_node.h
index 670e0849936..13f745f6fa6 100644
--- a/src/include/parser/parse_node.h
+++ b/src/include/parser/parse_node.h
@@ -54,22 +54,25 @@ typedef Node *(*CoerceParamHook) (ParseState *pstate, Param *param,
* p_joinlist: list of join items (RangeTblRef and JoinExpr nodes) that
* will become the fromlist of the query's top-level FromExpr node.
*
- * p_relnamespace: list of RTEs that represents the current namespace for
- * table lookup, ie, those RTEs that are accessible by qualified names.
- * This may be just a subset of the rtable + joinlist, and/or may contain
- * entries that are not yet added to the main joinlist.
- *
- * p_varnamespace: list of RTEs that represents the current namespace for
- * column lookup, ie, those RTEs that are accessible by unqualified names.
- * This is different from p_relnamespace because a JOIN without an alias does
- * not hide the contained tables (so they must still be in p_relnamespace)
- * but it does hide their columns (unqualified references to the columns must
- * refer to the JOIN, not the member tables). Other special RTEs such as
- * NEW/OLD for rules may also appear in just one of these lists.
+ * p_relnamespace: list of ParseNamespaceItems that represents the current
+ * namespace for table lookup, ie, those RTEs that are accessible by
+ * qualified names. (This may be just a subset of the whole rtable.)
+ *
+ * p_varnamespace: list of ParseNamespaceItems that represents the current
+ * namespace for column lookup, ie, those RTEs that are accessible by
+ * unqualified names. This is different from p_relnamespace because a JOIN
+ * without an alias does not hide the contained tables (so they must be in
+ * p_relnamespace) but it does hide their columns (unqualified references to
+ * the columns must refer to the JOIN, not the member tables). Other special
+ * RTEs such as NEW/OLD for rules may also appear in just one of these lists.
+ *
+ * p_lateral_active: TRUE if we are currently parsing a LATERAL subexpression
+ * of this parse level. This makes p_lateral_only namespace items visible,
+ * whereas they are not visible when p_lateral_active is FALSE.
*
* p_ctenamespace: list of CommonTableExprs (WITH items) that are visible
- * at the moment. This is different from p_relnamespace because you have
- * to make an RTE before you can access a CTE.
+ * at the moment. This is entirely different from p_relnamespace because
+ * a CTE is not an RTE, rather "visibility" means you could make an RTE.
*
* p_future_ctes: list of CommonTableExprs (WITH items) that are not yet
* visible due to scope rules. This is used to help improve error messages.
@@ -93,6 +96,7 @@ struct ParseState
* node's fromlist) */
List *p_relnamespace; /* current namespace for relations */
List *p_varnamespace; /* current namespace for columns */
+ bool p_lateral_active; /* p_lateral_only items visible? */
List *p_ctenamespace; /* current namespace for common table exprs */
List *p_future_ctes; /* common table exprs not yet in namespace */
CommonTableExpr *p_parent_cte; /* this query's containing CTE */
@@ -121,6 +125,14 @@ struct ParseState
void *p_ref_hook_state; /* common passthrough link for above */
};
+/* An element of p_relnamespace or p_varnamespace */
+typedef struct ParseNamespaceItem
+{
+ RangeTblEntry *p_rte; /* The relation's rangetable entry */
+ bool p_lateral_only; /* Is only visible to LATERAL expressions? */
+ bool p_lateral_ok; /* If so, does join type allow use? */
+} ParseNamespaceItem;
+
/* Support for parser_errposition_callback function */
typedef struct ParseCallbackState
{