summaryrefslogtreecommitdiff
path: root/tools/testing/selftests/nolibc
diff options
context:
space:
mode:
authorThomas Weißschuh <linux@weissschuh.net>2023-10-05 19:17:29 +0300
committerThomas Weißschuh <linux@weissschuh.net>2023-10-12 22:14:16 +0300
commit63aa531716268f22f0a60fbb65c005494dcde387 (patch)
treeea27f9c9b7df0f3c361a291b9bd902ea7c499e43 /tools/testing/selftests/nolibc
parenteddfc3c74214a7e6f4a3e56ad0cf5dab5d23f287 (diff)
downloadlinux-63aa531716268f22f0a60fbb65c005494dcde387.tar.xz
tools/nolibc: add support for constructors and destructors
With the startup code moved to C, implementing support for constructors and deconstructors is fairly easy to implement. Examples for code size impact: text data bss dec hex filename 21837 104 88 22029 560d nolibc-test.before 22135 120 88 22343 5747 nolibc-test.after 21970 104 88 22162 5692 nolibc-test.after-only-crt.h-changes The sections are defined by [0]. [0] https://refspecs.linuxfoundation.org/elf/gabi4+/ch5.dynamic.html Signed-off-by: Thomas Weißschuh <linux@weissschuh.net> Acked-by: Willy Tarreau <w@1wt.eu> Link: https://lore.kernel.org/lkml/20231007-nolibc-constructors-v2-1-ef84693efbc1@weissschuh.net/
Diffstat (limited to 'tools/testing/selftests/nolibc')
-rw-r--r--tools/testing/selftests/nolibc/nolibc-test.c17
1 files changed, 17 insertions, 0 deletions
diff --git a/tools/testing/selftests/nolibc/nolibc-test.c b/tools/testing/selftests/nolibc/nolibc-test.c
index 7e3936c182dc..8da7f15d010e 100644
--- a/tools/testing/selftests/nolibc/nolibc-test.c
+++ b/tools/testing/selftests/nolibc/nolibc-test.c
@@ -57,6 +57,9 @@ static int test_argc;
/* will be used by some test cases as readable file, please don't write it */
static const char *argv0;
+/* will be used by constructor tests */
+static int constructor_test_value;
+
/* definition of a series of tests */
struct test {
const char *name; /* test name */
@@ -594,6 +597,19 @@ int expect_strne(const char *expr, int llen, const char *cmp)
#define CASE_TEST(name) \
case __LINE__: llen += printf("%d %s", test, #name);
+/* constructors validate that they are executed in definition order */
+__attribute__((constructor))
+static void constructor1(void)
+{
+ constructor_test_value = 1;
+}
+
+__attribute__((constructor))
+static void constructor2(void)
+{
+ constructor_test_value *= 2;
+}
+
int run_startup(int min, int max)
{
int test;
@@ -630,6 +646,7 @@ int run_startup(int min, int max)
CASE_TEST(environ_HOME); EXPECT_PTRNZ(1, getenv("HOME")); break;
CASE_TEST(auxv_addr); EXPECT_PTRGT(test_auxv != (void *)-1, test_auxv, brk); break;
CASE_TEST(auxv_AT_UID); EXPECT_EQ(1, getauxval(AT_UID), getuid()); break;
+ CASE_TEST(constructor); EXPECT_EQ(1, constructor_test_value, 2); break;
case __LINE__:
return ret; /* must be last */
/* note: do not set any defaults so as to permit holes above */