Changeset: 3cf1ff006870 for MonetDB
URL: http://dev.monetdb.org/hg/MonetDB?cmd=changeset;node=3cf1ff006870
Modified Files:
        sql/backends/monet5/sql.c
        sql/backends/monet5/sql_gencode.c
        sql/include/Makefile.ag
        sql/include/sql_catalog.h
        sql/server/rel_schema.c
        sql/server/rel_schema.h
        sql/server/rel_select.c
        sql/server/sql_mvc.c
        sql/server/sql_mvc.h
        sql/server/sql_parser.h
        sql/storage/Makefile.ag
        sql/storage/bat/bat_storage.c
        sql/storage/sql_catalog.c
        sql/storage/sql_storage.h
        sql/storage/store.c
Branch: arrays
Log Message:

create array: dimensions contain all necessary information


diffs (truncated from 764 to 300 lines):

diff --git a/sql/backends/monet5/sql.c b/sql/backends/monet5/sql.c
--- a/sql/backends/monet5/sql.c
+++ b/sql/backends/monet5/sql.c
@@ -419,7 +419,7 @@ create_table_or_view(mvc *sql, char *sna
 
        osa = sql->sa;
        sql->sa = NULL;
-       /* first check default values */
+       /* first check default values. I should update that to deal with 
dimensions */
        for (n = t->columns.set->h; n; n = n->next) {
                sql_column *c = n->data;
 
@@ -439,13 +439,27 @@ create_table_or_view(mvc *sql, char *sna
                }
        }
 
+       //create a copy of the table without the changesets
        nt = sql_trans_create_table(sql->session->tr, s, t->base.name, 
t->query, t->type, t->system, temp, t->commit_action, t->sz);
 
+       if(isArray(t)) {
+               assert(t->dimensions.set); //an array should always have 
dimensional column(s)
+
+               for (n = t->dimensions.set->h; n; n = n->next) {
+                       sql_dimension *d = n->data;
+                       if (mvc_copy_dimension(sql, nt, d) == NULL)
+                               throw(SQL, "sql.catalog", "CREATE ARRAY: 
%s_%s_%s conflicts", s->base.name, t->base.name, d->base.name);
+
+               }
+       }
        for (n = t->columns.set->h; n; n = n->next) {
                sql_column *c = n->data;
-               if (mvc_copy_column(sql, nt, c) == NULL)
-                       throw(SQL, "sql.catalog", "CREATE TABLE: %s_%s_%s 
conflicts", s->base.name, t->base.name, c->base.name);
-
+               if (mvc_copy_column(sql, nt, c) == NULL) {
+                       if(isArray(t))
+                               throw(SQL, "sql.catalog", "CREATE ARRAY: 
%s_%s_%s conflicts", s->base.name, t->base.name, c->base.name);
+                       else
+                               throw(SQL, "sql.catalog", "CREATE TABLE: 
%s_%s_%s conflicts", s->base.name, t->base.name, c->base.name);
+               }
        }
        if (t->idxs.set) {
                for (n = t->idxs.set->h; n; n = n->next) {
diff --git a/sql/backends/monet5/sql_gencode.c 
b/sql/backends/monet5/sql_gencode.c
--- a/sql/backends/monet5/sql_gencode.c
+++ b/sql/backends/monet5/sql_gencode.c
@@ -2650,7 +2650,7 @@ backend_dumpproc(backend *be, Client c, 
        setVarUDFtype(mb, 0);
        setModuleId(curInstr, userRef);
 
-       if (m->argc) {
+       if (m->argc) { //it reads the literals that had been included in the 
query.
                for (argc = 0; argc < m->argc; argc++) {
                        atom *a = m->args[argc];
                        int type = atom_type(a)->type->localtype;
diff --git a/sql/include/Makefile.ag b/sql/include/Makefile.ag
--- a/sql/include/Makefile.ag
+++ b/sql/include/Makefile.ag
@@ -16,6 +16,7 @@
 # All Rights Reserved.
 
 ## Process this file with automake to produce Makefile.in
+#INCLUDES = ../server \
 
 #EXTRA_HEADERS = sql_mem.h sql_list.h sql_hash.h sql_catalog.h sql_keyword.h 
sql_relation.h 
 EXTRA_DIST = sql_mem.h sql_list.h sql_hash.h sql_stack.h sql_catalog.h 
sql_keyword.h sql_relation.h 
diff --git a/sql/include/sql_catalog.h b/sql/include/sql_catalog.h
--- a/sql/include/sql_catalog.h
+++ b/sql/include/sql_catalog.h
@@ -452,6 +452,39 @@ typedef struct sql_column {
        void *data;
 } sql_column;
 
+//dimension needs atom. Since is stores pointers to atom there is no
+//need to find the type. The important is to know that there is a
+//type atom
+typedef struct atom atom;
+
+typedef struct sql_dimension {
+       sql_base base;
+       sql_subtype type;
+       int dimnr; //the order of the dimension
+       char *def; //I think this is for default values
+       char *storage_type;
+       size_t dcount; /* what does it do? */
+
+       bit unbounded_min;
+       bit unbounded_max;
+
+       //the range of the dimension
+       //It is void to store any type of dimensions
+       //the exact type is found through the type field of the struct
+       //Niels said to use atom. In this case do I need the information about 
the type?
+       //maybe I need to to check that the values when inserting a new cell 
are of the correct type
+       atom *min;
+       atom *step;
+       atom *max;
+       
+       lng lvl1_repeatsNum; //number of times each value of the dimension is 
repeated before being increased
+       lng lvl2_repeatsNum; //number of times all values of the dimension are 
repeated as a group (including the duplicated values defined by repeatNum)
+       lng elementsNum; //the distinct number of elements in this dimension, 
i.e. the nu,ber of indices
+
+       struct sql_table *t;
+//     void *data; //it does not have data since it is not materialised
+} sql_dimension;
+
 typedef enum table_types {
        tt_table = 0,           /* table */
        tt_view = 1,            /* view */
@@ -486,6 +519,7 @@ typedef struct sql_table {
        int  sz;
 
        sql_ukey *pkey;
+       changeset dimensions; //used only when the table is an array
        changeset columns;
        changeset idxs;
        changeset keys;
@@ -554,6 +588,7 @@ extern sql_key *find_sql_key(sql_table *
 extern sql_idx *find_sql_idx(sql_table *t, const char *kname);
 
 extern sql_column *find_sql_column(sql_table *t, const char *cname);
+extern sql_dimension *find_sql_dimension(sql_table *t, const char *dname);
 
 extern sql_table *find_sql_table(sql_schema *s, const char *tname);
 extern sql_table *find_sql_table_id(sql_schema *s, int id);
diff --git a/sql/server/rel_schema.c b/sql/server/rel_schema.c
--- a/sql/server/rel_schema.c
+++ b/sql/server/rel_schema.c
@@ -568,6 +568,55 @@ table_constraint(mvc *sql, symbol *s, sq
 }
 
 static int
+create_dimension(mvc *sql, symbol *s, sql_schema *ss, sql_table *t)
+{
+       dlist *l = s->data.lval;
+       char *dname = l->h->data.sval;
+       sql_subtype *dtype = &l->h->next->data.typeval;
+       symbol *ranges_sym = l->h->next->next->data.sym;
+       list *range = sa_list(sql->sa);
+
+(void)ss;
+
+       assert(ranges_sym->token == SQL_RANGE);
+
+       if (dname && dtype) {
+               sql_dimension *dim = NULL;
+               dnode *range_value = NULL;
+
+               dim = find_sql_dimension(t, dname); //check whether the name 
has already been used
+               if (dim) {
+                       sql_error(sql, 02, "42S21!CREATE ARRAY: a column named 
'%s' already exists\n", dname);
+                       return SQL_ERR;
+               }
+
+               //if only one value is provided the dimension should be of type 
integer
+               if(dlist_length(ranges_sym->data.lval) == 1) {
+                       if(dtype->type->localtype != TYPE_int) {
+                               sql_error(sql, 02, "42S21!CREATE ARRAY: 
dimension named  '%s' should be of type integer to have a single argument", 
dname);
+                               return SQL_ERR;
+                       }
+               }
+
+               for(range_value = ranges_sym->data.lval->h ; range_value ; 
range_value = range_value->next) {
+                       atom *val = NULL;
+                       
+                       assert(range_value->data.sym->token == SQL_COLUMN);
+                       val = sql_bind_arg(sql, 
range_value->data.sym->data.lval->h->data.i_val);
+
+                       //check whether the type of the value for the range is 
compatible with the type of the dimension
+                       //I do not do any casting here, just making sure that 
the types are compatible
+                       if(!rel_check_type(sql, dtype, exp_atom(sql->sa, val), 
type_cast))
+                               return SQL_ERR;
+                       list_append(range, val);
+               }
+
+               dim = mvc_create_dimension(sql, t, dname, dtype, range);
+       }
+       return SQL_OK;
+}
+
+static int
 create_column(mvc *sql, symbol *s, sql_schema *ss, sql_table *t, int alter)
 {
        dlist *l = s->data.lval;
@@ -577,7 +626,7 @@ create_column(mvc *sql, symbol *s, sql_s
        int res = SQL_OK;
 
 (void)ss;
-       if (alter && !isTable(t)) {
+       if (alter && !(isTable(t) || isArray(t))) {
                sql_error(sql, 02, "42000!ALTER TABLE: cannot add column to 
VIEW '%s'\n", t->base.name);
                return SQL_ERR;
        }
@@ -649,7 +698,7 @@ table_element(mvc *sql, symbol *s, sql_s
 
        switch (s->token) {
        case SQL_DIMENSION:
-               fprintf(stderr, "table_element: Do something for dimensions\n");
+               res = create_dimension(sql, s, ss, t);
                break;
        case SQL_COLUMN:
                res = create_column(sql, s, ss, t, alter);
@@ -808,6 +857,28 @@ table_element(mvc *sql, symbol *s, sql_s
        return res;
 }
 
+int compute_repeats(mvc *sql, sql_table *t) {
+       node *n;
+       sql_dimension **dims_array = SA_NEW_ARRAY(sql->sa, sql_dimension*, 
list_length(t->dimensions.set));
+       lng i=0;
+
+       for(n=t->dimensions.set->h ; n->next ; n = n->next) {
+               sql_dimension *currentDim = n->data;
+               sql_dimension *nextDim = n->next->data;
+               
+               nextDim->lvl1_repeatsNum = currentDim->lvl1_repeatsNum * 
currentDim->elementsNum;
+       
+               dims_array[i] = currentDim; 
+               i++;
+       }
+       dims_array[i] = n->data;
+
+       for(i=i-1; i>=0; i--)
+               dims_array[i]->lvl2_repeatsNum = 
dims_array[i+1]->lvl2_repeatsNum * dims_array[i+1]->elementsNum;
+
+       return SQL_OK;
+}
+
 sql_rel* rel_create_array(mvc *sql, sql_schema *ss, int temp, char *sname, 
char *name, symbol *array_elements, int commit_action) {
        sql_schema *s = NULL;
 //     int instantiate = (sql->emode == m_instantiate);
@@ -853,6 +924,10 @@ sql_rel* rel_create_array(mvc *sql, sql_
                        if (res == SQL_ERR) 
                                return NULL;
                }
+
+               //compute the repeats of the dimensional columns
+               compute_repeats(sql, t);
+
                temp = (tt == tt_array)?temp:SQL_PERSIST;
                return rel_table(sql, DDL_CREATE_TABLE, sname, t, temp); //the 
array does not differ from a table at least until this point
        } 
@@ -1766,7 +1841,7 @@ rel_schemas(mvc *sql, symbol *s)
                dlist *qname = l->h->next->data.lval;
                char *sname = qname_schema(qname); //the name of the schema
                char *name = qname_table(qname); //the name of the array
-               int temp = l->h->data.i_val; //the type of the array. For now 
there is only tt_array
+               int temp = l->h->data.i_val; //SQL_PERSIST
 
                //if any of the following is not true there is an error in the 
parse tree
                assert(l->h->type == type_int); 
diff --git a/sql/server/rel_schema.h b/sql/server/rel_schema.h
--- a/sql/server/rel_schema.h
+++ b/sql/server/rel_schema.h
@@ -32,5 +32,6 @@ extern sql_rel *rel_list(sql_allocator *
 extern sql_table * mvc_create_table_as_subquery( mvc *sql, sql_rel *sq, 
sql_schema *s, char *tname, dlist *column_spec, int temp, int commit_action );
 
 extern sql_rel *rel_create_array(mvc *sql, sql_schema *ss, int temp, char 
*sname, char *name, symbol *table_elements_or_subquery, int commit_action);
+extern int compute_repeats(mvc*, sql_table*);
 
 #endif /*_REL_SCHEMA_H_*/
diff --git a/sql/server/rel_select.c b/sql/server/rel_select.c
--- a/sql/server/rel_select.c
+++ b/sql/server/rel_select.c
@@ -2554,7 +2554,7 @@ rel_compare(mvc *sql, sql_rel *rel, symb
                                return NULL;
                }
        } else {
-               /* first try without current relation, too see if there
+               /* first try without current relation, to see if there
                   are correlations with the outer relation */
                sql_rel *r = rel_subquery(sql, NULL, ro, ek, APPLY_JOIN);
 
diff --git a/sql/server/sql_mvc.c b/sql/server/sql_mvc.c
--- a/sql/server/sql_mvc.c
+++ b/sql/server/sql_mvc.c
@@ -1046,8 +1046,8 @@ mvc_create_column(mvc *m, sql_table *t, 
 {
        if (mvc_debug)
                fprintf(stderr, "#mvc_create_column %s %s %s\n", t->base.name, 
name, tpe->type->sqlname);
-       if ((isDeclaredTable(t) || isDeclaredArray(t)) && (!t->s || 
strcmp(t->s->base.name, dt_schema))) 
-               /* declared tables or arrays should not end up in the catalog */
+       if (isDeclaredTable(t) && (!t->s || strcmp(t->s->base.name, 
dt_schema))) 
+               /* declared tables should not end up in the catalog */
                return create_sql_column(m->sa, t, name, tpe);
        else
                return sql_trans_create_column(m->session->tr, t, name, tpe);
@@ -1064,6 +1064,21 @@ mvc_drop_column(mvc *m, sql_table *t, sq
                sql_trans_drop_column(m->session->tr, t, col->base.id,  
drop_action ? DROP_CASCADE_START : DROP_RESTRICT);
 }
 
+sql_dimension *
+mvc_create_dimension(mvc *m, sql_table *t, const char *name, sql_subtype *tpe, 
list* dimensionRange)
+{
+       if (mvc_debug)
+               fprintf(stderr, "#mvc_create_dimension %s %s %s\n", 
t->base.name, name, tpe->type->sqlname);
+       if (isDeclaredArray(t) && (!t->s || strcmp(t->s->base.name, 
dt_schema))) {
+               /* declared arrays should not end up in the catalog */
+               return create_sql_dimension(m->sa, t, name, tpe, 
dimensionRange);
+       }
_______________________________________________
checkin-list mailing list
[email protected]
https://www.monetdb.org/mailman/listinfo/checkin-list

Reply via email to