Changeset: 6be8d05dfd8f for MonetDB URL: https://dev.monetdb.org/hg/MonetDB?cmd=changeset;node=6be8d05dfd8f Modified Files: clients/Tests/exports.stable.out gdk/gdk_cand.c gdk/gdk_cand.h monetdb5/mal/mal_interpreter.c sql/backends/monet5/sql.c Branch: candidate-exceptions Log Message:
introduced BATnegcands and BATcands sofar used in the SQLtids and mal main loop. (grafted from bc5533df50034ab8374cc13e3ba32e24f1d7f2df) diffs (240 lines): diff --git a/clients/Tests/exports.stable.out b/clients/Tests/exports.stable.out --- a/clients/Tests/exports.stable.out +++ b/clients/Tests/exports.stable.out @@ -107,6 +107,7 @@ dbl BATcalcvariance_sample(dbl *avgp, BA BAT *BATcalcxor(BAT *b1, BAT *b2, BAT *s); BAT *BATcalcxorcst(BAT *b, const ValRecord *v, BAT *s); bool BATcandcontains(BAT *s, oid o); +BAT *BATcands(BAT *negcands); gdk_return BATclear(BAT *b, bool force); void BATcommit(BAT *b); BAT *BATconstant(oid hseq, int tt, const void *val, BUN cnt, role_t role); @@ -154,6 +155,7 @@ void *BATmin(BAT *b, void *aggr); void *BATmin_skipnil(BAT *b, void *aggr, bit skipnil); gdk_return BATmode(BAT *b, bool transient); void BATmsync(BAT *b); +int BATnegcands(BAT *cands, BAT *odels); bool BATordered(BAT *b); bool BATordered_rev(BAT *b); gdk_return BATorderidx(BAT *b, bool stable); diff --git a/gdk/gdk_cand.c b/gdk/gdk_cand.c --- a/gdk/gdk_cand.c +++ b/gdk/gdk_cand.c @@ -919,3 +919,73 @@ canditer_slice2(struct canditer *ci, BUN } return virtualize(bn); } + +int +BATnegcands(BAT *dense_cands, BAT *odels) +{ + const char *nme; + Heap *dels; + char *fname = 0; + + nme = BBP_physical(dense_cands->batCacheid); + if ((dels = (Heap*)GDKzalloc(sizeof(Heap))) == NULL || + (dels->farmid = BBPselectfarm(dense_cands->batRole, dense_cands->ttype, varheap)) < 0 || + (fname = GDKfilepath(NOFARM, NULL, nme, "theap")) == NULL){ + if (fname) + GDKfree(fname); + GDKfree(dels); + return GDK_FAIL; + } + //dels->farmid = dense_cands->theap.farmid; + strncpy(dels->filename, fname, sizeof(dels->filename)); + + if (HEAPalloc(dels, BATcount(odels), sizeof(oid)) != GDK_SUCCEED) + return GDK_FAIL; + dels->parentid = dense_cands->batCacheid; + memcpy(dels->base, Tloc(odels,0), sizeof(oid)*BATcount(odels)); + dels->free += sizeof(oid)*BATcount(odels); + dense_cands->batDirtydesc = TRUE; + dense_cands->tvheap = dels; + return GDK_SUCCEED; +} + +BAT * +BATcands(BAT *neg_cands) +{ + BAT *bn; + size_t dcnt = neg_cands->tvheap->free/sizeof(oid); + oid ncf, ncl, *restrict p; + const oid *restrict dp, *dpe; + + bn = COLnew(0, TYPE_oid, BATcount(neg_cands), TRANSIENT); + if (bn == NULL) + return NULL; + ncf = BUNtoid(neg_cands, 0); + ncl = BUNtoid(neg_cands, BUNlast(neg_cands) - 1); + BAThseqbase(bn, ncf); + + /* neg_cands is dense */ + dp = (const oid *)neg_cands->tvheap->base; + dpe = dp + dcnt; + p = Tloc(bn, 0); + /* first skip deletes outside of the dense range */ + while (dp < dpe && *dp < ncf) + dp++; + while (ncf <= ncl && dp < dpe) { + if (ncf < *dp) { + *p++ = ncf++; + } else if (ncf == *dp) { + dp++; + ncf++; + } + } + while (ncf <= ncl) + *p++ = ncf++; + BATsetcount(bn, (BUN) (p - (oid *) Tloc(bn, 0))); + bn->trevsorted = BATcount(bn) <= 1; + bn->tsorted = true; + bn->tkey = true; + bn->tnil = false; + bn->tnonil = true; + return bn; +} diff --git a/gdk/gdk_cand.h b/gdk/gdk_cand.h --- a/gdk/gdk_cand.h +++ b/gdk/gdk_cand.h @@ -74,5 +74,7 @@ gdk_export void canditer_reset(struct ca gdk_export BUN canditer_search(struct canditer *ci, oid o, bool next); gdk_export BAT *canditer_slice(struct canditer *ci, BUN lo, BUN hi); gdk_export BAT *canditer_slice2(struct canditer *ci, BUN lo1, BUN hi1, BUN lo2, BUN hi2); +gdk_export int BATnegcands( BAT *cands, BAT *odels); +gdk_export BAT *BATcands( BAT *negcands); #endif /* _GDK_CAND_H_ */ diff --git a/monetdb5/mal/mal_interpreter.c b/monetdb5/mal/mal_interpreter.c --- a/monetdb5/mal/mal_interpreter.c +++ b/monetdb5/mal/mal_interpreter.c @@ -18,6 +18,7 @@ #include "mal_debugger.h" /* for mdbStep() */ #include "mal_type.h" #include "mal_private.h" +#include "gdk_cand.h" static lng qptimeout = 0; /* how often we print still running queries (usec) */ @@ -443,6 +444,40 @@ callMAL(Client cntxt, MalBlkPtr mb, MalS return ret; } + +static void +sqlHandleTids(Client cntxt, MalBlkPtr mb, InstrPtr pci, MalStkPtr stk, int cmd) +{ + int i; + + (void)cntxt; + (void)stk; + + for(i = pci->retc; i< pci->argc; i++) { + int a = getArg(pci, i); + int t = getArgType(mb, pci, i); + + if (isaBatType(t) && getBatType(t) == TYPE_oid) { + bat bid; + BAT *_b; + + MT_lock_set(&mal_contextLock); + bid = stk->stk[a].val.bval; + _b = BATdescriptor(bid); + if (_b && _b->tvheap) { + BAT *bn; + printf("#found neg tids (%s:%s:%d)\n", cmd?"command":"pattern", pci->fcnname, i); + + bn = BATcands(_b); + BBPkeepref(stk->stk[a].val.bval = bn->batCacheid); + BBPrelease(bid); + } + MT_lock_unset(&mal_contextLock); + if(_b) BBPunfix(bid); + } + } +} + /* * The core of the interpreter is presented next. It takes the context * information and starts the interpretation at the designated @@ -644,6 +679,7 @@ str runMALsequence(Client cntxt, MalBlkP } break; case PATcall: + sqlHandleTids(cntxt, mb, pci, stk, 0); if (pci->fcn == NULL) { ret = createException(MAL,"mal.interpreter", "address of pattern %s.%s missing", pci->modname, pci->fcnname); } else { @@ -674,6 +710,7 @@ str runMALsequence(Client cntxt, MalBlkP } break; case CMDcall: + sqlHandleTids(cntxt, mb, pci, stk, 1); ret = malCommandCall(stk, pci); #ifndef NDEBUG if (ret == MAL_SUCCEED) { 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 @@ -40,6 +40,7 @@ #include "mal_instruction.h" #include "mal_resource.h" #include "mal_authorize.h" +#include "gdk_cand.h" static int rel_is_table(sql_rel *rel) @@ -2177,6 +2178,7 @@ BATleftproject(bat *Res, const bat *Col, return MAL_SUCCEED; } + /* str SQLtid(bat *result, mvc *m, str *sname, str *tname) */ str SQLtid(Client cntxt, MalBlkPtr mb, MalStkPtr stk, InstrPtr pci) @@ -2235,14 +2237,35 @@ SQLtid(Client cntxt, MalBlkPtr mb, MalSt if (tids == NULL) throw(SQL, "sql.tid", SQLSTATE(HY001) MAL_MALLOC_FAIL); + /* V1 of the deleted list + * 1) in case of deletes, bind_del, order it, put into a heap(of the tids bat) + * 2) in mal recognize this type of bat. + * 3) if function can handle it pass along, else fall back to first diff. + * */ if ((dcnt = store_funcs.count_del(tr, t)) > 0) { - BAT *d = store_funcs.bind_del(tr, t, RD_INS); - BAT *diff; + BAT *d = store_funcs.bind_del(tr, t, RD_INS), *o; + int ret = GDK_SUCCEED; + if (d == NULL) { BBPunfix(tids->batCacheid); throw(SQL,"sql.tid", SQLSTATE(45002) "Can not bind delete column"); } + ret = BATsort(&o, NULL, NULL, d, NULL, NULL, false, false, false); + BBPunfix(d->batCacheid); + if (ret != GDK_SUCCEED) + throw(MAL, "sql.tids", SQLSTATE(HY001) MAL_MALLOC_FAIL); + + /* TODO handle dense o, ie full range out of the dense tids, could be at beginning or end (reduce range of tids) + * else materialize */ + /* copy into heap */ + ret = BATnegcands(tids, o); + BBPunfix(o->batCacheid); + if (ret != GDK_SUCCEED) + throw(MAL, "sql.tids", SQLSTATE(45003) "TIDdeletes failed"); + +/* + BAT *diff; diff = BATdiff(tids, d, NULL, NULL, false, false, BUN_NONE); // assert(pci->argc == 6 || BATcount(diff) == (nr-dcnt)); if( !(pci->argc == 6 || BATcount(diff) == (nr-dcnt)) ) @@ -2253,6 +2276,7 @@ SQLtid(Client cntxt, MalBlkPtr mb, MalSt throw(SQL,"sql.tid", SQLSTATE(45002) "Cannot subtract delete column"); BAThseqbase(diff, sb); tids = diff; +*/ } BBPkeepref(*res = tids->batCacheid); return msg; _______________________________________________ checkin-list mailing list checkin-list@monetdb.org https://www.monetdb.org/mailman/listinfo/checkin-list