From 091c9c011e398c72a244813a0a0ed54424b31b52 Mon Sep 17 00:00:00 2001 From: Gregory Lirent Date: Mon, 6 Jun 2022 23:43:18 +0300 Subject: [PATCH 1/4] Fix vnode creation --- src/vnode.c | 37 +++++++++++++++++++++++++------------ src/vtype.c | 4 ++-- 2 files changed, 27 insertions(+), 14 deletions(-) diff --git a/src/vnode.c b/src/vnode.c index 6ec31dd..0963a99 100644 --- a/src/vnode.c +++ b/src/vnode.c @@ -5,6 +5,16 @@ #include "__internal/vnode.h" #include "../include/string.h" +static vtype internal_round(u64_t* x, ldbl_t v) { + if (v > 0) { + *x = (u64_t)(v + 0.5); + return VTYPE_UINT64; + } else { + *x = (s64_t)(v - 0.5); + return VTYPE_INT64; + } +} + /*#####################################################################################################################*/ @@ -12,25 +22,28 @@ static vnode_t create_value(vtype xt, const void* v, vtype t) { var_t _; if (t == VTYPE_FLOAT) { - _.u64 = (s64_t)roundf(*(fl_t*)v); - t = VTYPE_INT64; + t = internal_round(&_.u64, *(fl_t*)v); } else if (t == VTYPE_DOUBLE) { - _.u64 = (s64_t)round (*(dbl_t*)v); - t = VTYPE_INT64; - } else { - _.u64 = (s64_t)roundl(*(ldbl_t*)v); - t = VTYPE_INT64; + t = internal_round(&_.u64, *(dbl_t*)v); + } else if (t == VTYPE_LDOUBLE) { + t = internal_round(&_.u64, *(ldbl_t*)v); } if (sizeof(void*) == 8) { - if (t == VTYPE_UINT8 || t == VTYPE_INT8 || t == VTYPE_BOOLEAN ) { + if (t == VTYPE_UINT8 || t == VTYPE_BOOLEAN ) { _.u64 = *(u8_t*)v; - } else if (t == VTYPE_UINT16 || t == VTYPE_INT16) { + } else if (t == VTYPE_UINT16) { _.u64 = *(u16_t*)v; - } else if (t == VTYPE_UINT32 || t == VTYPE_INT32 || (sizeof(void*) == 4 && t == VTYPE_POINTER)) { + } else if (t == VTYPE_UINT32 || (sizeof(void*) == 4 && t == VTYPE_POINTER)) { _.u64 = *(u32_t*)v; } else if (t == VTYPE_UINT64 || t == VTYPE_INT64 || (sizeof(void*) == 8 && t == VTYPE_POINTER)) { _.u64 = *(u64_t*)v; + } else if (t == VTYPE_INT8) { + _.u64 = *(s8_t*)v; + } else if (t == VTYPE_INT16) { + _.u64 = *(s16_t*)v; + } else if (t == VTYPE_INT32) { + _.u64 = *(s32_t*)v; } if (is_big_endian) { @@ -105,7 +118,7 @@ static vnode_t create_float(vtype xt, const void* v, vtype t) { _.ptr = memndup(&_.f, sizeof(_.f)); } } else if (xt == VTYPE_DOUBLE) { - _.f = _.d; + _.d = _.ld; if (!is_permissible(dbl_t)) { _.ptr = memndup(&_.d, sizeof(_.d)); } @@ -267,7 +280,7 @@ vnode_t libcdsb_vnode_create_target(vtype xt, const void* v, vtype t) { if (xt <= VTYPE_INT64) return create_value(xt, v, t); - return create_value(xt, v, t); + return create_float(xt, v, t); } else if (t == VTYPE_POINTER && (t = xt) > VTYPE_STRING) { v = *(void**)v; } diff --git a/src/vtype.c b/src/vtype.c index 266ecda..e3561db 100644 --- a/src/vtype.c +++ b/src/vtype.c @@ -30,6 +30,8 @@ static ldbl_t normalize_value(const void* v, vtype t) { } else return abs(*(ldbl_t*)v) <= LDBL_EPSILON ? 0 : *(ldbl_t*)v; } +/*#####################################################################################################################*/ + int libcdsb_vtype_compare_values(const void* s0, vtype t0, const void* s1, vtype t1) { if (t0 == t1) return libcdsb_vtype_compare_values_eq(s0, s1, t0); @@ -45,8 +47,6 @@ int libcdsb_vtype_compare_values(const void* s0, vtype t0, const void* s1, vtype return t0 - t1; } -/*#####################################################################################################################*/ - int libcdsb_vtype_compare_values_eq(const void* s0, const void* s1, vtype t) { From 09acdb5118d6a313fd787e43c2b764f42c3f4486 Mon Sep 17 00:00:00 2001 From: Gregory Lirent Date: Mon, 6 Jun 2022 23:45:11 +0300 Subject: [PATCH 2/4] Fix rbtree rotation --- src/rbtree.c | 17 ++++++----------- 1 file changed, 6 insertions(+), 11 deletions(-) diff --git a/src/rbtree.c b/src/rbtree.c index 22dee93..a8681b7 100644 --- a/src/rbtree.c +++ b/src/rbtree.c @@ -32,19 +32,15 @@ static inline void rotate(rbnode_t **x, rbnode_t *c, rbdir_t d) { rbdir_inv(c, d) = rbdir_dir(n, d); n->parent = c->parent; - if (!rbnode_is_empty(rbdir_dir(n, d))) { + if (!rbnode_is_empty(rbdir_dir(n, d))) rbdir_dir(n, d)->parent = c; - } if (!rbnode_is_root(c)) { - rbnode_t* p = c->parent; - - if (rbdir_dir(p, d) == c) { - rbdir_dir(p, d) = n; - } else rbdir_inv(c, d) = n; + if (c->parent->left == c) c->parent->left = n; + else c->parent->right = n; } else *x = n; - rbdir_inv(n, d) = c; + rbdir_dir(n, d) = c; c->parent = n; } @@ -202,7 +198,6 @@ static void delete_fixup(rbnode_t** x, rbnode_t* n) { rbnode_t* libcdsb_rbtree_node_delete(rbnode_t** x, rbnode_t* c) { rbnode_t *n, *t; int s; - void* v; s = c->colored; @@ -269,7 +264,7 @@ void libcdsb_rbtree_node_fixup(rbnode_t** x, rbnode_t* n) { p = n->parent; gp = p->parent; } - p->colored = 0; + p->colored = 0; gp->colored = 1; rotate(x, gp, d[0]); @@ -346,7 +341,7 @@ void libcdsb_rbtree_iter_reset(rbiter_t* iter) { } -rbnode_t* hhttpc_rbtree_iter_next(rbiter_t* iter) { +rbnode_t* libcdsb_rbtree_iter_next(rbiter_t* iter) { rbnode_t* c; From c17edda61c58772930a66fd4c8d711c05f99cc9c Mon Sep 17 00:00:00 2001 From: Gregory Lirent Date: Mon, 6 Jun 2022 23:46:55 +0300 Subject: [PATCH 3/4] Fix set (extra) insertion & foreach --- src/set/extra.c | 34 ++++++++++++++++++++-------------- 1 file changed, 20 insertions(+), 14 deletions(-) diff --git a/src/set/extra.c b/src/set/extra.c index 0c68389..3c3be91 100644 --- a/src/set/extra.c +++ b/src/set/extra.c @@ -36,33 +36,38 @@ _Bool libcdsb_vset_find(val_t* x, set_t* s, const void* v, vtype t, _Bool cut) { _Bool libcdsb_vset_insert(set_t* x, const void* v, vtype t) { - int cmp; + int cmp; rbnode_t* n; rbnode_t* p; + vnode_t vn; - n = x->root; + n = x->root; + vn = vnode_tcreate(x->type, v, t); + t = x->type; + v = vnode_peek(&vn, t); if (!rbnode_is_empty(n)) { do { - p = n; - cmp = vtype_compare(vnode_peek(&n->value, x->type), x->type, v, t); + p = n; + cmp = vtype_compare(v, t, vnode_peek(&n->value, t), t); - if (cmp == 0) return false; + if (cmp == 0) { + vnode_free(&vn, t); + return false; + } - n = (cmp > 0) ? n->left : n->right; + n = (cmp < 0) ? n->left : n->right; } while (!rbnode_is_empty(n)); - n = rbnode_create(0, p, 1); + n = rbnode_create(vn, p, 1); - if (cmp > 0) p->left = n; + if (cmp < 0) p->left = n; else p->right = n; - if (!rbnode_is_root(n->parent)) + if (!rbnode_is_root(p)) rbnode_fixup(&x->root, n); - } else n = x->root = rbnode_create(0, p, 1); - - n->value = vnode_tcreate(x->type, v, t); + } else n = x->root = rbnode_create(vn, rbnode_empty, 0); return true; } @@ -74,10 +79,11 @@ _Bool libcdsb_vset_insert(set_t* x, const void* v, vtype t) { int libcdsb_vset_foreach(const vtype_set* x, int (*callback)(const void* value, vtype type)) { rbiter_t i; int r; + rbnode_t* c; if (rbiter_init(&i, &x->root, 0)) { - while (!rbnode_is_empty(rbiter_next(&i))) { - if ((r = callback(vnode_peek(&i.cursor->value, x->type), x->type))) + while (!rbnode_is_empty(c = rbiter_next(&i))) { + if ((r = callback(vnode_peek(&c->value, x->type), x->type))) return r; } } From 9a34d1d71fc9a75708d244204eb5bb8588696798 Mon Sep 17 00:00:00 2001 From: Gregory Lirent Date: Mon, 6 Jun 2022 23:47:26 +0300 Subject: [PATCH 4/4] Update headers --- include/extra/array.h | 2 +- include/set.h | 6 +++--- src/array/extra.c | 2 +- 3 files changed, 5 insertions(+), 5 deletions(-) diff --git a/include/extra/array.h b/include/extra/array.h index af89ba0..fd662a9 100644 --- a/include/extra/array.h +++ b/include/extra/array.h @@ -17,6 +17,6 @@ extern ssize_t libcdsb_array_get(vtype_value* x, vtype_array* s, ssize_t index, extern ssize_t libcdsb_array_find(const vtype_array* x, const void* value, vtype value_type) LIBCDSB_nt__ LIBCDSB_nn1__; extern ssize_t libcdsb_array_push( vtype_array* x, const void* value, vtype value_type) LIBCDSB_nt__ LIBCDSB_nn1__; -extern int libcdsb_array_foreach(vtype_array* x, int (*callback)(void* value, ssize_t index, vtype type)) LIBCDSB_nt__ LIBCDSB_nn12__; +extern int libcdsb_array_foreach(const vtype_array* x, int (*callback)(void* value, ssize_t index, vtype type)) LIBCDSB_nt__ LIBCDSB_nn12__; #endif /* LIBCDSB_EXTRA_ARRAY_H */ diff --git a/include/set.h b/include/set.h index cb0202e..11e265b 100644 --- a/include/set.h +++ b/include/set.h @@ -9,10 +9,10 @@ extern void vset_init(vtype_set* x, vtype type); -#define vset_remove(x, value) _LIBCDSB_Generic (libcdsb_vset, touch, key)(x, value, 1) -#define vset_push(x, value) _LIBCDSB_Generic (libcdsb_vset, push, key)(x, value) +#define vset_remove(x, value) _LIBCDSB_Generic (libcdsb_vset, touch, value)(x, value, 1) +#define vset_push(x, value) _LIBCDSB_Generic (libcdsb_vset, push, value)(x, value) -#define in_vset(x, value) _LIBCDSB_Generic (libcdsb_vset, touch, key)(x, value, 0) +#define in_vset(x, value) _LIBCDSB_Generic (libcdsb_vset, touch, value)(x, value, 0) extern _Bool libcdsb_vset_push_pointer(vtype_set* x, const void* value); extern _Bool libcdsb_vset_push_cstring(vtype_set* x, const char* value); diff --git a/src/array/extra.c b/src/array/extra.c index 99070e1..211d423 100644 --- a/src/array/extra.c +++ b/src/array/extra.c @@ -76,7 +76,7 @@ ssize_t libcdsb_array_get(val_t* x, arr_t* s, ssize_t i, _Bool cut) { /*#####################################################################################################################*/ -int libcdsb_array_foreach(vtype_array* x, int (*callback)(void* value, ssize_t index, vtype type)) { +int libcdsb_array_foreach(const vtype_array* x, int (*callback)(void* value, ssize_t index, vtype type)) { void* p; void* e;