*** plancat.c.orig 2007-04-30 12:17:55.785145396 -0400 --- plancat.c 2007-04-30 14:15:48.093639183 -0400 *************** *** 473,478 **** --- 473,479 ---- List *constraint_pred; List *safe_constraints; ListCell *lc; + bool found_unsafe_restrictions; /* Skip the test if constraint exclusion is disabled */ if (!constraint_exclusion) *************** *** 486,491 **** --- 487,493 ---- * Note: strip off RestrictInfo because predicate_refuted_by() isn't * expecting to see any in its predicate argument. */ + found_unsafe_restrictions = false; safe_restrictions = NIL; foreach(lc, rel->baserestrictinfo) { *************** *** 493,498 **** --- 495,502 ---- if (!contain_mutable_functions((Node *) rinfo->clause)) safe_restrictions = lappend(safe_restrictions, rinfo->clause); + else + found_unsafe_restrictions = true; } if (predicate_refuted_by(safe_restrictions, safe_restrictions)) *************** *** 522,527 **** --- 526,559 ---- } /* + * Check the restrictions against the relation constraints. + * If we found mutable functions in the restrictions, try to simplify + * them prior to checking. Effectively, this folds stable and immutable + * functions into constant values. + */ + if (found_unsafe_restrictions) + { + List * simp_restrictions = NIL; + foreach(lc, rel->baserestrictinfo) + { + RestrictInfo *rinfo = (RestrictInfo *) lfirst(lc); + Node * baseNode = (Node *) rinfo->clause; + + if (IsA(baseNode, FuncExpr) || IsA(baseNode, OpExpr)) + { + Node * simpNode = estimate_expression_value(baseNode); + simp_restrictions = lappend(simp_restrictions, simpNode); + } + else + { + simp_restrictions = lappend(simp_restrictions, baseNode); + } + } + + if (predicate_refuted_by(safe_constraints, simp_restrictions)) + return true; + } + /* * The constraints are effectively ANDed together, so we can just try to * refute the entire collection at once. This may allow us to make proofs * that would fail if we took them individually. *************** *** 531,538 **** * have volatile and nonvolatile subclauses, and it's OK to make * deductions with the nonvolatile parts. */ ! if (predicate_refuted_by(safe_constraints, rel->baserestrictinfo)) return true; return false; } --- 563,572 ---- * have volatile and nonvolatile subclauses, and it's OK to make * deductions with the nonvolatile parts. */ ! else if (predicate_refuted_by(safe_constraints, rel->baserestrictinfo)) ! { return true; + } return false; }