summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--aclocal.m426
-rw-r--r--configure.ac7
-rw-r--r--lib/Makefile2
-rw-r--r--lib/birdlib.h18
-rw-r--r--lib/route.h2
-rw-r--r--lib/type.h12
-rw-r--r--lib/type_test.c78
-rw-r--r--nest/Makefile2
-rw-r--r--nest/bird.h1
9 files changed, 139 insertions, 9 deletions
diff --git a/aclocal.m4 b/aclocal.m4
index 1613d680..58c48791 100644
--- a/aclocal.m4
+++ b/aclocal.m4
@@ -1,6 +1,32 @@
dnl ** Additional Autoconf tests for BIRD configure script
dnl ** (c) 1999 Martin Mares <mj@ucw.cz>
+AC_DEFUN([BIRD_CHECK_POINTER_ALIGNMENT],
+[
+ AC_CACHE_CHECK(
+ [how pointers are aligned],
+ [bird_cv_pointer_alignment],
+ AC_COMPILE_IFELSE([
+ AC_LANG_PROGRAM(
+ [
+ _Static_assert(_Alignof(void *) == 8, "bad");
+ ], []
+ )
+ ],
+ [bird_cv_pointer_alignment=8],
+ AC_COMPILE_IFELSE([
+ AC_LANG_PROGRAM(
+ [
+ _Static_assert(_Alignof(void *) == 4, "bad");
+ ], []
+ )
+ ],
+ [bird_cv_pointer_alignment=4],
+ [bird_cv_pointer_alignment=unknown]
+ ))
+ )
+])
+
AC_DEFUN([BIRD_CHECK_THREAD_LOCAL],
[
AC_CACHE_CHECK(
diff --git a/configure.ac b/configure.ac
index 64181d29..321bed95 100644
--- a/configure.ac
+++ b/configure.ac
@@ -360,6 +360,13 @@ AC_C_BIGENDIAN(
[AC_MSG_ERROR([Cannot determine CPU endianity.])]
)
+BIRD_CHECK_POINTER_ALIGNMENT
+if test "$bird_cv_pointer_alignment" = "unknown" ; then
+ AC_MSG_ERROR([Couldn't determine pointer alignment])
+else
+ AC_DEFINE_UNQUOTED([CPU_POINTER_ALIGNMENT], [$bird_cv_pointer_alignment], [Pointer alignment for macro usage])
+fi
+
BIRD_CHECK_ANDROID_GLOB
if test "$bird_cv_lib_glob" = no ; then
AC_MSG_ERROR([glob.h not found.])
diff --git a/lib/Makefile b/lib/Makefile
index 853e0a22..15f757d9 100644
--- a/lib/Makefile
+++ b/lib/Makefile
@@ -2,6 +2,6 @@ src := a-path.c a-set.c bitmap.c bitops.c blake2s.c blake2b.c checksum.c event.c
obj := $(src-o-files)
$(all-daemon)
-tests_src := a-set_test.c a-path_test.c bitmap_test.c heap_test.c buffer_test.c event_test.c flowspec_test.c bitops_test.c patmatch_test.c fletcher16_test.c slist_test.c checksum_test.c lists_test.c mac_test.c ip_test.c hash_test.c printf_test.c slab_test.c
+tests_src := a-set_test.c a-path_test.c bitmap_test.c heap_test.c buffer_test.c event_test.c flowspec_test.c bitops_test.c patmatch_test.c fletcher16_test.c slist_test.c checksum_test.c lists_test.c mac_test.c ip_test.c hash_test.c printf_test.c slab_test.c type_test.c
tests_targets := $(tests_targets) $(tests-target-files)
tests_objs := $(tests_objs) $(src-o-files)
diff --git a/lib/birdlib.h b/lib/birdlib.h
index 6f0bab96..9b6e4a16 100644
--- a/lib/birdlib.h
+++ b/lib/birdlib.h
@@ -9,18 +9,30 @@
#ifndef _BIRD_BIRDLIB_H_
#define _BIRD_BIRDLIB_H_
+#include "sysdep/config.h"
#include "lib/alloca.h"
/* Ugly structure offset handling macros */
-struct align_probe { char x; long int y; };
-
#define OFFSETOF(s, i) ((size_t) &((s *)0)->i)
#define SKIP_BACK(s, i, p) ((s *)((char *)p - OFFSETOF(s, i)))
#define BIRD_ALIGN(s, a) (((s)+a-1)&~(a-1))
-#define CPU_STRUCT_ALIGN (sizeof(struct align_probe))
+#define CPU_STRUCT_ALIGN (MAX_(_Alignof(void*), _Alignof(u64)))
#define BIRD_CPU_ALIGN(s) BIRD_ALIGN((s), CPU_STRUCT_ALIGN)
+/* Structure item alignment macros */
+
+#define PADDING_NAME(id) _padding_##id
+#define PADDING_(id, sz) u8 PADDING_NAME(id)[sz]
+
+#if CPU_POINTER_ALIGNMENT == 4
+#define PADDING(id, n32, n64) PADDING_(id, n32)
+#elif CPU_POINTER_ALIGNMENT == 8
+#define PADDING(id, n32, n64) PADDING_(id, n64)
+#else
+#error "Strange CPU pointer alignment: " CPU_POINTER_ALIGNMENT
+#endif
+
/* Utility macros */
#define MIN_(a,b) (((a)<(b))?(a):(b))
diff --git a/lib/route.h b/lib/route.h
index 431da4d8..ba7bab61 100644
--- a/lib/route.h
+++ b/lib/route.h
@@ -144,6 +144,8 @@ typedef struct eattr {
byte fresh:1; /* An uncached attribute (e.g. modified in export filter) */
byte undef:1; /* Explicitly undefined */
+ PADDING(unused, 0, 4);
+
union bval u;
} eattr;
diff --git a/lib/type.h b/lib/type.h
index 6d19a250..e43389f3 100644
--- a/lib/type.h
+++ b/lib/type.h
@@ -13,9 +13,15 @@
#include "lib/attrs.h"
union bval {
-#define BVAL_ITEMS \
- u32 data; /* Integer type inherited from eattrs */ \
- u32 i; /* Integer type inherited from filters */ \
+#define BVAL_ITEMS \
+ struct { \
+ u32 data; /* Integer type inherited from eattrs */ \
+ PADDING(data, 0, 4); /* Must be padded on 64-bits */ \
+ }; \
+ struct { \
+ u32 i; /* Integer type inherited from filters */ \
+ PADDING(i, 0, 4); /* Must be padded on 64-bits */ \
+ }; \
const struct adata *ptr; /* Generic attribute data inherited from eattrs */ \
const struct adata *ad; /* Generic attribute data inherited from filters */ \
diff --git a/lib/type_test.c b/lib/type_test.c
new file mode 100644
index 00000000..20e7630b
--- /dev/null
+++ b/lib/type_test.c
@@ -0,0 +1,78 @@
+/*
+ * BIRD Library -- Data Type Alignment Tests
+ *
+ * (c) 2022 Maria Matejka <mq@jmq.cz>
+ *
+ * Can be freely distributed and used under the terms of the GNU GPL.
+ */
+
+#include "test/birdtest.h"
+#include "lib/type.h"
+#include "lib/route.h"
+
+#define CHECK_ONE(val) \
+ for (uint i=0; i<sizeof(val); i++) \
+ bt_assert(((const u8 *) &val)[i] == (u8) ~0);
+
+#define SET_PADDING(val, name) \
+ for (uint i=0; i<sizeof(val.PADDING_NAME(name)); i++) \
+ val.PADDING_NAME(name)[i] = ~0;
+
+
+static int
+t_bval(void)
+{
+ union bval v;
+
+ memset(&v, 0, sizeof(v));
+ v.data = ~0;
+ SET_PADDING(v, data);
+ CHECK_ONE(v);
+
+ memset(&v, 0, sizeof(v));
+ v.i = ~0;
+ SET_PADDING(v, i);
+ CHECK_ONE(v);
+
+ memset(&v, 0, sizeof(v));
+ v.ptr = (void *) ~0;
+ CHECK_ONE(v);
+
+ memset(&v, 0, sizeof(v));
+ v.ad = (void *) ~0;
+ CHECK_ONE(v);
+
+ return 1;
+}
+
+static int
+t_eattr(void)
+{
+ struct eattr e;
+ memset(&e, 0, sizeof(e));
+
+ e.id = ~0;
+ e.flags = ~0;
+ e.type = ~0;
+ e.originated = ~0;
+ e.fresh = ~0;
+ e.undef = ~0;
+ memset(&e.u, ~0, sizeof(e.u)); /* Assumes t_bval passed */
+
+ SET_PADDING(e, unused);
+
+ CHECK_ONE(e);
+
+ return 1;
+}
+
+
+int main(int argc, char *argv[])
+{
+ bt_init(argc, argv);
+
+ bt_test_suite(t_bval, "Structure alignment test: bval");
+ bt_test_suite(t_eattr, "Structure alignment test: eattr");
+
+ return bt_exit_value();
+}
diff --git a/nest/Makefile b/nest/Makefile
index c0765530..0350c3b6 100644
--- a/nest/Makefile
+++ b/nest/Makefile
@@ -6,7 +6,7 @@ $(call proto-build,dev_build)
$(proto-build-c): $(lastword $(MAKEFILE_LIST))
$(E)echo GEN $@
- $(Q)echo "$(patsubst %,void %(void); ,$(PROTO_BUILD)) void protos_build_gen(void) { $(patsubst %, %(); ,$(PROTO_BUILD))}" > $@
+ $(Q)echo "#include \"lib/birdlib.h\"\n$(patsubst %,void %(void);\n,$(PROTO_BUILD)) void protos_build_gen(void) { $(patsubst %, %();\n,$(PROTO_BUILD))}" > $@
tests_src :=
tests_targets := $(tests_targets) $(tests-target-files)
diff --git a/nest/bird.h b/nest/bird.h
index 55712abe..931974a0 100644
--- a/nest/bird.h
+++ b/nest/bird.h
@@ -9,7 +9,6 @@
#ifndef _BIRD_BIRD_H_
#define _BIRD_BIRD_H_
-#include "sysdep/config.h"
#include "lib/birdlib.h"
#include "lib/ip.h"
#include "lib/net.h"