Changeset: 77ff6e9bae1e for MonetDB
URL: https://dev.monetdb.org/hg/MonetDB?cmd=changeset;node=77ff6e9bae1e
Added Files:
sql/test/miscellaneous/Tests/vessels.sql
sql/test/miscellaneous/Tests/vessels.stable.err
sql/test/miscellaneous/Tests/vessels.stable.out
Modified Files:
sql/server/rel_exp.c
sql/server/rel_exp.h
sql/server/rel_psm.c
sql/server/rel_rel.c
sql/server/rel_rel.h
sql/server/rel_select.c
sql/server/rel_unnest.c
sql/server/sql_parser.y
sql/test/BugTracker-2015/Tests/window_function_crash.Bug-3861.stable.err
sql/test/miscellaneous/Tests/All
sql/test/pg_regress/Tests/arrays.stable.err
sql/test/subquery/Tests/subquery4.stable.err
sql/test/subquery/Tests/subquery6.sql
sql/test/subquery/Tests/subquery6.stable.err
sql/test/subquery/Tests/subquery6.stable.out
Branch: default
Log Message:
Merged with Jun2020
diffs (truncated from 968 to 300 lines):
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
@@ -155,8 +155,6 @@ exp_compare(sql_allocator *sa, sql_exp *
if (e == NULL)
return NULL;
e->card = MAX(l->card,r->card);
- if (e->card == CARD_ATOM && !exp_is_atom(l))
- e->card = CARD_AGGR;
e->l = l;
e->r = r;
e->flag = cmptype;
@@ -169,12 +167,10 @@ exp_compare2(sql_allocator *sa, sql_exp
sql_exp *e = exp_create(sa, e_cmp);
if (e == NULL)
return NULL;
+ assert(f);
e->card = MAX(MAX(l->card,r->card),f->card);
- if (e->card == CARD_ATOM && !exp_is_atom(l))
- e->card = CARD_AGGR;
e->l = l;
e->r = r;
- assert(f);
e->f = f;
e->flag = cmptype;
return e;
@@ -252,30 +248,19 @@ exp_in_func(mvc *sql, sql_exp *le, sql_e
}
sql_exp *
-exp_compare_func(mvc *sql, sql_exp *le, sql_exp *re, sql_exp *oe, const char
*compareop, int quantifier)
+exp_compare_func(mvc *sql, sql_exp *le, sql_exp *re, const char *compareop,
int quantifier)
{
- sql_subfunc *cmp_func = NULL;
+ sql_subfunc *cmp_func = sql_bind_func(sql->sa, NULL, compareop,
exp_subtype(le), exp_subtype(le), F_FUNC);
sql_exp *e;
-
- if (!oe) {
- cmp_func = sql_bind_func(sql->sa, NULL, compareop,
exp_subtype(le), exp_subtype(le), F_FUNC);
- assert(cmp_func);
- e = exp_binop(sql->sa, le, re, cmp_func);
- } else {
- list *types = sa_list(sql->sa), *args = sa_list(sql->sa);
- append(types, exp_subtype(le));
- append(types, exp_subtype(le));
- append(types, exp_subtype(le));
- append(args, le);
- append(args, re);
- append(args, oe);
- cmp_func = sql_bind_func_(sql->sa, NULL, compareop, types,
F_FUNC);
- assert(cmp_func);
- e = exp_op(sql->sa, args, cmp_func);
- }
+
+ assert(cmp_func);
+ e = exp_binop(sql->sa, le, re, cmp_func);
if (e) {
e->flag = quantifier;
- e->card = le->card;
+ if (quantifier)
+ e->card = le->card; /* At ANY and ALL operators, the
cardinality on the right side is ignored */
+ else
+ e->card = MAX(le->card, re->card);
}
return e;
}
@@ -314,8 +299,6 @@ exp_op( sql_allocator *sa, list *l, sql_
if (e == NULL)
return NULL;
e->card = exps_card(l);
- if (!l || list_length(l) == 0)
- e->card = CARD_ATOM; /* unop returns a single atom */
e->l = l;
e->f = f;
e->semantics = f->func->semantics;
@@ -336,8 +319,6 @@ exp_rank_op( sql_allocator *sa, list *l,
if (e == NULL)
return NULL;
e->card = exps_card(l);
- if (!l || list_length(l) == 0)
- e->card = CARD_ATOM; /* unop returns a single atom */
e->l = l;
e->r = append(append(sa_list(sa), gbe), obe);
e->f = f;
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
@@ -36,7 +36,7 @@ extern sql_exp *exp_filter(sql_allocator
extern sql_exp *exp_or(sql_allocator *sa, list *l, list *r, int anti);
extern sql_exp *exp_in(sql_allocator *sa, sql_exp *l, list *r, int cmptype);
extern sql_exp *exp_in_func(mvc *sql, sql_exp *le, sql_exp *vals, int
anyequal, int is_tuple);
-extern sql_exp *exp_compare_func(mvc *sql, sql_exp *le, sql_exp *re, sql_exp
*oe, const char *compareop, int quantifier);
+extern sql_exp *exp_compare_func(mvc *sql, sql_exp *le, sql_exp *re, const
char *compareop, int quantifier);
#define exp_fromtype(e) ((list*)e->r)->h->data
#define exp_totype(e) ((list*)e->r)->h->next->data
diff --git a/sql/server/rel_psm.c b/sql/server/rel_psm.c
--- a/sql/server/rel_psm.c
+++ b/sql/server/rel_psm.c
@@ -16,6 +16,15 @@
#include "rel_updates.h"
#include "sql_privileges.h"
+#define psm_zero_or_one(exp) \
+ do { \
+ if (exp && exp->card > CARD_AGGR) { \
+ sql_subfunc *zero_or_one = sql_bind_func(sql->sa,
sql->session->schema, "zero_or_one", exp_subtype(exp), NULL, F_AGGR); \
+ assert(zero_or_one); \
+ exp = exp_aggr1(sql->sa, exp, zero_or_one, 0, 0,
CARD_ATOM, has_nil(exp)); \
+ } \
+ } while(0)
+
static list *sequential_block(sql_query *query, sql_subtype *restype, list
*restypelist, dlist *blk, char *opt_name, int is_func);
sql_rel *
@@ -94,13 +103,9 @@ psm_set_exp(sql_query *query, dnode *n)
if (!resolve_variable_on_scope(sql, s, sname, vname, &var, &a,
&tpe, &level, "SET"))
return NULL;
- if (!(e = rel_value_exp2(query, &rel, val, sql_sel |
sql_psm_set, ek)))
+ if (!(e = rel_value_exp2(query, &rel, val, sql_sel | sql_psm,
ek)))
return NULL;
- if (e->card > CARD_AGGR) {
- sql_subfunc *zero_or_one = sql_bind_func(sql->sa,
sql->session->schema, "zero_or_one", exp_subtype(e), NULL, F_AGGR);
- assert(zero_or_one);
- e = exp_aggr1(sql->sa, e, zero_or_one, 0, 0, CARD_ATOM,
has_nil(e));
- }
+ psm_zero_or_one(e);
if (!(e = rel_check_type(sql, tpe, rel, e, type_cast)))
return NULL;
@@ -255,14 +260,14 @@ rel_psm_while_do( sql_query *query, sql_
sql_rel *rel = NULL;
exp_kind ek = {type_value, card_value, FALSE};
- cond = rel_logical_value_exp(query, &rel, n->data.sym, sql_sel,
ek);
+ cond = rel_logical_value_exp(query, &rel, n->data.sym, sql_sel
| sql_psm, ek);
+ psm_zero_or_one(cond);
n = n->next;
whilestmts = sequential_block(query, res, restypelist,
n->data.lval, n->next->data.sval, is_func);
if (sql->session->status || !cond || !whilestmts)
return NULL;
- assert(!rel);
return exp_while( sql->sa, cond, whilestmts );
}
return NULL;
@@ -287,7 +292,8 @@ psm_if_then_else( sql_query *query, sql_
sql_rel *rel = NULL;
exp_kind ek = {type_value, card_value, FALSE};
- cond = rel_logical_value_exp(query, &rel, n->data.sym, sql_sel,
ek);
+ cond = rel_logical_value_exp(query, &rel, n->data.sym, sql_sel
| sql_psm, ek);
+ psm_zero_or_one(cond);
n = n->next;
ifstmts = sequential_block(query, res, restypelist,
n->data.lval, NULL, is_func);
n = n->next;
@@ -296,7 +302,6 @@ psm_if_then_else( sql_query *query, sql_
if (sql->session->status || !cond || !ifstmts)
return NULL;
- assert(!rel);
return append(sa_list(sql->sa), exp_if( sql->sa, cond, ifstmts,
elsestmts));
} else { /* else */
symbol *e = elseif->data.sym;
@@ -320,7 +325,8 @@ rel_psm_if_then_else( sql_query *query,
sql_rel *rel = NULL;
exp_kind ek = {type_value, card_value, FALSE};
- cond = rel_logical_value_exp(query, &rel, n->data.sym, sql_sel,
ek);
+ cond = rel_logical_value_exp(query, &rel, n->data.sym, sql_sel
| sql_psm, ek);
+ psm_zero_or_one(cond);
n = n->next;
ifstmts = sequential_block(query, res, restypelist,
n->data.lval, NULL, is_func);
n = n->next;
@@ -328,7 +334,6 @@ rel_psm_if_then_else( sql_query *query,
if (sql->session->status || !cond || !ifstmts)
return NULL;
- assert(!rel);
return exp_if( sql->sa, cond, ifstmts, elsestmts);
}
return NULL;
@@ -366,30 +371,28 @@ rel_psm_case( sql_query *query, sql_subt
list *else_stmt = NULL;
sql_rel *rel = NULL;
exp_kind ek = {type_value, card_value, FALSE};
- sql_exp *v = rel_value_exp(query, &rel, case_value, sql_sel,
ek);
+ sql_exp *v = rel_value_exp(query, &rel, case_value, sql_sel |
sql_psm, ek);
+ psm_zero_or_one(v);
if (!v)
return NULL;
- if (rel)
- return sql_error(sql, 02, SQLSTATE(42000) "CASE: No
SELECT statements allowed within the CASE condition");
- if (else_statements) {
- if (!(else_stmt = sequential_block(query, res,
restypelist, else_statements, NULL, is_func)))
- return NULL;
- }
+ if (else_statements && !(else_stmt = sequential_block(query,
res, restypelist, else_statements, NULL, is_func)))
+ return NULL;
+
n = when_statements->h;
while(n) {
dnode *m = n->data.sym->data.lval->h;
- sql_exp *cond=0, *when_value = rel_value_exp(query,
&rel, m->data.sym, sql_sel, ek);
+ sql_exp *cond=0, *when_value = rel_value_exp(query,
&rel, m->data.sym, sql_sel | sql_psm, ek);
list *if_stmts = NULL;
sql_exp *case_stmt = NULL;
- if (!when_value || rel ||
+ psm_zero_or_one(when_value);
+ if (!when_value ||
(cond = rel_binop_(sql, rel, v, when_value, NULL,
"=", card_value)) == NULL ||
(if_stmts = sequential_block(query, res,
restypelist, m->next->data.lval, NULL, is_func)) == NULL ) {
- if (rel)
- return sql_error(sql, 02,
SQLSTATE(42000) "CASE: No SELECT statements allowed within the CASE condition");
return NULL;
}
+ psm_zero_or_one(cond);
case_stmt = exp_if(sql->sa, cond, if_stmts, NULL);
list_append(case_stmts, case_stmt);
n = n->next;
@@ -404,23 +407,21 @@ rel_psm_case( sql_query *query, sql_subt
dlist *else_statements = n->next->data.lval;
list *else_stmt = NULL;
- if (else_statements) {
- if (!(else_stmt = sequential_block(query, res,
restypelist, else_statements, NULL, is_func)))
- return NULL;
- }
+ if (else_statements && !(else_stmt = sequential_block(query,
res, restypelist, else_statements, NULL, is_func)))
+ return NULL;
+
n = whenlist->h;
while(n) {
dnode *m = n->data.sym->data.lval->h;
sql_rel *rel = NULL;
exp_kind ek = {type_value, card_value, FALSE};
- sql_exp *cond = rel_logical_value_exp(query, &rel,
m->data.sym, sql_sel, ek);
+ sql_exp *cond = rel_logical_value_exp(query, &rel,
m->data.sym, sql_sel | sql_psm, ek);
list *if_stmts = NULL;
sql_exp *case_stmt = NULL;
- if (!cond || rel ||
+ psm_zero_or_one(cond);
+ if (!cond ||
(if_stmts = sequential_block(query, res,
restypelist, m->next->data.lval, NULL, is_func)) == NULL ) {
- if (rel)
- return sql_error(sql, 02,
SQLSTATE(42000) "CASE: No SELECT statements allowed within the CASE condition");
return NULL;
}
case_stmt = exp_if(sql->sa, cond, if_stmts, NULL);
@@ -1447,7 +1448,9 @@ psm_analyze(sql_query *query, char *anal
append(exps, mm_exp = exp_atom_int(sql->sa, minmax));
append(tl, exp_subtype(mm_exp));
if (sample) {
- sample_exp = rel_value_exp(query, NULL, sample, 0, ek);
+ sql_rel *rel = NULL;
+ sample_exp = rel_value_exp(query, &rel, sample, sql_sel |
sql_psm, ek);
+ psm_zero_or_one(sample_exp);
if (!sample_exp || !(sample_exp = rel_check_type(sql,
sql_bind_localtype("lng"), NULL, sample_exp, type_cast)))
return NULL;
} else {
diff --git a/sql/server/rel_rel.c b/sql/server/rel_rel.c
--- a/sql/server/rel_rel.c
+++ b/sql/server/rel_rel.c
@@ -2307,3 +2307,25 @@ rel_visitor_bottomup(mvc *sql, sql_rel *
{
return rel_visitor(sql, rel, rel_rewriter, changes, false);
}
+
+static sql_exp *
+exp_check_has_analytics(mvc *sql, sql_rel *rel, sql_exp *e, int depth, int
*changes)
+{
+ (void)sql; (void)rel; (void)depth;
+ if (e && e->type == e_func) {
+ sql_subfunc *f = e->f;
+
+ if (f && f->func && f->func->type == F_ANALYTIC)
+ (*changes)++;
+ }
+ return e;
+}
+
+int
+exps_have_analytics(mvc *sql, list *exps)
+{
+ int changes = 0;
+ (void)exps_exp_visitor(sql, NULL, exps, 0, &exp_check_has_analytics,
&changes, 1);
+ return changes;
+}
+
diff --git a/sql/server/rel_rel.h b/sql/server/rel_rel.h
--- a/sql/server/rel_rel.h
+++ b/sql/server/rel_rel.h
@@ -26,7 +26,7 @@
#define sql_outer (1 << 10) //ORed
#define sql_group_totals (1 << 11) //ORed
_______________________________________________
checkin-list mailing list
[email protected]
https://www.monetdb.org/mailman/listinfo/checkin-list