[libdazzle] intpair: add a pointer-stashed int pair with 32-bit fallback
- From: Christian Hergert <chergert src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [libdazzle] intpair: add a pointer-stashed int pair with 32-bit fallback
- Date: Thu, 8 Jun 2017 22:38:23 +0000 (UTC)
commit f9264b5197bc7591be60dfd320b9f14ba43a797d
Author: Christian Hergert <chergert redhat com>
Date: Thu Jun 8 15:38:13 2017 -0700
intpair: add a pointer-stashed int pair with 32-bit fallback
If we are on 64-bit, we can stash two uint's in the pointer (or two signed
ints). This can be useful when working with small structures that want to
avoid allocations when possible.
src/dazzle.h | 1 +
src/util/dzl-int-pair.h | 161 +++++++++++++++++++++++++++++++++++++++++++++++
tests/meson.build | 6 ++
tests/test-int-pair.c | 79 +++++++++++++++++++++++
4 files changed, 247 insertions(+), 0 deletions(-)
---
diff --git a/src/dazzle.h b/src/dazzle.h
index 609b75a..2c2b406 100644
--- a/src/dazzle.h
+++ b/src/dazzle.h
@@ -122,6 +122,7 @@ G_BEGIN_DECLS
#include "util/dzl-gdk.h"
#include "util/dzl-gtk.h"
#include "util/dzl-heap.h"
+#include "util/dzl-int-pair.h"
#include "util/dzl-pango.h"
#include "util/dzl-rgba.h"
#include "util/dzl-ring.h"
diff --git a/src/util/dzl-int-pair.h b/src/util/dzl-int-pair.h
new file mode 100644
index 0000000..8ced907
--- /dev/null
+++ b/src/util/dzl-int-pair.h
@@ -0,0 +1,161 @@
+/* dzl-int-pair.h
+ *
+ * Copyright (C) 2017 Christian Hergert <chergert redhat com>
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef DZL_INT_PAIR_H
+#define DZL_INT_PAIR_H
+
+#include <glib.h>
+
+G_BEGIN_DECLS
+
+#if __WORDSIZE >= 64
+
+typedef union
+{
+ /*< private >*/
+ struct {
+ gint first;
+ gint second;
+ };
+ gpointer ptr;
+} DzlIntPair;
+
+typedef union
+{
+ /*< private >*/
+ struct {
+ guint first;
+ guint second;
+ };
+ gpointer ptr;
+} DzlUIntPair;
+
+#else
+
+typedef struct
+{
+ /*< private >*/
+ gint first;
+ gint second;
+} DzlIntPair;
+
+typedef struct
+{
+ /*< private >*/
+ guint first;
+ guint second;
+} DzlUIntPair;
+
+#endif
+
+G_STATIC_ASSERT (sizeof (DzlIntPair) == 8);
+G_STATIC_ASSERT (sizeof (DzlUIntPair) == 8);
+
+static inline DzlIntPair *
+dzl_int_pair_new (gint first, gint second)
+{
+ DzlIntPair pair = { .first = first, .second = second };
+#if __WORDSIZE >= 64
+ return pair.ptr;
+#else
+ return g_slice_copy (sizeof (DzlIntPair), &pair);
+#endif
+}
+
+static inline DzlUIntPair *
+dzl_uint_pair_new (guint first, guint second)
+{
+ DzlUIntPair pair = { .first = first, .second = second };
+#if __WORDSIZE >= 64
+ return pair.ptr;
+#else
+ return g_slice_copy (sizeof (DzlUIntPair), &pair);
+#endif
+}
+
+static inline gint
+dzl_int_pair_first (DzlIntPair *pair)
+{
+ DzlIntPair p;
+#if __WORDSIZE >= 64
+ p.ptr = pair;
+#else
+ p = *pair;
+#endif
+ return p.first;
+}
+
+static inline gint
+dzl_int_pair_second (DzlIntPair *pair)
+{
+ DzlIntPair p;
+#if __WORDSIZE >= 64
+ p.ptr = pair;
+#else
+ p = *pair;
+#endif
+ return p.second;
+}
+
+static inline guint
+dzl_uint_pair_first (DzlUIntPair *pair)
+{
+ DzlUIntPair p;
+#if __WORDSIZE >= 64
+ p.ptr = pair;
+#else
+ p = *pair;
+#endif
+ return p.first;
+}
+
+static inline guint
+dzl_uint_pair_second (DzlUIntPair *pair)
+{
+ DzlUIntPair p;
+#if __WORDSIZE >= 64
+ p.ptr = pair;
+#else
+ p = *pair;
+#endif
+ return p.second;
+}
+
+static inline void
+dzl_int_pair_free (DzlIntPair *pair)
+{
+#if __WORDSIZE >= 64
+ /* Do Nothing */
+#else
+ g_slice_free (DzlIntPair, pair);
+#endif
+}
+
+static inline void
+dzl_uint_pair_free (DzlUIntPair *pair)
+{
+#if __WORDSIZE >= 64
+ /* Do Nothing */
+#else
+ g_slice_free (DzlUIntPair, pair);
+#endif
+}
+
+G_END_DECLS
+
+#endif /* DZL_INT_PAIR_H */
diff --git a/tests/meson.build b/tests/meson.build
index 923e554..ba1b813 100644
--- a/tests/meson.build
+++ b/tests/meson.build
@@ -238,3 +238,9 @@ test_preferences = executable('test-preferences', 'test-preferences.c',
link_args: test_link_args,
dependencies: libdazzle_deps + [libdazzle_dep],
)
+
+test_int_pair = executable('test-int-pair', 'test-int-pair.c',
+ c_args: test_cflags,
+ link_args: test_link_args,
+ dependencies: libdazzle_deps + [libdazzle_dep],
+)
diff --git a/tests/test-int-pair.c b/tests/test-int-pair.c
new file mode 100644
index 0000000..1dd9e15
--- /dev/null
+++ b/tests/test-int-pair.c
@@ -0,0 +1,79 @@
+#include <dazzle.h>
+
+static void
+test_intpair_basic (void)
+{
+ DzlIntPair *p;
+
+ p = dzl_int_pair_new (0, 0);
+#if __WORDSIZE >= 64
+ /* Technically not ANSI as NULL is allowed to be non-zero, but all the
+ * platforms we support, this is the case.
+ */
+ g_assert (p == NULL);
+#else
+ g_assert (p != NULL);
+#endif
+
+ p = dzl_int_pair_new (4, 5);
+ g_assert (p != NULL);
+ g_assert_cmpint (dzl_int_pair_first (p), ==, 4);
+ g_assert_cmpint (dzl_int_pair_second (p), ==, 5);
+ dzl_int_pair_free (p);
+
+ p = dzl_int_pair_new (G_MAXINT, G_MAXINT-1);
+ g_assert (p != NULL);
+ g_assert_cmpint (dzl_int_pair_first (p), ==, G_MAXINT);
+ g_assert_cmpint (dzl_int_pair_second (p), ==, G_MAXINT-1);
+ dzl_int_pair_free (p);
+
+ p = dzl_int_pair_new (G_MAXINT-1, G_MAXINT);
+ g_assert (p != NULL);
+ g_assert_cmpint (dzl_int_pair_first (p), ==, G_MAXINT-1);
+ g_assert_cmpint (dzl_int_pair_second (p), ==, G_MAXINT);
+ dzl_int_pair_free (p);
+}
+
+static void
+test_uintpair_basic (void)
+{
+ DzlUIntPair *p;
+
+ p = dzl_uint_pair_new (0, 0);
+#if __WORDSIZE >= 64
+ /* Technically not ANSI as NULL is allowed to be non-zero, but all the
+ * platforms we support, this is the case.
+ */
+ g_assert (p == NULL);
+#else
+ g_assert (p != NULL);
+#endif
+
+ p = dzl_uint_pair_new (4, 5);
+ g_assert (p != NULL);
+ g_assert_cmpuint (dzl_uint_pair_first (p), ==, 4);
+ g_assert_cmpuint (dzl_uint_pair_second (p), ==, 5);
+ dzl_uint_pair_free (p);
+
+ p = dzl_uint_pair_new (G_MAXUINT, G_MAXUINT-1);
+ g_assert (p != NULL);
+ g_assert_cmpuint (dzl_uint_pair_first (p), ==, G_MAXUINT);
+ g_assert_cmpuint (dzl_uint_pair_second (p), ==, G_MAXUINT-1);
+ dzl_uint_pair_free (p);
+
+ p = dzl_uint_pair_new (G_MAXUINT-1, G_MAXUINT);
+ g_assert (p != NULL);
+ g_assert_cmpuint (dzl_uint_pair_first (p), ==, G_MAXUINT-1);
+ g_assert_cmpuint (dzl_uint_pair_second (p), ==, G_MAXUINT);
+ dzl_uint_pair_free (p);
+}
+
+gint
+main (gint argc,
+ gchar *argv[])
+{
+ g_test_init (&argc, &argv, NULL);
+ g_test_add_func ("/Dazzle/IntPair/basic", test_intpair_basic);
+ g_test_add_func ("/Dazzle/UIntPair/basic", test_uintpair_basic);
+ return g_test_run ();
+}
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]