-
Notifications
You must be signed in to change notification settings - Fork 15.2k
[libc] Move preinit/init/fini arrays to namespace #158746
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[libc] Move preinit/init/fini arrays to namespace #158746
Conversation
In change llvm#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.
@llvm/pr-subscribers-libc Author: Petr Hosek (petrhosek) ChangesIn 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:
to:
The Full diff: https://github.com/llvm/llvm-project/pull/158746.diff 2 Files Affected:
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
|
✅ With the latest revision this PR passed the C/C++ code formatter. |
#include "hdr/stdint_proxy.h" | ||
#include "src/__support/macros/config.h" | ||
|
||
namespace LIBC_NAMESPACE_DECL { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Given that the only declarations inside this namespace are extern "C"
, it would be easy to overlook this namespace
as being unnecessary for correctness -- especially if you don't realize the gnu::visibility("hidden")
magic behind it. This probably facilitated the bug being introduced in #146863.
Perhaps a comment here would be warranted (and same on init.h
of course).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done.
Good catch! |
In change llvm#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.
In change llvm#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.
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:
to:
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.