Changeset: 119bbf9daf84 for MonetDB
URL: https://dev.monetdb.org/hg/MonetDB/rev/119bbf9daf84
Modified Files:
sql/backends/monet5/rel_bin.c
Branch: returning
Log Message:
merge with default
diffs (truncated from 1623 to 300 lines):
diff --git a/gdk/CMakeLists.txt b/gdk/CMakeLists.txt
--- a/gdk/CMakeLists.txt
+++ b/gdk/CMakeLists.txt
@@ -64,6 +64,7 @@ target_sources(bat
gdk_string.c
gdk_qsort.c
gdk_qsort_impl.h
+ gdk_rsort.c
gdk_storage.c
gdk_bat.c
gdk_delta.c gdk_delta.h
diff --git a/gdk/gdk_batop.c b/gdk/gdk_batop.c
--- a/gdk/gdk_batop.c
+++ b/gdk/gdk_batop.c
@@ -2269,6 +2269,29 @@ do_sort(void *restrict h, void *restrict
{
if (n <= 1) /* trivially sorted */
return GDK_SUCCEED;
+ switch (tpe) {
+ case TYPE_bte:
+ case TYPE_sht:
+ case TYPE_int:
+ case TYPE_lng:
+#ifdef HAVE_HGE
+ case TYPE_hge:
+#endif
+ case TYPE_date:
+ case TYPE_daytime:
+ case TYPE_timestamp:
+ assert(base == NULL);
+ if (nilslast == reverse && (stable || n > 100))
+ return GDKrsort(h, t, n, hs, ts, reverse, false);
+ break;
+ case TYPE_uuid:
+ assert(base == NULL);
+ if (nilslast == reverse && (stable || n > 100))
+ return GDKrsort(h, t, n, hs, ts, reverse, true);
+ break;
+ default:
+ break;
+ }
if (stable) {
if (reverse)
return GDKssort_rev(h, t, base, n, hs, ts, tpe);
diff --git a/gdk/gdk_logger.c b/gdk/gdk_logger.c
--- a/gdk/gdk_logger.c
+++ b/gdk/gdk_logger.c
@@ -2429,6 +2429,8 @@ do_flush_range_cleanup(logger *lg)
logged_range *frange = lg->flush_ranges;
logged_range *first = frange;
+ if (frange == NULL)
+ return NULL;
while (frange->next) {
if (ATOMIC_GET(&frange->refcount) > 1)
break;
@@ -2532,6 +2534,7 @@ log_create(int debug, const char *fn, co
};
lg->current = &dummy;
if (log_open_output(lg) != GDK_SUCCEED) {
+ lg->current = NULL;
log_destroy(lg);
return NULL;
}
diff --git a/gdk/gdk_private.h b/gdk/gdk_private.h
--- a/gdk/gdk_private.h
+++ b/gdk/gdk_private.h
@@ -151,6 +151,9 @@ gdk_return GDKremovedir(int farmid, cons
gdk_return GDKsave(int farmid, const char *nme, const char *ext, void *buf,
size_t size, storage_t mode, bool dosync)
__attribute__((__warn_unused_result__))
__attribute__((__visibility__("hidden")));
+gdk_return GDKrsort(void *restrict h, void *restrict t, size_t n, size_t hs,
size_t ts, bool reverse, bool isuuid)
+ __attribute__((__warn_unused_result__))
+ __attribute__((__visibility__("hidden")));
gdk_return GDKssort_rev(void *restrict h, void *restrict t, const void
*restrict base, size_t n, int hs, int ts, int tpe)
__attribute__((__warn_unused_result__))
__attribute__((__visibility__("hidden")));
diff --git a/gdk/gdk_rsort.c b/gdk/gdk_rsort.c
new file mode 100644
--- /dev/null
+++ b/gdk/gdk_rsort.c
@@ -0,0 +1,171 @@
+/*
+ * SPDX-License-Identifier: MPL-2.0
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ *
+ * Copyright 2024 MonetDB Foundation;
+ * Copyright August 2008 - 2023 MonetDB B.V.;
+ * Copyright 1997 - July 2008 CWI.
+ */
+
+#include "monetdb_config.h"
+#include "gdk.h"
+#include "gdk_private.h"
+
+#define RADIX 8 /* one char at a time */
+#define NBUCKETS (1 << RADIX)
+
+gdk_return
+GDKrsort(void *restrict h, void *restrict t, size_t n, size_t hs, size_t ts,
bool reverse, bool isuuid)
+{
+ size_t *counts = GDKmalloc(hs * NBUCKETS * sizeof(size_t));
+ size_t pos[NBUCKETS];
+ uint8_t *h1 = h;
+ uint8_t *h2;
+ uint8_t *t1 = NULL;
+ uint8_t *t2 = NULL;
+ Heap tmph, tmpt;
+
+ if (counts == NULL)
+ return GDK_FAIL;
+
+ tmph = tmpt = (Heap) {
+ .farmid = 1,
+ };
+
+ snprintf(tmph.filename, sizeof(tmph.filename), "%s%crsort%zuh",
+ TEMPDIR_NAME, DIR_SEP, (size_t) MT_getpid());
+ if (HEAPalloc(&tmph, n, hs) != GDK_SUCCEED) {
+ GDKfree(counts);
+ return GDK_FAIL;
+ }
+ h2 = (uint8_t *) tmph.base;
+
+ if (t) {
+ snprintf(tmpt.filename, sizeof(tmpt.filename), "%s%crsort%zut",
+ TEMPDIR_NAME, DIR_SEP, (size_t) MT_getpid());
+ if (HEAPalloc(&tmpt, n, ts) != GDK_SUCCEED) {
+ GDKfree(counts);
+ HEAPfree(&tmph, true);
+ return GDK_FAIL;
+ }
+ t1 = t;
+ t2 = (uint8_t *) tmpt.base;
+ } else {
+ ts = 0;
+ }
+
+ memset(counts, 0, hs * NBUCKETS * sizeof(size_t));
+#ifndef WORDS_BIGENDIAN
+ if (isuuid /* UUID, treat like big-endian */)
+#endif
+ for (size_t i = 0, o = 0; i < n; i++, o += hs) {
+ for (size_t j = 0, k = hs - 1; j < hs; j++, k--) {
+ uint8_t v = h1[o + k];
+ counts[(j << RADIX) + v]++;
+ }
+ }
+#ifndef WORDS_BIGENDIAN
+ else
+ for (size_t i = 0, o = 0; i < n; i++, o += hs) {
+ for (size_t j = 0; j < hs; j++) {
+ uint8_t v = h1[o + j];
+ counts[(j << RADIX) + v]++;
+ }
+ }
+#endif
+ /* When sorting in ascending order, the negative numbers occupy
+ * the second half of the buckets in the last iteration; when
+ * sorting in descending order, the negative numbers occupy the
+ * first half. In either case, at the end we need to put the
+ * second half first and the first half after. */
+ size_t negpos = 0;
+ for (size_t j = 0, b = 0, k = hs - 1; j < hs; j++, b += NBUCKETS, k--) {
+ size_t nb = counts[b] > 0;
+ if (reverse) {
+ pos[NBUCKETS - 1] = 0;
+ for (size_t i = NBUCKETS - 1; i > 0; i--) {
+ pos[i - 1] = pos[i] + counts[b + i];
+ nb += counts[b + i] > 0;
+ }
+ } else {
+ pos[0] = 0;
+ for (size_t i = 1; i < NBUCKETS; i++) {
+ pos[i] = pos[i - 1] + counts[b + i - 1];
+ nb += counts[b + i] > 0;
+ }
+ }
+ /* we're only interested in the position in the last
+ * iteration */
+ negpos = pos[NBUCKETS / 2 - reverse];
+ if (nb == 1) {
+ /* no need to reshuffle data for this iteration:
+ * everything is in the same bucket */
+ continue;
+ }
+ /* note, this loop changes the pos array */
+#ifndef WORDS_BIGENDIAN
+ if (isuuid /* UUID, treat like big-endian */)
+#endif
+ for (size_t i = 0, ho = 0, to = 0; i < n; i++, ho +=
hs, to += ts) {
+ uint8_t v = h1[ho + k];
+ if (t)
+ memcpy(t2 + ts * pos[v], t1 + to, ts);
+ memcpy(h2 + hs * pos[v]++, h1 + ho, hs);
+ }
+#ifndef WORDS_BIGENDIAN
+ else
+ for (size_t i = 0, ho = 0, to = 0; i < n; i++, ho +=
hs, to += ts) {
+ uint8_t v = h1[ho + j];
+ if (t)
+ memcpy(t2 + ts * pos[v], t1 + to, ts);
+ memcpy(h2 + hs * pos[v]++, h1 + ho, hs);
+ }
+#endif
+ uint8_t *t = h1;
+ h1 = h2;
+ h2 = t;
+ t = t1;
+ t1 = t2;
+ t2 = t;
+ }
+ GDKfree(counts);
+
+ if (h1 != (uint8_t *) h) {
+ /* we need to copy the data back to the correct heap */
+ if (isuuid) {
+ /* no negative values in uuid, so no shuffling */
+ memcpy(h2, h1, n * hs);
+ if (t)
+ memcpy(t2, t1, n * ts);
+ } else {
+ /* copy the negative integers to the start, copy
positive after */
+ if (negpos < n) {
+ memcpy(h2, h1 + hs * negpos, (n - negpos) * hs);
+ if (t)
+ memcpy(t2, t1 + ts * negpos, (n -
negpos) * ts);
+ }
+ if (negpos > 0) {
+ memcpy(h2 + hs * (n - negpos), h1, negpos * hs);
+ if (t)
+ memcpy(t2 + ts * (n - negpos), t1,
negpos * ts);
+ }
+ }
+ } else if (negpos > 0 && negpos < n && !isuuid) {
+ /* copy the negative integers to the start, copy positive after
*/
+ memcpy(h2, h1 + hs * negpos, (n - negpos) * hs);
+ memcpy(h2 + hs * (n - negpos), h1, negpos * hs);
+ memcpy(h, h2, n * hs);
+ if (t) {
+ memcpy(t2, t1 + ts * negpos, (n - negpos) * ts);
+ memcpy(t2 + ts * (n - negpos), t1, negpos * ts);
+ memcpy(t, t2, n * ts);
+ }
+ } /* else, everything is already in the correct place */
+ HEAPfree(&tmph, true);
+ if (t)
+ HEAPfree(&tmpt, true);
+ return GDK_SUCCEED;
+}
diff --git a/sql/ChangeLog-Archive b/sql/ChangeLog-Archive
--- a/sql/ChangeLog-Archive
+++ b/sql/ChangeLog-Archive
@@ -48,6 +48,13 @@
are no longer accepted in the ANALYZE statement.
- The ANALYZE statement can now be used in procedures, functions and triggers.
+* Thu Apr 23 2024 Yunus Koning <[email protected]> -
11.51.1-20240812
+- Added support for CHECK constraints in CREATE TABLE and ALTER TABLE
+ ADD CONSTRAINT statements. Columns and tables can have multiple CHECK
+ constraints provided their names are unique within the schema of the table.
+ The syntax is: [ CONSTRAINT a_name ] CHECK ( boolean_expression ).
+ When no constraint name is specified, a constraint name will be generated.
+
* Wed Apr 10 2024 Lucas Pereira <[email protected]> -
11.51.1-20240812
- Make schema renaming more permissive. A schema can be renamed if it
does not contain objects that are a dependency for objects outside
diff --git a/sql/backends/monet5/UDF/pyapi3/convert_loops.h
b/sql/backends/monet5/UDF/pyapi3/convert_loops.h
--- a/sql/backends/monet5/UDF/pyapi3/convert_loops.h
+++ b/sql/backends/monet5/UDF/pyapi3/convert_loops.h
@@ -339,7 +339,7 @@ convert_and_append(BAT* b, const char* t
break;
\
case NPY_UNICODE:
\
NP_COL_BAT_LOOP_FUNC(bat, mtpe,
unicode_to_##mtpe, \
-
Py_UNICODE, index); \
+
wchar_t, index); \
break;
\
case NPY_OBJECT:
\
NP_COL_BAT_LOOP_FUNC(bat, mtpe,
pyobject_to_##mtpe, \
@@ -440,7 +440,7 @@ convert_and_append(BAT* b, const char* t
} else {
\
utf32_to_utf8(
\
0, ret->memory_size / 4,
utf8_string, \
- (const Py_UNICODE
\
+ (const wchar_t
\
*)(&data[(index_offset
* ret->count + iu) * \
ret->memory_size])); \
if (convert_and_append(b, utf8_string,
false) != GDK_SUCCEED) { \
diff --git a/sql/backends/monet5/UDF/pyapi3/type_conversion.h
b/sql/backends/monet5/UDF/pyapi3/type_conversion.h
--- a/sql/backends/monet5/UDF/pyapi3/type_conversion.h
+++ b/sql/backends/monet5/UDF/pyapi3/type_conversion.h
@@ -35,7 +35,7 @@ int hge_to_string(char *str, hge);
//! Converts a base-10 string to a hge value
str str_to_hge(const char *ptr, size_t maxsize, hge *value);
//! Converts a base-10 utf32-encoded string to a hge value
-str unicode_to_hge(Py_UNICODE *utf32, size_t maxsize, hge *value);
+str unicode_to_hge(wchar_t *utf32, size_t maxsize, hge *value);
_______________________________________________
checkin-list mailing list -- [email protected]
To unsubscribe send an email to [email protected]