Changeset: da41913be745 for MonetDB
URL: https://dev.monetdb.org/hg/MonetDB/rev/da41913be745
Modified Files:
gdk/gdk_atoms.c
gdk/gdk_atoms.h
gdk/gdk_string.c
geom/monetdb5/geom_atoms.c
monetdb5/modules/atoms/json.c
Branch: Dec2025
Log Message:
Fixed interface of atomRead function to read binary atoms from a stream.
If the function fails, it returns NULL and the buffer passed as argument
is unaffected. Before, it was sometimes unaffected and sometimes freed.
diffs (truncated from 312 to 300 lines):
diff --git a/gdk/gdk_atoms.c b/gdk/gdk_atoms.c
--- a/gdk/gdk_atoms.c
+++ b/gdk/gdk_atoms.c
@@ -869,19 +869,22 @@ TYPE##Read(allocator *ma, TYPE *A, size_
if (ma) { \
a = ma_realloc(ma, a, cnt * sizeof(TYPE), *dstlen); \
} else { \
- GDKfree(a); \
a = GDKmalloc(cnt * sizeof(TYPE)); \
} \
if (a == NULL) \
return NULL; \
- *dstlen = cnt * sizeof(TYPE); \
} \
if (mnstr_read##NAME##Array(s, (CAST *) a, cnt) == 0 || \
mnstr_errnr(s) != MNSTR_NO__ERROR) { \
- if (a != A) \
+ if (ma == NULL && a != A) \
GDKfree(a); \
return NULL; \
} \
+ if (a != A) { \
+ if (ma == NULL) \
+ GDKfree(A); \
+ *dstlen = cnt * sizeof(TYPE); \
+ } \
return a; \
} \
static gdk_return \
@@ -912,18 +915,21 @@ mskRead(allocator *ma, msk *A, size_t *d
if (ma) {
a = ma_realloc(ma, a, 1, *dstlen);
} else {
- GDKfree(a);
a = GDKmalloc(1);
}
if (a == NULL)
return NULL;
- *dstlen = 1;
}
if (mnstr_readBte(s, &v) != 1) {
- if (a != A)
+ if (ma == NULL && a != A)
GDKfree(a);
return NULL;
}
+ if (a != A) {
+ if (ma == NULL)
+ GDKfree(A);
+ *dstlen = 1;
+ }
*a = v != 0;
return a;
}
@@ -1350,18 +1356,21 @@ UUIDread(allocator *ma, void *U, size_t
if (ma) {
u = ma_realloc(ma, u, cnt * sizeof(uuid), *dstlen);
} else {
- GDKfree(u);
u = GDKmalloc(cnt * sizeof(uuid));
}
if (u == NULL)
return NULL;
- *dstlen = cnt * sizeof(uuid);
}
if (mnstr_read(s, u, UUID_SIZE, cnt) < (ssize_t) cnt) {
- if (u != U)
+ if (ma == NULL && u != (uuid *) U)
GDKfree(u);
return NULL;
}
+ if (u != (uuid *) U) {
+ if (ma == NULL)
+ GDKfree(U);
+ *dstlen = cnt * sizeof(uuid);
+ }
return u;
}
@@ -1500,18 +1509,21 @@ INET4read(allocator *ma, void *U, size_t
if (ma) {
u = ma_realloc(ma, u, cnt * sizeof(inet4), *dstlen);
} else {
- GDKfree(u);
u = GDKmalloc(cnt * sizeof(inet4));
}
if (u == NULL)
return NULL;
- *dstlen = cnt * sizeof(inet4);
}
- if (mnstr_read(s, u, 4, cnt) < (ssize_t) cnt) {
- if (u != U)
+ if (mnstr_read(s, u, sizeof(inet4), cnt) < (ssize_t) cnt) {
+ if (ma == NULL && u != (inet4 *) U)
GDKfree(u);
return NULL;
}
+ if (u != (inet4 *) U) {
+ if (ma == NULL)
+ GDKfree(U);
+ *dstlen = cnt * sizeof(inet4);
+ }
return u;
}
@@ -1820,18 +1832,21 @@ INET6read(allocator *ma, void *U, size_t
if (ma) {
u = ma_realloc(ma, u, cnt * sizeof(inet6), *dstlen);
} else {
- GDKfree(u);
u = GDKmalloc(cnt * sizeof(inet6));
}
if (u == NULL)
return NULL;
- *dstlen = cnt * sizeof(inet6);
}
if (mnstr_read(s, u, sizeof(inet6), cnt) < (ssize_t) cnt) {
- if (u != U)
+ if (ma == NULL && u != (inet6 *) U)
GDKfree(u);
return NULL;
}
+ if (u != (inet6 *) U) {
+ if (ma == NULL)
+ GDKfree(U);
+ *dstlen = cnt * sizeof(inet6);
+ }
return u;
}
@@ -2000,22 +2015,28 @@ BLOBread(allocator *ma, void *A, size_t
(void) cnt;
assert(cnt == 1);
- if (mnstr_readLng(s, &len) != 1 || len < 0)
+ if (mnstr_readLng(s, &len) != 1 || len < 0) {
return NULL;
+ }
if (a == NULL || (lng) *dstlen < len) {
if (ma) {
a = ma_realloc(ma, a, (size_t) len, *dstlen);
} else {
- GDKfree(a);
a = GDKmalloc((size_t) len);
}
if (a == NULL)
return NULL;
- *dstlen = (size_t) len;
}
if (mnstr_read(s, (char *) a, (size_t) len, 1) != 1) {
+ if (ma == NULL && a != (blob *) A)
+ GDKfree(a);
return NULL;
}
+ if (a != (blob *) A) {
+ if (ma == NULL)
+ GDKfree(A);
+ *dstlen = (size_t) len;
+ }
return a;
}
diff --git a/gdk/gdk_atoms.h b/gdk/gdk_atoms.h
--- a/gdk/gdk_atoms.h
+++ b/gdk/gdk_atoms.h
@@ -24,12 +24,20 @@
* points to.
*
* atomCmp returns a value less than zero/equal to zero/greater than
- * zer if the first argument points to a values which is deemed
+ * zero if the first argument points to a values which is deemed
* smaller/equal to/larger than the value pointed to by the second
* argument.
*
* atomHash calculates a hash function for the value pointed to by the
* argument.
+ *
+ * atomRead reads cnt values from stream s and returns them in dst. The
+ * available space in dst is given in *dstlen. If dst is too small (or
+ * NULL), a new buffer is allocated and *dstlen is filled in with the
+ * allocated size. atomRread returns a pointer to the buffer where the
+ * data was written. On any kind of failure (usually either allocation
+ * or reading), the function returns NULL and dst and *dstlen are
+ * unaffected (i.e. similar to realloc).
*/
#define IDLENGTH 64 /* maximum BAT id length */
diff --git a/gdk/gdk_string.c b/gdk/gdk_string.c
--- a/gdk/gdk_string.c
+++ b/gdk/gdk_string.c
@@ -755,9 +755,10 @@ strToStr(allocator *ma, char **restrict
}
str
-strRead(allocator *ma, str a, size_t *dstlen, stream *s, size_t cnt)
+strRead(allocator *ma, str A, size_t *dstlen, stream *s, size_t cnt)
{
int len;
+ str a = A;
(void) cnt;
assert(cnt == 1);
@@ -767,17 +768,22 @@ strRead(allocator *ma, str a, size_t *ds
if (ma) {
a = ma_realloc(ma, a, (size_t) len + 1, *dstlen);
} else {
- GDKfree(a);
a = GDKmalloc((size_t) len + 1);
}
if (a == NULL)
return NULL;
- *dstlen = len + 1;
}
if (len && mnstr_read(s, a, len, 1) != 1) {
+ if (ma == NULL && a != A)
+ GDKfree(a);
return NULL;
}
a[len] = 0;
+ if (a != A) {
+ if (ma == NULL)
+ GDKfree(A);
+ *dstlen = len + 1;
+ }
return a;
}
diff --git a/geom/monetdb5/geom_atoms.c b/geom/monetdb5/geom_atoms.c
--- a/geom/monetdb5/geom_atoms.c
+++ b/geom/monetdb5/geom_atoms.c
@@ -186,18 +186,22 @@ wkbREAD(allocator *ma, void *A, size_t *
if (ma) {
a = ma_realloc(ma, a, wkblen, *dstlen);
} else {
- GDKfree(a);
a = GDKmalloc(wkblen);
}
if (a == NULL)
return NULL;
- *dstlen = wkblen;
}
a->len = len;
a->srid = srid;
if (len > 0 && mnstr_read(s, (char *) a->data, len, 1) != 1) {
+ if (ma == NULL && a != (wkb *) A)
+ GDKfree(a);
return NULL;
}
+ if (ma == NULL && a != (wkb *) A) {
+ GDKfree(A);
+ *dstlen = wkblen;
+ }
return a;
}
@@ -558,15 +562,15 @@ mbrREAD(allocator *ma, void *A, size_t *
if (ma) {
a = ma_realloc(ma, a, cnt * sizeof(mbr), *dstlen);
} else {
- GDKfree(a);
a = GDKmalloc(cnt * sizeof(mbr));
}
if (a == NULL)
return NULL;
- *dstlen = cnt * sizeof(mbr);
}
for (i = 0, c = a; i < cnt; i++, c++) {
if (!mnstr_readIntArray(s, v, 4)) {
+ if (ma == NULL && a != (mbr *) A)
+ GDKfree(a);
return NULL;
}
memcpy(vals, v, 4 * sizeof(int));
@@ -575,6 +579,10 @@ mbrREAD(allocator *ma, void *A, size_t *
c->xmax = vals[2];
c->ymax = vals[3];
}
+ if (ma == NULL && a != (mbr *) A) {
+ GDKfree(A);
+ *dstlen = cnt * sizeof(mbr);
+ }
return a;
}
diff --git a/monetdb5/modules/atoms/json.c b/monetdb5/modules/atoms/json.c
--- a/monetdb5/modules/atoms/json.c
+++ b/monetdb5/modules/atoms/json.c
@@ -609,15 +609,18 @@ jsonRead(allocator *ma, str a, size_t *d
if ((a = BATatoms[TYPE_str].atomRead(ma, a, dstlen, s, cnt)) == NULL)
return NULL;
- msg = JSONstr2json_intern(ma, &out, &(size_t){0}, &(const char *){a});
- if (ma == NULL)
- GDKfree(a);
+ allocator *ta = MT_thread_getallocator();
+ allocator_state ta_state = ma_open(ta);
+ msg = JSONstr2json_intern(ta, &out, &(size_t){0}, &(const char *){a});
if (msg != MAL_SUCCEED) {
+ ma_close(&ta_state);
+ if (ma == NULL)
_______________________________________________
checkin-list mailing list -- [email protected]
To unsubscribe send an email to [email protected]