Changeset: d7378d64f5ca for MonetDB
URL: https://dev.monetdb.org/hg/MonetDB/rev/d7378d64f5ca
Modified Files:
        sql/backends/monet5/rel_bin.c
        sql/storage/store.c
        sql/test/miscellaneous/Tests/transaction_isolation3.SQL.py
Branch: iso
Log Message:

Added DML dependency checks


diffs (211 lines):

diff --git a/sql/backends/monet5/rel_bin.c b/sql/backends/monet5/rel_bin.c
--- a/sql/backends/monet5/rel_bin.c
+++ b/sql/backends/monet5/rel_bin.c
@@ -4365,6 +4365,9 @@ rel2bin_insert(backend *be, sql_rel *rel
        /* update predicate list */
        if (rel->r && !rel_predicates(be, rel->r))
                return NULL;
+       if (!isNew(t) && sql_trans_add_dependency_change(be->mvc->session->tr, 
t->base.id, dml) != LOG_OK)
+               return sql_error(sql, 02, SQLSTATE(HY013) MAL_MALLOC_FAIL);
+
        if (ddl) {
                ret = ddl;
                list_prepend(l, ddl);
@@ -5355,6 +5358,8 @@ rel2bin_update(backend *be, sql_rel *rel
                sql->cascade_action = NULL;
        if (rel->r && !rel_predicates(be, rel->r))
                return NULL;
+       if (!isNew(t) && sql_trans_add_dependency_change(be->mvc->session->tr, 
t->base.id, dml) != LOG_OK)
+               return sql_error(sql, 02, SQLSTATE(HY013) MAL_MALLOC_FAIL);
        return cnt;
 }
 
@@ -5596,6 +5601,9 @@ rel2bin_delete(backend *be, sql_rel *rel
        }
        if (rel->r && !rel_predicates(be, rel->r))
                return NULL;
+       if (!isNew(t) && sql_trans_add_dependency_change(be->mvc->session->tr, 
t->base.id, dml) != LOG_OK)
+               return sql_error(sql, 02, SQLSTATE(HY013) MAL_MALLOC_FAIL);
+
        return stdelete;
 }
 
@@ -5821,6 +5829,9 @@ rel2bin_truncate(backend *be, sql_rel *r
        restart_sequences = E_ATOM_INT(n->data);
        cascade = E_ATOM_INT(n->next->data);
 
+       if (!isNew(t) && sql_trans_add_dependency_change(be->mvc->session->tr, 
t->base.id, dml) != LOG_OK)
+               return sql_error(sql, 02, SQLSTATE(HY013) MAL_MALLOC_FAIL);
+
        truncate = sql_truncate(be, t, restart_sequences, cascade);
        if (sql->cascade_action)
                sql->cascade_action = NULL;
diff --git a/sql/storage/store.c b/sql/storage/store.c
--- a/sql/storage/store.c
+++ b/sql/storage/store.c
@@ -3108,8 +3108,18 @@ sql_trans_copy_key( sql_trans *tr, sql_t
        if ((res = store->table_api.table_insert(tr, syskey, &nk->base.id, 
&t->base.id, &nk->type, &nk->base.name, (nk->type == fkey) ? &((sql_fkey *) 
nk)->rkey : &neg, &action)))
                return res;
 
-       if (nk->type == fkey && (res = sql_trans_create_dependency(tr, 
((sql_fkey *) nk)->rkey, nk->base.id, FKEY_DEPENDENCY)))
-               return res;
+       if (nk->type == fkey) {
+               sql_key *rkey = (sql_key*)os_find_id(tr->cat->objects, tr, 
((sql_fkey*)k)->rkey);
+
+               if ((res = sql_trans_create_dependency(tr, rkey->base.id, 
nk->base.id, FKEY_DEPENDENCY)))
+                       return res;
+               /* TODO this has to be cleaned out once the sql_cat.c cleanup 
is done */
+               if (!isNew(rkey) && (res = sql_trans_add_dependency(tr, 
rkey->base.id, ddl)))
+                       return res;
+               if (!isNew(rkey) && (res = sql_trans_add_dependency(tr, 
rkey->t->base.id, dml))) /* disallow concurrent updates on other key */
+                       return res;
+       }
+
        for (n = nk->columns->h, nr = 0; n; n = n->next, nr++) {
                sql_kc *kc = n->data;
 
@@ -3128,7 +3138,15 @@ sql_trans_copy_key( sql_trans *tr, sql_t
                        if ((res = sql_trans_alter_null(tr, kc->c, 0)))
                                return res;
                }
-       }
+
+               /* TODO this has to be cleaned out too */
+               if (!isNew(kc->c) && (res = sql_trans_add_dependency(tr, 
kc->c->base.id, ddl)))
+                       return res;
+       }
+
+       /* TODO this has to be cleaned out too */
+       if (!isNew(t) && (res = sql_trans_add_dependency(tr, t->base.id, dml))) 
/* disallow concurrent updates on t */
+               return res;
        if (kres)
                *kres = nk;
        return res;
@@ -5091,6 +5109,8 @@ sql_trans_add_range_partition(sql_trans 
                return res;
        if (!isNew(pt) && (res = sql_trans_add_dependency_change(tr, 
pt->base.id, ddl))) /* protect from being added twice */
                return res;
+       if (!isNew(pt) && (res = sql_trans_add_dependency(tr, pt->base.id, 
dml))) /* disallow concurrent updates on pt */
+               return res;
 finish:
        VALclear(&vmin);
        VALclear(&vmax);
@@ -5221,6 +5241,8 @@ sql_trans_add_value_partition(sql_trans 
                return res;
        if (!isNew(pt) && (res = sql_trans_add_dependency_change(tr, 
pt->base.id, ddl))) /* protect from being added twice */
                return res;
+       if (!isNew(pt) && (res = sql_trans_add_dependency(tr, pt->base.id, 
dml))) /* disallow concurrent updates on pt */
+               return res;
        return 0;
 }
 
@@ -5669,7 +5691,7 @@ sql_trans_rename_column(sql_trans *tr, s
                return -1;
        sql_column *c = n->data;
 
-       if (!isNew(c->t) && (res = sql_trans_add_dependency_change(tr, 
c->t->base.id, ddl)))
+       if (!isNew(c) && (res = sql_trans_add_dependency_change(tr, 
c->t->base.id, ddl)))
                return res;
        if (!isNew(c) && (res = sql_trans_add_dependency_change(tr, id, ddl)))
                return res;
@@ -5780,6 +5802,9 @@ sql_trans_alter_null(sql_trans *tr, sql_
                if ((res = new_column(tr, col, &dup)))
                        return res;
                dup->null = isnull;
+
+               if (!isnull && !isNew(col) && (res = 
sql_trans_add_dependency(tr, col->t->base.id, dml))) /* disallow concurrent 
updates on pt */
+                       return res;
        }
        return res;
 }
@@ -6054,8 +6079,6 @@ sql_trans_create_fkey(sql_trans *tr, sql
                return NULL;
 
        sql_trans_create_dependency(tr, ((sql_fkey *) nk)->rkey, nk->base.id, 
FKEY_DEPENDENCY);
-       if (!isNew(nk) && (res = sql_trans_add_dependency(tr, ((sql_fkey *) 
nk)->rkey, ddl)))
-               return NULL;
        return (sql_fkey*) nk;
 }
 
@@ -6067,7 +6090,6 @@ sql_trans_create_kc(sql_trans *tr, sql_k
        int nr = list_length(k->columns);
        sql_schema *syss = find_sql_schema(tr, isGlobal(k->t)?"sys":"tmp");
        sql_table *syskc = find_sql_table(tr, syss, "objects");
-       int res = LOG_OK;
 
        assert(c);
        kc->c = c;
@@ -6077,8 +6099,6 @@ sql_trans_create_kc(sql_trans *tr, sql_k
 
        if (k->type == pkey) {
                sql_trans_create_dependency(tr, c->base.id, k->base.id, 
KEY_DEPENDENCY);
-               if (!isNew(c) && (res = sql_trans_add_dependency(tr, 
c->base.id, ddl)))
-                       return NULL;
                if (sql_trans_alter_null(tr, c, 0)) /* should never happen */
                        return NULL;
        }
@@ -6097,7 +6117,6 @@ sql_trans_create_fkc(sql_trans *tr, sql_
        int nr = list_length(k->columns);
        sql_schema *syss = find_sql_schema(tr, isGlobal(k->t)?"sys":"tmp");
        sql_table *syskc = find_sql_table(tr, syss, "objects");
-       int res = LOG_OK;
 
        assert(c);
        kc->c = c;
@@ -6106,8 +6125,6 @@ sql_trans_create_fkc(sql_trans *tr, sql_
                sql_trans_create_ic(tr, k->idx, c);
 
        sql_trans_create_dependency(tr, c->base.id, k->base.id, 
FKEY_DEPENDENCY);
-       if (!isNew(c) && (res = sql_trans_add_dependency(tr, c->base.id, ddl)))
-               return NULL;
 
        if (store->table_api.table_insert(tr, syskc, &k->base.id, 
&kc->c->base.name, &nr, ATOMnilptr(TYPE_int)))
                return NULL;
diff --git a/sql/test/miscellaneous/Tests/transaction_isolation3.SQL.py 
b/sql/test/miscellaneous/Tests/transaction_isolation3.SQL.py
--- a/sql/test/miscellaneous/Tests/transaction_isolation3.SQL.py
+++ b/sql/test/miscellaneous/Tests/transaction_isolation3.SQL.py
@@ -13,7 +13,7 @@ with SQLTestCase() as mdb1:
         mdb1.execute('commit;').assertSucceeded()
         mdb2.execute('rollback;').assertSucceeded()
 
-        mdb1.execute("CREATE TABLE notpossible (i int, j 
int);").assertSucceeded() # not fixed yet
+        mdb1.execute("CREATE TABLE notpossible (i int, j 
int);").assertSucceeded()
         mdb1.execute('start transaction;').assertSucceeded()
         mdb2.execute('start transaction;').assertSucceeded()
         mdb1.execute('insert into notpossible values 
(5,1),(5,2),(5,3);').assertSucceeded()
@@ -21,7 +21,7 @@ with SQLTestCase() as mdb1:
         mdb1.execute('commit;').assertSucceeded()
         mdb2.execute('commit;').assertFailed(err_code="40000", 
err_message="COMMIT: transaction is aborted because of concurrency conflicts, 
will ROLLBACK instead")
 
-        mdb1.execute("CREATE TABLE integers (i int, j 
int);").assertSucceeded() # not fixed yet
+        mdb1.execute("CREATE TABLE integers (i int, j int);").assertSucceeded()
         mdb1.execute('start transaction;').assertSucceeded()
         mdb2.execute('start transaction;').assertSucceeded()
         mdb1.execute('alter table integers add primary key 
(i);').assertSucceeded()
@@ -29,7 +29,7 @@ with SQLTestCase() as mdb1:
         mdb1.execute('commit;').assertSucceeded()
         mdb2.execute('commit;').assertFailed(err_code="40000", 
err_message="COMMIT: transaction is aborted because of concurrency conflicts, 
will ROLLBACK instead")
 
-        mdb1.execute('start transaction;').assertSucceeded() # not fixed yet
+        mdb1.execute('start transaction;').assertSucceeded()
         mdb2.execute('start transaction;').assertSucceeded()
         mdb1.execute('alter table integers alter j set not 
null;').assertSucceeded()
         mdb2.execute('insert into integers values 
(6,NULL),(7,NULL),(8,NULL);').assertSucceeded()
@@ -46,7 +46,7 @@ with SQLTestCase() as mdb1:
         mdb1.execute('commit;').assertSucceeded()
         mdb2.execute('commit;').assertFailed(err_code="40000", 
err_message="COMMIT: transaction is aborted because of concurrency conflicts, 
will ROLLBACK instead")
 
-        mdb1.execute('create merge table parent2(a int) PARTITION BY RANGE ON 
(a);').assertSucceeded() # not fixed yet
+        mdb1.execute('create merge table parent2(a int) PARTITION BY RANGE ON 
(a);').assertSucceeded()
         mdb1.execute('create table child2(c int);').assertSucceeded()
         mdb1.execute('start transaction;').assertSucceeded()
         mdb2.execute('start transaction;').assertSucceeded()
@@ -75,7 +75,7 @@ with SQLTestCase() as mdb1:
         mdb2.execute('commit;').assertFailed(err_code="40000", 
err_message="COMMIT: transaction is aborted because of concurrency conflicts, 
will ROLLBACK instead")
         mdb1.execute('select * from 
another();').assertSucceeded().assertDataResultMatch([(2,)])
 
-        mdb1.execute("CREATE TABLE y (i int);").assertSucceeded() # not fixed 
yet
+        mdb1.execute("CREATE TABLE y (i int);").assertSucceeded()
         mdb1.execute('CREATE TABLE integers2 (i int, j 
int);').assertSucceeded()
         mdb1.execute('insert into integers2 values 
(1,1),(2,2),(3,3);').assertSucceeded()
         mdb1.execute('alter table integers2 add primary key 
(i);').assertSucceeded()
_______________________________________________
checkin-list mailing list
checkin-list@monetdb.org
https://www.monetdb.org/mailman/listinfo/checkin-list

Reply via email to