[libc-commits] [libc] [libc] Move preinit/init/fini arrays to namespace (PR #158746)

Petr Hosek via libc-commits libc-commits at lists.llvm.org
Mon Sep 15 22:47:20 PDT 2025


https://github.com/petrhosek updated https://github.com/llvm/llvm-project/pull/158746

>From 0fe4e331792035927811ae3b20d7cfb5c7991802 Mon Sep 17 00:00:00 2001
From: Petr Hosek <phosek at google.com>
Date: Mon, 15 Sep 2025 14:54:03 -0700
Subject: [PATCH 1/3] [libc] Move preinit/init/fini arrays to namespace

In change #146863 we moved definitions of preinit/init/fini arrays to
header but unintentionally moved outside of the namespace. Since the
namespace also controls the visibility (through LIBC_NAMESPACE_DECL),
as a consequence these symbols no longer have the hidden visibility
which changes the codegen from:

```
 4: 4c11          ldr     r4, [pc, #0x44]         @ 0x4c <__libc_init_array+0x4c>
 6: 4812          ldr     r0, [pc, #0x48]         @ 0x50 <__libc_init_array+0x50>
 8: 447c          add     r4, pc
 a: 4478          add     r0, pc
 c: 1b00          subs    r0, r0, r4
```

to:

```
 4: 4813          ldr     r0, [pc, #0x4c]         @ 0x54 <__libc_init_array+0x54>
 6: 4914          ldr     r1, [pc, #0x50]         @ 0x58 <__libc_init_array+0x58>
 8: 4478          add     r0, pc
 a: 4479          add     r1, pc
 c: 6804          ldr     r4, [r0]
 e: 6808          ldr     r0, [r1]
10: 1b00          subs    r0, r0, r4
```

The `ldr` will trigger a fault in case where these symbols aren't
pointing to a valid memory location which is sometimes the case when
the array is empty.
---
 libc/startup/baremetal/fini.h | 6 ++++++
 libc/startup/baremetal/init.h | 5 +++++
 2 files changed, 11 insertions(+)

diff --git a/libc/startup/baremetal/fini.h b/libc/startup/baremetal/fini.h
index 74e9601983a33..681cbf954f94a 100644
--- a/libc/startup/baremetal/fini.h
+++ b/libc/startup/baremetal/fini.h
@@ -7,6 +7,9 @@
 //===----------------------------------------------------------------------===//
 
 #include "hdr/stdint_proxy.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
 
 extern "C" {
 extern uintptr_t __fini_array_start[];
@@ -14,3 +17,6 @@ extern uintptr_t __fini_array_end[];
 
 void __libc_fini_array(void);
 } // extern "C"
+
+
+} // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/startup/baremetal/init.h b/libc/startup/baremetal/init.h
index 6b545db3976da..da20c7766fee6 100644
--- a/libc/startup/baremetal/init.h
+++ b/libc/startup/baremetal/init.h
@@ -7,6 +7,9 @@
 //===----------------------------------------------------------------------===//
 
 #include "hdr/stdint_proxy.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
 
 extern "C" {
 extern uintptr_t __preinit_array_start[];
@@ -16,3 +19,5 @@ extern uintptr_t __init_array_end[];
 
 void __libc_init_array(void);
 } // extern "C"
+
+} // namespace LIBC_NAMESPACE_DECL

>From 90a6f7eb3b788ad5f71075ad295fd7a2cf891e54 Mon Sep 17 00:00:00 2001
From: Petr Hosek <phosek at google.com>
Date: Mon, 15 Sep 2025 15:25:37 -0700
Subject: [PATCH 2/3] Formatting

---
 libc/startup/baremetal/fini.h | 1 -
 1 file changed, 1 deletion(-)

diff --git a/libc/startup/baremetal/fini.h b/libc/startup/baremetal/fini.h
index 681cbf954f94a..0913d68296412 100644
--- a/libc/startup/baremetal/fini.h
+++ b/libc/startup/baremetal/fini.h
@@ -18,5 +18,4 @@ extern uintptr_t __fini_array_end[];
 void __libc_fini_array(void);
 } // extern "C"
 
-
 } // namespace LIBC_NAMESPACE_DECL

>From 93c5afea3b3a86bcc0d36c90dabdbe09c9d3cc25 Mon Sep 17 00:00:00 2001
From: Petr Hosek <phosek at google.com>
Date: Mon, 15 Sep 2025 22:46:15 -0700
Subject: [PATCH 3/3] Add comment

---
 libc/startup/baremetal/fini.h | 1 +
 libc/startup/baremetal/init.h | 1 +
 2 files changed, 2 insertions(+)

diff --git a/libc/startup/baremetal/fini.h b/libc/startup/baremetal/fini.h
index 0913d68296412..605d4920f9704 100644
--- a/libc/startup/baremetal/fini.h
+++ b/libc/startup/baremetal/fini.h
@@ -9,6 +9,7 @@
 #include "hdr/stdint_proxy.h"
 #include "src/__support/macros/config.h"
 
+// NOTE: The namespace is necessary here to set the correct symbol visibility.
 namespace LIBC_NAMESPACE_DECL {
 
 extern "C" {
diff --git a/libc/startup/baremetal/init.h b/libc/startup/baremetal/init.h
index da20c7766fee6..31497aefa170a 100644
--- a/libc/startup/baremetal/init.h
+++ b/libc/startup/baremetal/init.h
@@ -9,6 +9,7 @@
 #include "hdr/stdint_proxy.h"
 #include "src/__support/macros/config.h"
 
+// NOTE: The namespace is necessary here to set the correct symbol visibility.
 namespace LIBC_NAMESPACE_DECL {
 
 extern "C" {



More information about the libc-commits mailing list