Partially restore qual scope checks in distribute_qual_to_rels().

The LATERAL implementation is now basically complete, and I still don't
see a cost-effective way to make an exact qual scope cross-check in the
presence of LATERAL.  However, I did add a PlannerInfo.hasLateralRTEs flag
along the way, so it's easy to make the check only when not hasLateralRTEs.
That seems to still be useful, and it beats having no check at all.
This commit is contained in:
Tom Lane 2012-08-31 18:57:12 -04:00
parent da3df99870
commit c97a547a4a
1 changed files with 13 additions and 15 deletions

View File

@ -1103,21 +1103,20 @@ distribute_qual_to_rels(PlannerInfo *root, Node *clause,
relids = pull_varnos(clause);
/*
* Cross-check: clause should contain no relids not within its scope.
* Otherwise the parser messed up.
* Normally relids is a subset of qualscope, and we like to check that
* here as a crosscheck on the parser and rewriter. That need not be the
* case when there are LATERAL RTEs, however: the clause could contain
* references to rels outside its syntactic scope as a consequence of
* pull-up of such references from a LATERAL subquery below it. So, only
* check if the query contains no LATERAL RTEs.
*
* XXX temporarily disable the qualscope cross-check, which tends to
* reject quals pulled up from LATERAL subqueries. This is only in the
* nature of a debugging crosscheck anyway. I'm loath to remove it
* permanently, but need to think a bit harder about how to replace it.
* See also disabled Assert below. (The ojscope test is still okay
* because we prevent pullup of LATERAL subqueries that might cause it to
* be violated.)
* However, if it's an outer-join clause, we always insist that relids be
* a subset of ojscope. This is safe because is_simple_subquery()
* disallows pullup of LATERAL subqueries that could cause the restriction
* to be violated.
*/
#ifdef NOT_USED
if (!bms_is_subset(relids, qualscope))
if (!root->hasLateralRTEs && !bms_is_subset(relids, qualscope))
elog(ERROR, "JOIN qualification cannot refer to other relations");
#endif
if (ojscope && !bms_is_subset(relids, ojscope))
elog(ERROR, "JOIN qualification cannot refer to other relations");
@ -1272,9 +1271,8 @@ distribute_qual_to_rels(PlannerInfo *root, Node *clause,
if (outerjoin_delayed)
{
/* Should still be a subset of current scope ... */
#ifdef NOT_USED /* XXX temporarily disabled for LATERAL */
Assert(bms_is_subset(relids, qualscope));
#endif
Assert(root->hasLateralRTEs || bms_is_subset(relids, qualscope));
Assert(ojscope == NULL || bms_is_subset(relids, ojscope));
/*
* Because application of the qual will be delayed by outer join,