Changeset: d85f57f9c8bb for MonetDB
URL: https://dev.monetdb.org/hg/MonetDB?cmd=changeset;node=d85f57f9c8bb
Modified Files:
        sql/server/rel_dump.c
        sql/server/rel_exp.c
        sql/server/rel_exp.h
        sql/server/rel_optimizer.c
        sql/server/rel_rel.c
        sql/server/rel_select.c
        sql/server/rel_unnest.c
        sql/server/rel_updates.c
        sql/test/SQLancer/Tests/sqlancer05.sql
        sql/test/SQLancer/Tests/sqlancer05.stable.err
        sql/test/SQLancer/Tests/sqlancer05.stable.out
Branch: Oct2020
Log Message:

Making SQLancer happy. Test for duplicated column names on relation when trying 
to bind from them


diffs (truncated from 884 to 300 lines):

diff --git a/sql/server/rel_dump.c b/sql/server/rel_dump.c
--- a/sql/server/rel_dump.c
+++ b/sql/server/rel_dump.c
@@ -875,9 +875,12 @@ exp_read(mvc *sql, sql_rel *lrel, sql_re
                *e = old;
                skipWS(r, pos);
                if (pexps) {
-                       exp = exps_bind_column2(pexps, tname, cname);
+                       int mul = 0;
+                       exp = exps_bind_column2(pexps, tname, cname, &mul);
                        if (exp)
                                exp = exp_alias_or_copy(sql, tname, cname, 
lrel, exp);
+                       (void) mul;
+                       assert(mul == 0);
                }
                if (!exp && lrel) {
                        exp = rel_bind_column2(sql, lrel, tname, cname, 0);
@@ -1115,18 +1118,19 @@ exp_read(mvc *sql, sql_rel *lrel, sql_re
                }
                */
                if (!exp && lrel) {
-                       int amb = 0;
+                       int amb = 0, mul = 0;
 
                        old = *e;
                        *e = 0;
                        var_cname = sa_strdup(sql->sa, b);
                        if (pexps) {
-                               exp = exps_bind_column(pexps, var_cname, &amb, 
1);
+                               exp = exps_bind_column(pexps, var_cname, &amb, 
&mul, 1);
                                if (exp)
                                        exp = exp_alias_or_copy(sql, 
exp_relname(exp), var_cname, lrel, exp);
                        }
                        (void)amb;
-                       assert(amb == 0);
+                       (void)mul;
+                       assert(amb == 0 && mul == 0);
                        if (!exp && lrel)
                                exp = rel_bind_column(sql, lrel, var_cname, 0, 
1);
                        if (!exp && rrel)
diff --git a/sql/server/rel_exp.c b/sql/server/rel_exp.c
--- a/sql/server/rel_exp.c
+++ b/sql/server/rel_exp.c
@@ -1562,9 +1562,9 @@ rel_find_exp_and_corresponding_rel_( sql
        case e_column:
                if (rel->exps && (is_project(rel->op) || is_base(rel->op))) {
                        if (e->l) {
-                               ne = exps_bind_column2(rel->exps, e->l, e->r);
+                               ne = exps_bind_column2(rel->exps, e->l, e->r, 
NULL);
                        } else {
-                               ne = exps_bind_column(rel->exps, e->r, NULL, 1);
+                               ne = exps_bind_column(rel->exps, e->r, NULL, 
NULL, 1);
                        }
                }
                if (ne && res)
@@ -1625,7 +1625,7 @@ rel_find_exp_and_corresponding_rel(sql_r
                                *under_join = true;
                        break;
                case op_table:
-                       if (rel->exps && e->type == e_column && e->l && 
exps_bind_column2(rel->exps, e->l, e->r))
+                       if (rel->exps && e->type == e_column && e->l && 
exps_bind_column2(rel->exps, e->l, e->r, NULL))
                                ne = e;
                        if (ne && res)
                                *res = rel;
@@ -1637,11 +1637,11 @@ rel_find_exp_and_corresponding_rel(sql_r
                        if (rel->l)
                                ne = rel_find_exp_and_corresponding_rel(rel->l, 
e, res, under_join);
                        else if (rel->exps && e->l) {
-                               ne = exps_bind_column2(rel->exps, e->l, e->r);
+                               ne = exps_bind_column2(rel->exps, e->l, e->r, 
NULL);
                                if (ne && res)
                                        *res = rel;
                        } else if (rel->exps) {
-                               ne = exps_bind_column(rel->exps, e->r, NULL, 1);
+                               ne = exps_bind_column(rel->exps, e->r, NULL, 
NULL, 1);
                                if (ne && res)
                                        *res = rel;
                        }
@@ -1649,7 +1649,7 @@ rel_find_exp_and_corresponding_rel(sql_r
                break;
                case op_basetable:
                        if (rel->exps && e->type == e_column && e->l)
-                               ne = exps_bind_column2(rel->exps, e->l, e->r);
+                               ne = exps_bind_column2(rel->exps, e->l, e->r, 
NULL);
                        if (ne && res)
                                *res = rel;
                        break;
@@ -2221,9 +2221,9 @@ exp_key( sql_exp *e )
 }
 
 sql_exp *
-exps_bind_column( list *exps, const char *cname, int *ambiguous, int no_tname)
+exps_bind_column(list *exps, const char *cname, int *ambiguous, int *multiple, 
int no_tname)
 {
-       sql_exp *e = NULL;
+       sql_exp *res = NULL;
 
        if (exps && cname) {
                node *en;
@@ -2253,41 +2253,54 @@ exps_bind_column( list *exps, const char
                                sql_hash_e *he = 
exps->ht->buckets[key&(exps->ht->size-1)];
 
                                for (; he; he = he->chain) {
-                                       sql_exp *ce = he->value;
-
-                                       if (ce->alias.name && 
strcmp(ce->alias.name, cname) == 0 && (!no_tname || !ce->alias.rname)) {
-                                               if (e && e != ce && 
ce->alias.rname && e->alias.rname && strcmp(ce->alias.rname, e->alias.rname) != 
0 ) {
+                                       sql_exp *e = he->value;
+
+                                       if (e->alias.name && 
strcmp(e->alias.name, cname) == 0 && (!no_tname || !e->alias.rname)) {
+                                               if (res && multiple)
+                                                       *multiple = 1;
+                                               if (!res)
+                                                       res = e;
+                                               
+                                               if (res && res != e && 
e->alias.rname && res->alias.rname && strcmp(e->alias.rname, res->alias.rname) 
!= 0 ) {
                                                        if (ambiguous)
                                                                *ambiguous = 1;
                                                        
MT_lock_unset(&exps->ht_lock);
                                                        return NULL;
                                                }
-                                               e = ce;
+                                               res = e;
                                        }
                                }
                                MT_lock_unset(&exps->ht_lock);
-                               return e;
+                               return res;
                        }
                        MT_lock_unset(&exps->ht_lock);
                }
                for (en = exps->h; en; en = en->next ) {
-                       sql_exp *ce = en->data;
-                       if (ce->alias.name && strcmp(ce->alias.name, cname) == 
0 && (!no_tname || !ce->alias.rname)) {
-                               if (e && e != ce && ce->alias.rname && 
e->alias.rname && strcmp(ce->alias.rname, e->alias.rname) != 0 ) {
+                       sql_exp *e = en->data;
+
+                       if (e->alias.name && strcmp(e->alias.name, cname) == 0 
&& (!no_tname || !e->alias.rname)) {
+                               if (res && multiple)
+                                       *multiple = 1;
+                               if (!res)
+                                       res = e;
+
+                               if (res && res != e && e->alias.rname && 
res->alias.rname && strcmp(e->alias.rname, res->alias.rname) != 0 ) {
                                        if (ambiguous)
                                                *ambiguous = 1;
                                        return NULL;
                                }
-                               e = ce;
+                               res = e;
                        }
                }
        }
-       return e;
+       return res;
 }
 
 sql_exp *
-exps_bind_column2( list *exps, const char *rname, const char *cname )
+exps_bind_column2(list *exps, const char *rname, const char *cname, int 
*multiple)
 {
+       sql_exp *res = NULL;
+
        if (exps) {
                node *en;
 
@@ -2297,7 +2310,7 @@ exps_bind_column2( list *exps, const cha
                                exps->ht = hash_new(exps->sa, 
list_length(exps), (fkeyvalue)&exp_key);
                                if (exps->ht == NULL) {
                                        MT_lock_unset(&exps->ht_lock);
-                                       return NULL;
+                                       return res;
                                }
 
                                for (en = exps->h; en; en = en->next ) {
@@ -2307,7 +2320,7 @@ exps_bind_column2( list *exps, const cha
 
                                                if (hash_add(exps->ht, key, e) 
== NULL) {
                                                        
MT_lock_unset(&exps->ht_lock);
-                                                       return NULL;
+                                                       return res;
                                                }
                                        }
                                }
@@ -2320,23 +2333,29 @@ exps_bind_column2( list *exps, const cha
                                        sql_exp *e = he->value;
 
                                        if (e && e->alias.name && 
e->alias.rname && strcmp(e->alias.name, cname) == 0 && strcmp(e->alias.rname, 
rname) == 0) {
-                                               MT_lock_unset(&exps->ht_lock);
-                                               return e;
+                                               if (res && multiple)
+                                                       *multiple = 1;
+                                               if (!res)
+                                                       res = e;
                                        }
                                }
                                MT_lock_unset(&exps->ht_lock);
-                               return NULL;
+                               return res;
                        }
                        MT_lock_unset(&exps->ht_lock);
                }
                for (en = exps->h; en; en = en->next ) {
                        sql_exp *e = en->data;
 
-                       if (e && e->alias.name && e->alias.rname && 
strcmp(e->alias.name, cname) == 0 && strcmp(e->alias.rname, rname) == 0)
-                               return e;
+                       if (e && e->alias.name && e->alias.rname && 
strcmp(e->alias.name, cname) == 0 && strcmp(e->alias.rname, rname) == 0) {
+                               if (res && multiple)
+                                       *multiple = 1;
+                               if (!res)
+                                       res = e;
+                       }
                }
        }
-       return NULL;
+       return res;
 }
 
 /* find an column based on the original name, not the alias it got */
@@ -2445,9 +2464,9 @@ is_identity( sql_exp *e, sql_rel *r)
                if (r && is_project(r->op)) {
                        sql_exp *re = NULL;
                        if (e->l)
-                               re = exps_bind_column2(r->exps, e->l, e->r);
+                               re = exps_bind_column2(r->exps, e->l, e->r, 
NULL);
                        if (!re && has_label(e))
-                               re = exps_bind_column(r->exps, e->r, NULL, 1);
+                               re = exps_bind_column(r->exps, e->r, NULL, 
NULL, 1);
                        if (re)
                                return is_identity(re, r->l);
                }
diff --git a/sql/server/rel_exp.h b/sql/server/rel_exp.h
--- a/sql/server/rel_exp.h
+++ b/sql/server/rel_exp.h
@@ -171,9 +171,9 @@ extern int rel_has_all_exps(sql_rel *rel
 extern sql_rel *find_rel(list *rels, sql_exp *e);
 extern sql_rel *find_one_rel(list *rels, sql_exp *e);
 
-extern sql_exp *exps_bind_column( list *exps, const char *cname, int 
*ambiguous, int no_tname /* set if expressions should be without a tname */);
-extern sql_exp *exps_bind_column2( list *exps, const char *rname, const char 
*cname);
-extern sql_exp *exps_bind_alias( list *exps, const char *rname, const char 
*cname);
+extern sql_exp *exps_bind_column(list *exps, const char *cname, int 
*ambiguous, int *multiple, int no_tname /* set if expressions should be without 
a tname */);
+extern sql_exp *exps_bind_column2(list *exps, const char *rname, const char 
*cname, int *multiple);
+extern sql_exp *exps_bind_alias(list *exps, const char *rname, const char 
*cname);
 
 extern unsigned int exps_card( list *l );
 extern void exps_fix_card( list *exps, unsigned int card);
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
@@ -48,9 +48,9 @@ name_find_column( sql_rel *rel, const ch
                        sql_exp *e;
 
                        if (rname)
-                               e = exps_bind_column2(rel->exps, rname, name);
+                               e = exps_bind_column2(rel->exps, rname, name, 
NULL);
                        else
-                               e = exps_bind_column(rel->exps, name, NULL, 0);
+                               e = exps_bind_column(rel->exps, name, NULL, 
NULL, 0);
                        if (!e || e->type != e_column)
                                return NULL;
                        if (e->l)
@@ -125,14 +125,14 @@ name_find_column( sql_rel *rel, const ch
                if (!rel->exps)
                        break;
                if (rname)
-                       alias = exps_bind_column2(rel->exps, rname, name);
+                       alias = exps_bind_column2(rel->exps, rname, name, NULL);
                else
-                       alias = exps_bind_column(rel->exps, name, NULL, 1);
+                       alias = exps_bind_column(rel->exps, name, NULL, NULL, 
1);
                if (is_groupby(rel->op) && alias && alias->type == e_column && 
rel->r) {
                        if (alias->l)
-                               alias = exps_bind_column2(rel->r, alias->l, 
alias->r);
+                               alias = exps_bind_column2(rel->r, alias->l, 
alias->r, NULL);
                        else
-                               alias = exps_bind_column(rel->r, alias->r, 
NULL, 1);
+                               alias = exps_bind_column(rel->r, alias->r, 
NULL, NULL, 1);
                }
                if (is_groupby(rel->op) && !alias && rel->l) {
                        /* Group by column not found as alias in projection
@@ -193,8 +193,8 @@ list_find_exp( list *exps, sql_exp *e)
 
        if (e->type != e_column)
                return NULL;
-       if (( e->l && (ne=exps_bind_column2(exps, e->l, e->r)) != NULL) ||
-          ((!e->l && (ne=exps_bind_column(exps, e->r, NULL, 1)) != NULL)))
+       if (( e->l && (ne=exps_bind_column2(exps, e->l, e->r, NULL)) != NULL) ||
+          ((!e->l && (ne=exps_bind_column(exps, e->r, NULL, NULL, 1)) != 
NULL)))
                return ne;
        return NULL;
 }
@@ -1236,10 +1236,10 @@ exp_rename(mvc *sql, sql_exp *e, sql_rel
        switch(e->type) {
        case e_column:
                if (e->l) {
-                       ne = exps_bind_column2(f->exps, e->l, e->r);
+                       ne = exps_bind_column2(f->exps, e->l, e->r, NULL);
                        /* if relation name matches expressions relation name, 
find column based on column name alone */
_______________________________________________
checkin-list mailing list
checkin-list@monetdb.org
https://www.monetdb.org/mailman/listinfo/checkin-list

Reply via email to