aboutsummaryrefslogtreecommitdiff
path: root/src/backend/rewrite/rewriteHandler.c
diff options
context:
space:
mode:
authorTom Lane <tgl@sss.pgh.pa.us>2000-04-20 00:31:49 +0000
committerTom Lane <tgl@sss.pgh.pa.us>2000-04-20 00:31:49 +0000
commit7c22d2e5f09ec325eb796ac2817e6362104e8218 (patch)
tree87c48baeaa3f4c5839ecf9061643e1c96d075856 /src/backend/rewrite/rewriteHandler.c
parent0156fdf9a5b763b21cce51e4374e20e4d0ed4c53 (diff)
downloadpostgresql-7c22d2e5f09ec325eb796ac2817e6362104e8218.tar.gz
postgresql-7c22d2e5f09ec325eb796ac2817e6362104e8218.zip
Correct error in rewriter that caused SELECT count(*) FROM view
to give wrong results: it should be looking at inJoinSet not inFromCl. Also, make 'modified' flag be local to ApplyRetrieveRule: we should append a rule's quals to the query iff that particular rule applies, not if we have fired any previously-considered rule for the query!
Diffstat (limited to 'src/backend/rewrite/rewriteHandler.c')
-rw-r--r--src/backend/rewrite/rewriteHandler.c38
1 files changed, 19 insertions, 19 deletions
diff --git a/src/backend/rewrite/rewriteHandler.c b/src/backend/rewrite/rewriteHandler.c
index 714f08c2629..327d8c0aefe 100644
--- a/src/backend/rewrite/rewriteHandler.c
+++ b/src/backend/rewrite/rewriteHandler.c
@@ -7,7 +7,7 @@
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/backend/rewrite/rewriteHandler.c,v 1.71 2000/04/12 17:15:32 momjian Exp $
+ * $Header: /cvsroot/pgsql/src/backend/rewrite/rewriteHandler.c,v 1.72 2000/04/20 00:31:49 tgl Exp $
*
*-------------------------------------------------------------------------
*/
@@ -704,8 +704,7 @@ ApplyRetrieveRule(Query *parsetree,
int rt_index,
int relation_level,
Relation relation,
- bool relWasInJoinSet,
- int *modified)
+ bool relWasInJoinSet)
{
Query *rule_action = NULL;
Node *rule_qual;
@@ -714,6 +713,7 @@ ApplyRetrieveRule(Query *parsetree,
*l;
int nothing,
rt_length;
+ int modified = false;
int badsql = false;
rule_qual = rule->qual;
@@ -809,18 +809,23 @@ ApplyRetrieveRule(Query *parsetree,
parsetree = (Query *) apply_RIR_view((Node *) parsetree,
rt_index, rte,
rule_action->targetList,
- modified, 0);
+ &modified, 0);
rule_action = (Query *) apply_RIR_view((Node *) rule_action,
rt_index, rte,
rule_action->targetList,
- modified, 0);
+ &modified, 0);
+ /* always apply quals of relation-level rules, whether we found a
+ * var to substitute or not.
+ */
+ modified = true;
}
else
{
HandleRIRAttributeRule(parsetree, rtable, rule_action->targetList,
- rt_index, rule->attrno, modified, &badsql);
+ rt_index, rule->attrno, &modified, &badsql);
+ /* quals will be inserted only if we found uses of the attribute */
}
- if (*modified && !badsql)
+ if (modified && !badsql)
{
AddQual(parsetree, rule_action->qual);
AddGroupClause(parsetree, rule_action->groupClause,
@@ -894,7 +899,6 @@ fireRIRrules(Query *parsetree)
RewriteRule *rule;
RewriteRule RIRonly;
bool relWasInJoinSet;
- int modified = false;
int i;
List *l;
@@ -910,18 +914,15 @@ fireRIRrules(Query *parsetree)
rte = rt_fetch(rt_index, parsetree->rtable);
/*
- * If the table is not one named in the original FROM clause then
- * it must be referenced in the query, or we ignore it. This
- * prevents infinite expansion loop due to new rtable entries
- * inserted by expansion of a rule.
+ * If the table is not referenced in the query, then we ignore it.
+ * This prevents infinite expansion loop due to new rtable entries
+ * inserted by expansion of a rule. A table is referenced if it is
+ * part of the join set (a source table), or is the result table,
+ * or is referenced by any Var nodes.
*/
- if (!rte->inFromCl && rt_index != parsetree->resultRelation &&
+ if (!rte->inJoinSet && rt_index != parsetree->resultRelation &&
!rangeTableEntry_used((Node *) parsetree, rt_index, 0))
- {
- /* Make sure the planner ignores it too... */
- rte->inJoinSet = false;
continue;
- }
rel = heap_openr(rte->relname, AccessShareLock);
rules = rel->rd_rules;
@@ -989,8 +990,7 @@ fireRIRrules(Query *parsetree)
rt_index,
RIRonly.attrno == -1,
rel,
- relWasInJoinSet,
- &modified);
+ relWasInJoinSet);
}
heap_close(rel, AccessShareLock);