ARM: make CRT_LEGACY_WORKAROUND work as intended
To properly support legacy ARM shared libraries, libc.so needs
to export the symbols __dso_handle and atexit, even though
these are now supplied by the crt startup code.
This patch reshuffles the existing CRT_LEGACY_WORKAROUND
conditionally compiled code slightly so it works as the
original author likely intended.
Change-Id: Id6c0e94dc65b7928324a5f0bad7eba6eb2f464b9
Signed-off-by: Ard Biesheuvel <ard.biesheuvel@gmail.com>
diff --git a/libc/arch-arm/bionic/crtbegin_so.c b/libc/arch-arm/bionic/crtbegin_so.c
index 57d19bf..36e4b9c 100644
--- a/libc/arch-arm/bionic/crtbegin_so.c
+++ b/libc/arch-arm/bionic/crtbegin_so.c
@@ -34,10 +34,25 @@
__cxa_finalize(&__dso_handle);
}
+/* CRT_LEGACY_WORKAROUND should only be defined when building
+ * this file as part of the platform's C library.
+ *
+ * The C library already defines a function named 'atexit()'
+ * for backwards compatibility with older NDK-generated binaries.
+ *
+ * For newer ones, 'atexit' is actually embedded in the C
+ * runtime objects that are linked into the final ELF
+ * binary (shared library or executable), and will call
+ * __cxa_atexit() in order to un-register any atexit()
+ * handler when a library is unloaded.
+ *
+ * This function must be global *and* hidden. Only the
+ * code inside the same ELF binary should be able to access it.
+ */
+
#ifdef CRT_LEGACY_WORKAROUND
#include "__dso_handle.h"
#else
-#include "__dso_handle_so.h"
-#endif
-
+#include "__dso_handle_so.c"
#include "atexit.h"
+#endif