Changeset: 11e197a303ab for MonetDB
URL: https://dev.monetdb.org/hg/MonetDB?cmd=changeset;node=11e197a303ab
Modified Files:
        sql/server/rel_optimizer.c
        sql/test/SQLancer/Tests/sqlancer04.sql
        sql/test/SQLancer/Tests/sqlancer04.stable.out
Branch: default
Log Message:

SQLancer assertion error and fix. e_cmp expressions are now allowed in 
projections. Updated exp_shares_exps


diffs (133 lines):

diff --git a/sql/server/rel_optimizer.c b/sql/server/rel_optimizer.c
--- a/sql/server/rel_optimizer.c
+++ b/sql/server/rel_optimizer.c
@@ -2670,13 +2670,33 @@ rel_distinct_project2groupby(visitor *v,
        return rel;
 }
 
+static int exp_shares_exps(sql_exp *e, list *shared, lng *uses);
+
 static int
-exp_shares_exps( sql_exp *e, list *shared, lng *uses)
+exps_shares_exps(list *exps, list *shared, lng *uses)
+{
+       if (!exps || !shared)
+               return 0;
+       for (node *n = exps->h; n; n = n->next) {
+               sql_exp *e = n->data;
+
+               if (exp_shares_exps(e, shared, uses))
+                       return 1;
+       }
+       return 0;
+}
+
+static int
+exp_shares_exps(sql_exp *e, list *shared, lng *uses)
 {
        switch(e->type) {
-       case e_cmp: /* not in projection list */
-       case e_psm:
-               assert(0);
+       case e_cmp:
+               if (e->flag == cmp_or || e->flag == cmp_filter)
+                       return exps_shares_exps(e->l, shared, uses) || 
exps_shares_exps(e->r, shared, uses);
+               else if (e->flag == cmp_in || e->flag == cmp_notin)
+                       return exp_shares_exps(e->l, shared, uses) || 
exps_shares_exps(e->r, shared, uses);
+               else
+                       return exp_shares_exps(e->l, shared, uses) || 
exp_shares_exps(e->r, shared, uses) || (e->f && exp_shares_exps(e->f, shared, 
uses));
        case e_atom:
                return 0;
        case e_column:
@@ -2697,43 +2717,31 @@ exp_shares_exps( sql_exp *e, list *share
                        }
                        if (ne && ne != e && (list_position(shared, e) < 0 || 
list_position(shared, e) > list_position(shared, ne)))
                                /* maybe ne refers to a local complex exp */
-                               return exp_shares_exps( ne, shared, uses);
+                               return exp_shares_exps(ne, shared, uses);
                        return 0;
                }
        case e_convert:
                return exp_shares_exps(e->l, shared, uses);
-
        case e_aggr:
        case e_func:
-               {
-                       list *l = e->l;
-                       node *n;
-
-                       if (!l)
-                               return 0;
-                       for (n = l->h; n; n = n->next) {
-                               sql_exp *e = n->data;
-
-                               if (exp_shares_exps( e, shared, uses))
-                                       return 1;
-                       }
-               }
+               return exps_shares_exps(e->l, shared, uses);
+       case e_psm:
+               assert(0);  /* not in projection list */
        }
        return 0;
 }
 
 static int
-exps_share_expensive_exp( list *exps, list *shared )
-{
-       node *n;
+exps_share_expensive_exp(list *exps, list *shared )
+{
        lng uses = 0;
 
        if (!exps || !shared)
                return 0;
-       for (n = exps->h; n; n = n->next){
+       for (node *n = exps->h; n; n = n->next) {
                sql_exp *e = n->data;
 
-               if (exp_shares_exps( e, shared, &uses))
+               if (exp_shares_exps(e, shared, &uses))
                        return 1;
        }
        return 0;
diff --git a/sql/test/SQLancer/Tests/sqlancer04.sql 
b/sql/test/SQLancer/Tests/sqlancer04.sql
--- a/sql/test/SQLancer/Tests/sqlancer04.sql
+++ b/sql/test/SQLancer/Tests/sqlancer04.sql
@@ -239,3 +239,11 @@ UNION ALL
 SELECT count(*) FROM t1 CROSS JOIN t0 GROUP BY 0.2 HAVING (max((ltrim(')''+')) 
NOT IN (CAST(t0.c1 AS VARCHAR(32)), CAST(INTERVAL '6' MONTH AS VARCHAR(32)), 
CAST(INTERVAL '7' MONTH AS VARCHAR(32))))) IS NULL;
        -- empty
 ROLLBACK;
+
+START TRANSACTION;
+CREATE TABLE IF NOT EXISTS t0(c0 FLOAT, c1 DECIMAL NULL UNIQUE);
+CREATE TEMP TABLE t1 (c0 TIME);
+SELECT 1 FROM t1 INNER JOIN (SELECT 2 FROM t0) AS sub0 ON CASE 8 WHEN 3 THEN 
(4) IN (5, 6, 7) END;
+SELECT t1.c0 FROM t1 INNER JOIN (SELECT ALL CAST(TIMESTAMP '1970-01-07 
06:59:48' AS TIMESTAMP) FROM t0) AS sub0 ON CASE t1.c0 WHEN sql_min(t1.c0, 
t1.c0) 
+THEN (((((((496867080) IN (52439321, 1596181433, 
-506328570))OR(((r'W1')ILIKE(r'0.48600327092830353')))))OR((t1.c0) BETWEEN 
SYMMETRIC (t1.c0) AND (t1.c0))))OR(NOT (FALSE))) END;
+ROLLBACK;
diff --git a/sql/test/SQLancer/Tests/sqlancer04.stable.out 
b/sql/test/SQLancer/Tests/sqlancer04.stable.out
--- a/sql/test/SQLancer/Tests/sqlancer04.stable.out
+++ b/sql/test/SQLancer/Tests/sqlancer04.stable.out
@@ -301,6 +301,21 @@ stdout of test 'sqlancer04` in directory
 % bigint # type
 % 1 # length
 #ROLLBACK;
+#START TRANSACTION;
+#CREATE TABLE IF NOT EXISTS t0(c0 FLOAT, c1 DECIMAL NULL UNIQUE);
+#CREATE TEMP TABLE t1 (c0 TIME);
+#SELECT 1 FROM t1 INNER JOIN (SELECT 2 FROM t0) AS sub0 ON CASE 8 WHEN 3 THEN 
(4) IN (5, 6, 7) END;
+% .%17 # table_name
+% %17 # name
+% tinyint # type
+% 1 # length
+#SELECT t1.c0 FROM t1 INNER JOIN (SELECT ALL CAST(TIMESTAMP '1970-01-07 
06:59:48' AS TIMESTAMP) FROM t0) AS sub0 ON CASE t1.c0 WHEN sql_min(t1.c0, 
t1.c0) 
+#THEN (((((((496867080) IN (52439321, 1596181433, 
-506328570))OR(((r'W1')ILIKE(r'0.48600327092830353')))))OR((t1.c0) BETWEEN 
SYMMETRIC (t1.c0) AND (t1.c0))))OR(NOT (FALSE))) END;
+% tmp.t1 # table_name
+% c0 # name
+% time # type
+% 8 # length
+#ROLLBACK;
 
 # 09:44:50 >  
 # 09:44:50 >  "Done."
_______________________________________________
checkin-list mailing list
checkin-list@monetdb.org
https://www.monetdb.org/mailman/listinfo/checkin-list

Reply via email to