summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDale Rahn <drahn@cvs.openbsd.org>2000-10-13 05:14:04 +0000
committerDale Rahn <drahn@cvs.openbsd.org>2000-10-13 05:14:04 +0000
commit9c38c1942a644f6c07685cd3baa240884a39bf8c (patch)
tree662d75e749fc251e1c925f185d82bb6690a66782
parent166278aa215c155f4eec814b86d340a3cb4b52ad (diff)
Changes to the powerpc startup files to work in a more typical ELF
manner. the linker knows about the magic function _init and _fini and will create a .dynamic tag to point to those symbols in the executable/shared libraries. Take advantage of that fact to allow ld.so to easily find the appropriate ctors/dtors calls for shared libraries Since the crtbeginS.c now contains executable code, it must be compiled with -fPIC. Rename the __init and __fini functions to _init/_fini so the linker will locate them.
-rw-r--r--lib/csu/powerpc/Makefile8
-rw-r--r--lib/csu/powerpc/crtbeginS.c61
2 files changed, 63 insertions, 6 deletions
diff --git a/lib/csu/powerpc/Makefile b/lib/csu/powerpc/Makefile
index fde62a6b022..94560788ba0 100644
--- a/lib/csu/powerpc/Makefile
+++ b/lib/csu/powerpc/Makefile
@@ -1,8 +1,10 @@
-# $OpenBSD: Makefile,v 1.6 2000/06/28 04:56:44 rahnds Exp $
+# $OpenBSDe Makefile,v 1.6 2000/06/28 04:56:44 rahnds Exp $
# from: @(#)Makefile 8.1 (Berkeley) 6/1/93
CFLAGS= -DLIBC_SCCS
OBJS= crt0.o gcrt0.o scrt0.o crtbegin.o crtend.o crtbeginS.o crtendS.o
+PICFLAG?=-fpic
+
CLEANFILES+= core a.out
all: ${OBJS}
@@ -35,8 +37,8 @@ crtend.o: crtend.c
@rm -f ${.TARGET}.o
crtbeginS.o: crtbeginS.c
- @echo ${CC} ${CFLAGS} -c ${.ALLSRC} -o ${.TARGET}
- @${CC} ${CFLAGS} -c ${.ALLSRC} -o ${.TARGET}.o
+ @echo ${CC} ${PICFLAG} ${CFLAGS} -c ${.ALLSRC} -o ${.TARGET}
+ @${CC} ${PICFLAG} ${CFLAGS} -c ${.ALLSRC} -o ${.TARGET}.o
@${LD} -x -r -o ${.TARGET} ${.TARGET}.o
@rm -f ${.TARGET}.o
diff --git a/lib/csu/powerpc/crtbeginS.c b/lib/csu/powerpc/crtbeginS.c
index 2b7e08d53a4..bf2ce4498fd 100644
--- a/lib/csu/powerpc/crtbeginS.c
+++ b/lib/csu/powerpc/crtbeginS.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: crtbeginS.c,v 1.1 2000/06/13 04:07:03 rahnds Exp $ */
+/* $OpenBSD: crtbeginS.c,v 1.2 2000/10/13 05:14:03 drahn Exp $ */
/* $NetBSD: crtbegin.c,v 1.1 1996/09/12 16:59:03 cgd Exp $ */
/*
@@ -46,7 +46,62 @@
*/
#include <stdlib.h>
-void (*__CTOR_LIST__[0]) __P((void))
+static void (*__CTOR_LIST__[0]) __P((void))
__attribute__((section(".ctors"))) = { (void *)-1 }; /* XXX */
-void (*__DTOR_LIST__[0]) __P((void))
+static void (*__DTOR_LIST__[0]) __P((void))
__attribute__((section(".dtors"))) = { (void *)-1 }; /* XXX */
+
+static void __dtors __P((void));
+static void __ctors __P((void));
+
+void
+__dtors()
+{
+ unsigned long i = (unsigned long) __DTOR_LIST__[0];
+ void (**p)(void);
+
+ if (i == -1) {
+ for (i = 1; __DTOR_LIST__[i] != NULL; i++)
+ ;
+ i--;
+ }
+ p = __DTOR_LIST__ + i;
+ while (i--) {
+ (**p--)();
+ }
+}
+
+static void
+__ctors()
+{
+ void (**p)(void) = __CTOR_LIST__ + 1;
+
+ while (*p) {
+ (**p++)();
+ }
+}
+
+void
+_init()
+{
+ static int initialized = 0;
+
+ /*
+ * Call global constructors.
+ * Arrange to call global destructors at exit.
+ */
+ if (!initialized) {
+ initialized = 1;
+ __ctors();
+
+ atexit(__dtors);
+ }
+}
+void
+_fini()
+{
+ /*
+ * since the _init() function sets up the destructors to be called
+ * by atexit, do not call the destructors here.
+ */
+}