Changeset: 553f9299d443 for MonetDB URL: https://dev.monetdb.org/hg/MonetDB/rev/553f9299d443 Modified Files: gdk/gdk.h gdk/gdk_atoms.c gdk/gdk_atoms.h gdk/gdk_value.c Branch: nilmask Log Message:
Implemented some basic stuff for unsigned types. diffs (truncated from 499 to 300 lines): diff --git a/gdk/gdk.h b/gdk/gdk.h --- a/gdk/gdk.h +++ b/gdk/gdk.h @@ -458,9 +458,13 @@ enum { typedef bool msk; typedef int8_t bit; typedef int8_t bte; +typedef uint8_t ubte; typedef int16_t sht; +typedef uint16_t usht; +typedef uint32_t uint; /* typedef int64_t lng; -- defined in gdk_system.h */ typedef uint64_t ulng; +/* hge and uhge are defined in monetdb_config.h */ #define SIZEOF_OID SIZEOF_SIZE_T typedef size_t oid; @@ -648,6 +652,13 @@ typedef struct { hge hval; #endif uuid uval; + ubte ubtval; + usht ushval; + uint uival; + ulng ulval; +#ifdef HAVE_HGE + uhge uhval; +#endif } val; size_t len; short vtype; @@ -1952,13 +1963,18 @@ VALptr(const ValRecord *v) case TYPE_void: return (const void *) &v->val.oval; case TYPE_msk: return (const void *) &v->val.mval; case TYPE_bte: return (const void *) &v->val.btval; + case TYPE_ubte: return (const void *) &v->val.ubtval; case TYPE_sht: return (const void *) &v->val.shval; + case TYPE_usht: return (const void *) &v->val.ushval; case TYPE_int: return (const void *) &v->val.ival; + case TYPE_uint: return (const void *) &v->val.uival; case TYPE_flt: return (const void *) &v->val.fval; case TYPE_dbl: return (const void *) &v->val.dval; + case TYPE_ulng: return (const void *) &v->val.ulval; case TYPE_lng: return (const void *) &v->val.lval; #ifdef HAVE_HGE case TYPE_hge: return (const void *) &v->val.hval; + case TYPE_uhge: return (const void *) &v->val.uhval; #endif case TYPE_uuid: return (const void *) &v->val.uval; case TYPE_ptr: return (const void *) &v->val.pval; diff --git a/gdk/gdk_atoms.c b/gdk/gdk_atoms.c --- a/gdk/gdk_atoms.c +++ b/gdk/gdk_atoms.c @@ -88,6 +88,38 @@ dblCmp(const dbl *l, const dbl *r) return is_dbl_nil(*l) ? -!is_dbl_nil(*r) : is_dbl_nil(*r) ? 1 : (*l > *r) - (*l < *r); } +static int +ubteCmp(const ubte *l, const ubte *r) +{ + return (*l > *r) - (*l < *r); +} + +static int +ushtCmp(const usht *l, const usht *r) +{ + return (*l > *r) - (*l < *r); +} + +static int +uintCmp(const uint *l, const uint *r) +{ + return (*l > *r) - (*l < *r); +} + +static int +ulngCmp(const ulng *l, const ulng *r) +{ + return (*l > *r) - (*l < *r); +} + +#ifdef HAVE_HGE +static int +uhgeCmp(const uhge *l, const uhge *r) +{ + return (*l > *r) - (*l < *r); +} +#endif + /* * @- inline hash routines * Return some positive integer derived from one atom value. @@ -878,6 +910,137 @@ hgeFromStr(const char *src, size_t *len, } #endif +#ifdef HAVE_HGE +const uhge maxunum = ((uhge) UINT64_C(18446744073709551615) << 64) | + (uhge) UINT64_C(18446744073709551615); /* (1 << 128) - 1: 340282366920938463463374607431768211455*/ +#else +const ulng maxunum = UINT64_C(18446744073709551615); /* (1 << 64) - 1 */ +#endif + +static ssize_t +unumFromStr(const char *src, size_t *len, void **dst, int tp) +{ + const char *p = src; + size_t sz = ATOMsize(tp); +#ifdef HAVE_HGE + uhge base = 0; +#else + ulng base = 0; +#endif + + /* a valid unsigned number has the following syntax: + * [0-9]+(LL)? -- PCRE syntax, or in other words + * one or more digits, optional LL + * embedded spaces are not allowed + * the optional LL at the end are only allowed for lng and hge + * values */ + atommem(sz); + + if (strNil(src)) { + GDKerror("not a number"); + goto bailout; + } + + while (GDKisspace(*p)) + p++; + if (!GDKisdigit(*p)) { + GDKerror("not a number"); + goto bailout; + } + do { + int dig = base10(*p); + if (base > maxunum / 10 || + (base == maxunum / 10 && dig > 5)) { + /* overflow */ + goto overflow; + } + base = 10 * base + dig; + p++; + } while (GDKisdigit(*p)); + switch (sz) { + case 1: + if (base > GDK_ubte_max) + goto overflow; + **(ubte **) dst = (ubte) base; + break; + case 2: + if (base > GDK_usht_max) + goto overflow; + **(usht **) dst = (usht) base; + break; + case 4: + if (base > GDK_uint_max) + goto overflow; + **(uint **) dst = (uint) base; + break; + case 8: +#ifndef HAVE_HGE + if (base > GDK_ulng_max) + goto overflow; +#endif + **(ulng **) dst = (ulng) base; + if (p[0] == 'L' && p[1] == 'L') + p += 2; + break; +#ifdef HAVE_HGE + case 16: + **(uhge **) dst = (uhge) base; + if (p[0] == 'L' && p[1] == 'L') + p += 2; + break; +#endif + } + while (GDKisspace(*p)) + p++; + return (ssize_t) (p - src); + + overflow: + while (GDKisdigit(*p)) + p++; + GDKerror("overflow: \"%.*s\" does not fit in %s\n", + (int) (p - src), src, ATOMname(tp)); + bailout: + memset(*dst, 0, sz); + return -1; +} + +static ssize_t +ubteFromStr(const char *src, size_t *len, ubte **dst, bool external) +{ + (void) external; + return unumFromStr(src, len, (void **) dst, TYPE_ubte); +} + +static ssize_t +ushtFromStr(const char *src, size_t *len, usht **dst, bool external) +{ + (void) external; + return unumFromStr(src, len, (void **) dst, TYPE_usht); +} + +static ssize_t +uintFromStr(const char *src, size_t *len, uint **dst, bool external) +{ + (void) external; + return unumFromStr(src, len, (void **) dst, TYPE_uint); +} + +static ssize_t +ulngFromStr(const char *src, size_t *len, ulng **dst, bool external) +{ + (void) external; + return unumFromStr(src, len, (void **) dst, TYPE_ulng); +} + +#ifdef HAVE_HGE +static ssize_t +uhgeFromStr(const char *src, size_t *len, uhge **dst, bool external) +{ + (void) external; + return unumFromStr(src, len, (void **) dst, TYPE_uhge); +} +#endif + #define atom_io(TYPE, NAME, CAST) \ static TYPE * \ TYPE##Read(TYPE *A, size_t *dstlen, stream *s, size_t cnt) \ @@ -979,7 +1142,48 @@ hgeToStr(char **dst, size_t *len, const return strlen(*dst); } } -atom_io(hge, Hge, hge) +atom_io(hge, Hge, hge); +#endif + +#define uatomtostr(TYPE, FMT, FMTCAST) \ +static ssize_t \ +u##TYPE##ToStr(char **dst, size_t *len, const u##TYPE *src, bool external) \ +{ \ + (void) external; \ + atommem(TYPE##Strlen); \ + return snprintf(*dst, *len, FMT, FMTCAST *src); \ +} + +uatomtostr(bte, "%hhu", ) +uatomtostr(sht, "%hu", ) +uatomtostr(int, "%u", ) +uatomtostr(lng, ULLFMT, ) + +#ifdef HAVE_HGE +#define HGE_LL018FMT "%018" PRId64 +#define HGE_LL18DIGITS LL_CONSTANT(1000000000000000000) +#define HGE_ABS(a) (((a) < 0) ? -(a) : (a)) +static ssize_t +uhgeToStr(char **dst, size_t *len, const uhge *src, bool external) +{ + atommem(hgeStrlen); + if (*src <= (hge) GDK_lng_max) { + ulng s = (ulng) *src; + return ulngToStr(dst, len, &s, external); + } + char *p = *dst; + uhge v = *src; + do { + *p++ = (v % 10) + '0'; + v /= 10; + } while (v != 0); + for (int i = (int) (p - *dst) - 1, j = 0; i > j; i--, j++) { + char c = (*dst)[i]; + (*dst)[i] = (*dst)[j]; + (*dst)[j] = c; + } + return (ssize_t) (p - *dst); +} #endif ssize_t @@ -1695,13 +1899,13 @@ atomDesc BATatoms[MAXATOMS] = { .name = "ubte", .storage = TYPE_bte, .linear = true, - .size = sizeof(bte), + .size = sizeof(ubte), .atomNull = NULL, - .atomFromStr = (ssize_t (*)(const char *, size_t *, void **, bool)) bteFromStr, - .atomToStr = (ssize_t (*)(char **, size_t *, const void *, bool)) bteToStr, + .atomFromStr = (ssize_t (*)(const char *, size_t *, void **, bool)) ubteFromStr, + .atomToStr = (ssize_t (*)(char **, size_t *, const void *, bool)) ubteToStr, .atomRead = (void *(*)(void *, size_t *, stream *, size_t)) bteRead, .atomWrite = (gdk_return (*)(const void *, stream *, size_t)) bteWrite, - .atomCmp = (int (*)(const void *, const void *)) bteCmp, + .atomCmp = (int (*)(const void *, const void *)) ubteCmp, .atomHash = (BUN (*)(const void *)) bteHash, }, [TYPE_sht] = { @@ -1721,13 +1925,12 @@ atomDesc BATatoms[MAXATOMS] = { .name = "usht", _______________________________________________ checkin-list mailing list -- checkin-list@monetdb.org To unsubscribe send an email to checkin-list-le...@monetdb.org