diff options
Diffstat (limited to 'src/backend/optimizer/util/clauses.c')
-rw-r--r-- | src/backend/optimizer/util/clauses.c | 39 |
1 files changed, 25 insertions, 14 deletions
diff --git a/src/backend/optimizer/util/clauses.c b/src/backend/optimizer/util/clauses.c index 317c10c2b9f..33790a4f463 100644 --- a/src/backend/optimizer/util/clauses.c +++ b/src/backend/optimizer/util/clauses.c @@ -31,6 +31,7 @@ #include "funcapi.h" #include "miscadmin.h" #include "nodes/makefuncs.h" +#include "nodes/multibitmapset.h" #include "nodes/nodeFuncs.h" #include "nodes/subscripting.h" #include "nodes/supportnodes.h" @@ -1566,7 +1567,7 @@ find_nonnullable_rels_walker(Node *node, bool top_level) * find_nonnullable_vars * Determine which Vars are forced nonnullable by given clause. * - * Returns a list of all level-zero Vars that are referenced in the clause in + * Returns the set of all level-zero Vars that are referenced in the clause in * such a way that the clause cannot possibly return TRUE if any of these Vars * is NULL. (It is OK to err on the side of conservatism; hence the analysis * here is simplistic.) @@ -1578,8 +1579,9 @@ find_nonnullable_rels_walker(Node *node, bool top_level) * the expression to have been AND/OR flattened and converted to implicit-AND * format. * - * The result is a palloc'd List, but we have not copied the member Var nodes. - * Also, we don't bother trying to eliminate duplicate entries. + * Attnos of the identified Vars are returned in a multibitmapset (a List of + * Bitmapsets). List indexes correspond to relids (varnos), while the per-rel + * Bitmapsets hold varattnos offset by FirstLowInvalidHeapAttributeNumber. * * top_level is true while scanning top-level AND/OR structure; here, showing * the result is either FALSE or NULL is good enough. top_level is false when @@ -1608,7 +1610,9 @@ find_nonnullable_vars_walker(Node *node, bool top_level) Var *var = (Var *) node; if (var->varlevelsup == 0) - result = list_make1(var); + result = mbms_add_member(result, + var->varno, + var->varattno - FirstLowInvalidHeapAttributeNumber); } else if (IsA(node, List)) { @@ -1623,9 +1627,9 @@ find_nonnullable_vars_walker(Node *node, bool top_level) */ foreach(l, (List *) node) { - result = list_concat(result, - find_nonnullable_vars_walker(lfirst(l), - top_level)); + result = mbms_add_members(result, + find_nonnullable_vars_walker(lfirst(l), + top_level)); } } else if (IsA(node, FuncExpr)) @@ -1657,7 +1661,12 @@ find_nonnullable_vars_walker(Node *node, bool top_level) switch (expr->boolop) { case AND_EXPR: - /* At top level we can just recurse (to the List case) */ + + /* + * At top level we can just recurse (to the List case), since + * the result should be the union of what we can prove in each + * arm. + */ if (top_level) { result = find_nonnullable_vars_walker((Node *) expr->args, @@ -1689,7 +1698,7 @@ find_nonnullable_vars_walker(Node *node, bool top_level) if (result == NIL) /* first subresult? */ result = subresult; else - result = list_intersection(result, subresult); + result = mbms_int_members(result, subresult); /* * If the intersection is empty, we can stop looking. This @@ -1788,8 +1797,8 @@ find_nonnullable_vars_walker(Node *node, bool top_level) * side of conservatism; hence the analysis here is simplistic. In fact, * we only detect simple "var IS NULL" tests at the top level.) * - * The result is a palloc'd List, but we have not copied the member Var nodes. - * Also, we don't bother trying to eliminate duplicate entries. + * As with find_nonnullable_vars, we return the varattnos of the identified + * Vars in a multibitmapset. */ List * find_forced_null_vars(Node *node) @@ -1804,7 +1813,9 @@ find_forced_null_vars(Node *node) var = find_forced_null_var(node); if (var) { - result = list_make1(var); + result = mbms_add_member(result, + var->varno, + var->varattno - FirstLowInvalidHeapAttributeNumber); } /* Otherwise, handle AND-conditions */ else if (IsA(node, List)) @@ -1815,8 +1826,8 @@ find_forced_null_vars(Node *node) */ foreach(l, (List *) node) { - result = list_concat(result, - find_forced_null_vars(lfirst(l))); + result = mbms_add_members(result, + find_forced_null_vars((Node *) lfirst(l))); } } else if (IsA(node, BoolExpr)) |