640 lines
16 KiB
Diff
640 lines
16 KiB
Diff
|
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||
|
From: Peter Jones <pjones@redhat.com>
|
||
|
Date: Fri, 23 Aug 2019 16:23:21 -0400
|
||
|
Subject: [PATCH] Make ELF constructors and destructors work.
|
||
|
|
||
|
Signed-off-by: Peter Jones <pjones@redhat.com>
|
||
|
---
|
||
|
apps/Makefile | 5 +-
|
||
|
apps/ctors_fns.c | 26 ++++++++++
|
||
|
apps/ctors_test.c | 20 ++++++++
|
||
|
gnuefi/crt0-efi-aa64.S | 2 +
|
||
|
gnuefi/crt0-efi-arm.S | 2 +
|
||
|
gnuefi/crt0-efi-ia32.S | 2 +
|
||
|
gnuefi/crt0-efi-ia64.S | 6 +++
|
||
|
gnuefi/crt0-efi-mips64el.S | 12 ++++-
|
||
|
gnuefi/crt0-efi-x64.S | 2 +
|
||
|
gnuefi/elf_aa64_efi.lds | 15 ++++++
|
||
|
gnuefi/elf_arm_efi.lds | 14 ++++++
|
||
|
gnuefi/elf_ia32_efi.lds | 15 ++++++
|
||
|
gnuefi/elf_ia32_fbsd_efi.lds | 15 ++++++
|
||
|
gnuefi/elf_ia64_efi.lds | 15 ++++++
|
||
|
gnuefi/elf_mips64el_efi.lds | 14 ++++++
|
||
|
gnuefi/elf_x64_efi.lds | 16 +++++++
|
||
|
gnuefi/elf_x64_fbsd_efi.lds | 15 ++++++
|
||
|
lib/Makefile | 2 +-
|
||
|
lib/ctors.c | 45 +++++++++++++++++
|
||
|
lib/init.c | 112 ++++++++++++++++++++++++++-----------------
|
||
|
20 files changed, 307 insertions(+), 48 deletions(-)
|
||
|
create mode 100644 apps/ctors_fns.c
|
||
|
create mode 100644 apps/ctors_test.c
|
||
|
create mode 100644 lib/ctors.c
|
||
|
|
||
|
diff --git a/apps/Makefile b/apps/Makefile
|
||
|
index cba84f4a3c1..a2476d37bed 100644
|
||
|
--- a/apps/Makefile
|
||
|
+++ b/apps/Makefile
|
||
|
@@ -62,7 +62,8 @@ TARGET_APPS = t.efi t2.efi t3.efi t4.efi t5.efi t6.efi \
|
||
|
printenv.efi t7.efi t8.efi tcc.efi modelist.efi \
|
||
|
route80h.efi drv0_use.efi AllocPages.efi exit.efi \
|
||
|
FreePages.efi setjmp.efi debughook.efi debughook.efi.debug \
|
||
|
- bltgrid.efi lfbgrid.efi setdbg.efi unsetdbg.efi
|
||
|
+ bltgrid.efi lfbgrid.efi setdbg.efi unsetdbg.efi \
|
||
|
+ ctors_test.efi
|
||
|
TARGET_BSDRIVERS = drv0.efi
|
||
|
TARGET_RTDRIVERS =
|
||
|
|
||
|
@@ -87,6 +88,8 @@ TARGETS = $(TARGET_APPS) $(TARGET_BSDRIVERS) $(TARGET_RTDRIVERS)
|
||
|
|
||
|
all: $(TARGETS)
|
||
|
|
||
|
+ctors_test.so : ctors_fns.o ctors_test.o
|
||
|
+
|
||
|
clean:
|
||
|
rm -f $(TARGETS) *~ *.o *.so
|
||
|
|
||
|
diff --git a/apps/ctors_fns.c b/apps/ctors_fns.c
|
||
|
new file mode 100644
|
||
|
index 00000000000..89c84f43c6b
|
||
|
--- /dev/null
|
||
|
+++ b/apps/ctors_fns.c
|
||
|
@@ -0,0 +1,26 @@
|
||
|
+/*
|
||
|
+ * ctors.c
|
||
|
+ * Copyright 2019 Peter Jones <pjones@redhat.com>
|
||
|
+ *
|
||
|
+ */
|
||
|
+
|
||
|
+#include <efi.h>
|
||
|
+#include <efilib.h>
|
||
|
+
|
||
|
+int constructed_value = 0;
|
||
|
+
|
||
|
+static void __attribute__((__constructor__)) ctor(void)
|
||
|
+{
|
||
|
+ Print(L"%a:%d:%a() constructed_value:%d\n", __FILE__, __LINE__, __func__, constructed_value);
|
||
|
+ constructed_value = 1;
|
||
|
+ Print(L"%a:%d:%a() constructed_value:%d\n", __FILE__, __LINE__, __func__, constructed_value);
|
||
|
+}
|
||
|
+
|
||
|
+static void __attribute__((__destructor__)) dtor(void)
|
||
|
+{
|
||
|
+ Print(L"%a:%d:%a() constructed_value:%d\n", __FILE__, __LINE__, __func__, constructed_value);
|
||
|
+ constructed_value = 0;
|
||
|
+ Print(L"%a:%d:%a() constructed_value:%d\n", __FILE__, __LINE__, __func__, constructed_value);
|
||
|
+}
|
||
|
+
|
||
|
+// vim:fenc=utf-8:tw=75:noet
|
||
|
diff --git a/apps/ctors_test.c b/apps/ctors_test.c
|
||
|
new file mode 100644
|
||
|
index 00000000000..7e48da8ef35
|
||
|
--- /dev/null
|
||
|
+++ b/apps/ctors_test.c
|
||
|
@@ -0,0 +1,20 @@
|
||
|
+/*
|
||
|
+ * ctors_test.c
|
||
|
+ * Copyright 2019 Peter Jones <pjones@redhat.com>
|
||
|
+ *
|
||
|
+ */
|
||
|
+
|
||
|
+#include <efi.h>
|
||
|
+#include <efilib.h>
|
||
|
+
|
||
|
+extern int constructed_value;
|
||
|
+
|
||
|
+EFI_STATUS
|
||
|
+efi_main (EFI_HANDLE image EFI_UNUSED, EFI_SYSTEM_TABLE *systab EFI_UNUSED)
|
||
|
+{
|
||
|
+ Print(L"%a:%d:%a() constructed_value:%d\n", __FILE__, __LINE__, __func__, constructed_value);
|
||
|
+
|
||
|
+ return EFI_SUCCESS;
|
||
|
+}
|
||
|
+
|
||
|
+// vim:fenc=utf-8:tw=75:noet
|
||
|
diff --git a/gnuefi/crt0-efi-aa64.S b/gnuefi/crt0-efi-aa64.S
|
||
|
index d6e610b8c79..1d85d78785e 100644
|
||
|
--- a/gnuefi/crt0-efi-aa64.S
|
||
|
+++ b/gnuefi/crt0-efi-aa64.S
|
||
|
@@ -124,7 +124,9 @@ _start:
|
||
|
cbnz x0, 0f
|
||
|
|
||
|
ldp x0, x1, [sp, #16]
|
||
|
+ bl _ctors
|
||
|
bl efi_main
|
||
|
+ bl _dtors
|
||
|
|
||
|
0: ldp x29, x30, [sp], #32
|
||
|
ret
|
||
|
diff --git a/gnuefi/crt0-efi-arm.S b/gnuefi/crt0-efi-arm.S
|
||
|
index c5bb6d482da..135fdcae8c4 100644
|
||
|
--- a/gnuefi/crt0-efi-arm.S
|
||
|
+++ b/gnuefi/crt0-efi-arm.S
|
||
|
@@ -136,7 +136,9 @@ _start:
|
||
|
bne 0f
|
||
|
|
||
|
ldmfd sp, {r0-r1}
|
||
|
+ bl _ctors
|
||
|
bl efi_main
|
||
|
+ bl _dtors
|
||
|
|
||
|
0: add sp, sp, #12
|
||
|
ldr pc, [sp], #4
|
||
|
diff --git a/gnuefi/crt0-efi-ia32.S b/gnuefi/crt0-efi-ia32.S
|
||
|
index f9d5191ecb5..93eeda4b703 100644
|
||
|
--- a/gnuefi/crt0-efi-ia32.S
|
||
|
+++ b/gnuefi/crt0-efi-ia32.S
|
||
|
@@ -59,7 +59,9 @@ _start:
|
||
|
testl %eax,%eax
|
||
|
jne .exit
|
||
|
|
||
|
+ call _ctors
|
||
|
call efi_main # call app with "image" and "systab" argument
|
||
|
+ call _dtors
|
||
|
|
||
|
.exit: leave
|
||
|
ret
|
||
|
diff --git a/gnuefi/crt0-efi-ia64.S b/gnuefi/crt0-efi-ia64.S
|
||
|
index 40c3c837a1c..14b5683cac7 100644
|
||
|
--- a/gnuefi/crt0-efi-ia64.S
|
||
|
+++ b/gnuefi/crt0-efi-ia64.S
|
||
|
@@ -56,7 +56,13 @@ _start:
|
||
|
|
||
|
mov out0=in0 // image handle
|
||
|
mov out1=in1 // systab
|
||
|
+ ;;
|
||
|
+ br.call.sptk.few rp=_ctors
|
||
|
+ ;;
|
||
|
br.call.sptk.few rp=efi_main
|
||
|
+ ;;
|
||
|
+ br.call.sptk.few rp=_dtors
|
||
|
+ ;;
|
||
|
.Lret2:
|
||
|
.exit:
|
||
|
mov ar.pfs=loc0
|
||
|
diff --git a/gnuefi/crt0-efi-mips64el.S b/gnuefi/crt0-efi-mips64el.S
|
||
|
index 6a62aca98b4..ee871cd33ce 100644
|
||
|
--- a/gnuefi/crt0-efi-mips64el.S
|
||
|
+++ b/gnuefi/crt0-efi-mips64el.S
|
||
|
@@ -172,11 +172,19 @@ _pc:
|
||
|
|
||
|
// a0: ImageHandle
|
||
|
ld $a0, 16($sp)
|
||
|
- // call efi_main
|
||
|
- dla $t9, efi_main
|
||
|
+ // call _ctors
|
||
|
+ dla $t9, _ctors
|
||
|
jalr $t9
|
||
|
// a1: SystemTable
|
||
|
ld $a1, 24($sp)
|
||
|
+ // call efi_main
|
||
|
+ dla $t9, efi_main
|
||
|
+ jalr $t9
|
||
|
+ nop
|
||
|
+ // call _dtors
|
||
|
+ dla $t9, _dtors
|
||
|
+ jalr $t9
|
||
|
+ nop
|
||
|
|
||
|
1:
|
||
|
ld $gp, 8($sp)
|
||
|
diff --git a/gnuefi/crt0-efi-x64.S b/gnuefi/crt0-efi-x64.S
|
||
|
index 6533af7461f..5501876bbb3 100644
|
||
|
--- a/gnuefi/crt0-efi-x64.S
|
||
|
+++ b/gnuefi/crt0-efi-x64.S
|
||
|
@@ -56,8 +56,10 @@ _start:
|
||
|
popq %rdi
|
||
|
popq %rsi
|
||
|
|
||
|
+ call _ctors
|
||
|
call efi_main
|
||
|
addq $8, %rsp
|
||
|
+ call _dtors
|
||
|
|
||
|
.exit:
|
||
|
ret
|
||
|
diff --git a/gnuefi/elf_aa64_efi.lds b/gnuefi/elf_aa64_efi.lds
|
||
|
index 836d98255d8..7220636e40c 100644
|
||
|
--- a/gnuefi/elf_aa64_efi.lds
|
||
|
+++ b/gnuefi/elf_aa64_efi.lds
|
||
|
@@ -26,6 +26,20 @@ SECTIONS
|
||
|
*(.got.plt)
|
||
|
*(.got)
|
||
|
|
||
|
+ . = ALIGN(16);
|
||
|
+ _init_array = .;
|
||
|
+ *(SORT_BY_NAME(.init_array))
|
||
|
+ _init_array_end = .;
|
||
|
+ __CTOR_LIST__ = .;
|
||
|
+ *(SORT_BY_NAME(.ctors))
|
||
|
+ __CTOR_END__ = .;
|
||
|
+ __DTOR_LIST__ = .;
|
||
|
+ *(SORT_BY_NAME(.dtors))
|
||
|
+ __DTOR_END__ = .;
|
||
|
+ _fini_array = .;
|
||
|
+ *(SORT_BY_NAME(.fini_array))
|
||
|
+ _fini_array_end = .;
|
||
|
+
|
||
|
/* the EFI loader doesn't seem to like a .bss section, so we stick
|
||
|
it all into .data: */
|
||
|
. = ALIGN(16);
|
||
|
@@ -36,6 +50,7 @@ SECTIONS
|
||
|
*(.bss)
|
||
|
*(COMMON)
|
||
|
. = ALIGN(16);
|
||
|
+
|
||
|
_bss_end = .;
|
||
|
}
|
||
|
|
||
|
diff --git a/gnuefi/elf_arm_efi.lds b/gnuefi/elf_arm_efi.lds
|
||
|
index 665bbdbf065..f891921e58f 100644
|
||
|
--- a/gnuefi/elf_arm_efi.lds
|
||
|
+++ b/gnuefi/elf_arm_efi.lds
|
||
|
@@ -26,6 +26,20 @@ SECTIONS
|
||
|
*(.got.plt)
|
||
|
*(.got)
|
||
|
|
||
|
+ . = ALIGN(16);
|
||
|
+ _init_array = .;
|
||
|
+ *(SORT_BY_NAME(.init_array))
|
||
|
+ _init_array_end = .;
|
||
|
+ __CTOR_LIST__ = .;
|
||
|
+ *(SORT_BY_NAME(.ctors))
|
||
|
+ __CTOR_END__ = .;
|
||
|
+ __DTOR_LIST__ = .;
|
||
|
+ *(SORT_BY_NAME(.dtors))
|
||
|
+ __DTOR_END__ = .;
|
||
|
+ _fini_array = .;
|
||
|
+ *(SORT_BY_NAME(.fini_array))
|
||
|
+ _fini_array_end = .;
|
||
|
+
|
||
|
/* the EFI loader doesn't seem to like a .bss section, so we stick
|
||
|
it all into .data: */
|
||
|
. = ALIGN(16);
|
||
|
diff --git a/gnuefi/elf_ia32_efi.lds b/gnuefi/elf_ia32_efi.lds
|
||
|
index f27fe5fc6e6..739c370c9eb 100644
|
||
|
--- a/gnuefi/elf_ia32_efi.lds
|
||
|
+++ b/gnuefi/elf_ia32_efi.lds
|
||
|
@@ -40,6 +40,21 @@ SECTIONS
|
||
|
*(.sdata)
|
||
|
*(.got.plt)
|
||
|
*(.got)
|
||
|
+
|
||
|
+ . = ALIGN(16);
|
||
|
+ _init_array = .;
|
||
|
+ *(SORT_BY_NAME(.init_array))
|
||
|
+ _init_array_end = .;
|
||
|
+ __CTOR_LIST__ = .;
|
||
|
+ *(SORT_BY_NAME(.ctors))
|
||
|
+ __CTOR_END__ = .;
|
||
|
+ __DTOR_LIST__ = .;
|
||
|
+ *(SORT_BY_NAME(.dtors))
|
||
|
+ __DTOR_END__ = .;
|
||
|
+ _fini_array = .;
|
||
|
+ *(SORT_BY_NAME(.fini_array))
|
||
|
+ _fini_array_end = .;
|
||
|
+
|
||
|
/* the EFI loader doesn't seem to like a .bss section, so we stick
|
||
|
it all into .data: */
|
||
|
*(.sbss)
|
||
|
diff --git a/gnuefi/elf_ia32_fbsd_efi.lds b/gnuefi/elf_ia32_fbsd_efi.lds
|
||
|
index cd309e24f7f..33c38a0b2d0 100644
|
||
|
--- a/gnuefi/elf_ia32_fbsd_efi.lds
|
||
|
+++ b/gnuefi/elf_ia32_fbsd_efi.lds
|
||
|
@@ -40,6 +40,21 @@ SECTIONS
|
||
|
*(.sdata)
|
||
|
*(.got.plt)
|
||
|
*(.got)
|
||
|
+
|
||
|
+ . = ALIGN(16);
|
||
|
+ _init_array = .;
|
||
|
+ *(SORT_BY_NAME(.init_array))
|
||
|
+ _init_array_end = .;
|
||
|
+ __CTOR_LIST__ = .;
|
||
|
+ *(SORT_BY_NAME(.ctors))
|
||
|
+ __CTOR_END__ = .;
|
||
|
+ __DTOR_LIST__ = .;
|
||
|
+ *(SORT_BY_NAME(.dtors))
|
||
|
+ __DTOR_END__ = .;
|
||
|
+ _fini_array = .;
|
||
|
+ *(SORT_BY_NAME(.fini_array))
|
||
|
+ _fini_array_end = .;
|
||
|
+
|
||
|
/* the EFI loader doesn't seem to like a .bss section, so we stick
|
||
|
it all into .data: */
|
||
|
*(.sbss)
|
||
|
diff --git a/gnuefi/elf_ia64_efi.lds b/gnuefi/elf_ia64_efi.lds
|
||
|
index 190792a0c94..5afd6443722 100644
|
||
|
--- a/gnuefi/elf_ia64_efi.lds
|
||
|
+++ b/gnuefi/elf_ia64_efi.lds
|
||
|
@@ -39,6 +39,21 @@ SECTIONS
|
||
|
*(.data*)
|
||
|
*(.gnu.linkonce.d*)
|
||
|
*(.plabel) /* data whose relocs we want to ignore */
|
||
|
+
|
||
|
+ . = ALIGN(16);
|
||
|
+ _init_array = .;
|
||
|
+ *(SORT_BY_NAME(.init_array))
|
||
|
+ _init_array_end = .;
|
||
|
+ __CTOR_LIST__ = .;
|
||
|
+ *(SORT_BY_NAME(.ctors))
|
||
|
+ __CTOR_END__ = .;
|
||
|
+ __DTOR_LIST__ = .;
|
||
|
+ *(SORT_BY_NAME(.dtors))
|
||
|
+ __DTOR_END__ = .;
|
||
|
+ _fini_array = .;
|
||
|
+ *(SORT_BY_NAME(.fini_array))
|
||
|
+ _fini_array_end = .;
|
||
|
+
|
||
|
/* the EFI loader doesn't seem to like a .bss section, so we stick
|
||
|
it all into .data: */
|
||
|
*(.dynbss)
|
||
|
diff --git a/gnuefi/elf_mips64el_efi.lds b/gnuefi/elf_mips64el_efi.lds
|
||
|
index 4d1a077d8f8..cc0eee3bdcd 100644
|
||
|
--- a/gnuefi/elf_mips64el_efi.lds
|
||
|
+++ b/gnuefi/elf_mips64el_efi.lds
|
||
|
@@ -27,6 +27,20 @@ SECTIONS
|
||
|
HIDDEN (_gp = ALIGN (16) + 0x7ff0);
|
||
|
*(.got)
|
||
|
|
||
|
+ . = ALIGN(16);
|
||
|
+ _init_array = .;
|
||
|
+ *(SORT_BY_NAME(.init_array))
|
||
|
+ _init_array_end = .;
|
||
|
+ __CTOR_LIST__ = .;
|
||
|
+ *(SORT_BY_NAME(.ctors))
|
||
|
+ __CTOR_END__ = .;
|
||
|
+ __DTOR_LIST__ = .;
|
||
|
+ *(SORT_BY_NAME(.dtors))
|
||
|
+ __DTOR_END__ = .;
|
||
|
+ _fini_array = .;
|
||
|
+ *(SORT_BY_NAME(.fini_array))
|
||
|
+ _fini_array_end = .;
|
||
|
+
|
||
|
/* the EFI loader doesn't seem to like a .bss section, so we stick
|
||
|
it all into .data: */
|
||
|
. = ALIGN(16);
|
||
|
diff --git a/gnuefi/elf_x64_efi.lds b/gnuefi/elf_x64_efi.lds
|
||
|
index c7a105898c8..356e63bb8a7 100644
|
||
|
--- a/gnuefi/elf_x64_efi.lds
|
||
|
+++ b/gnuefi/elf_x64_efi.lds
|
||
|
@@ -30,6 +30,7 @@ SECTIONS
|
||
|
{
|
||
|
*(.reloc)
|
||
|
}
|
||
|
+
|
||
|
. = ALIGN(4096);
|
||
|
.data :
|
||
|
{
|
||
|
@@ -39,6 +40,21 @@ SECTIONS
|
||
|
*(.got)
|
||
|
*(.data*)
|
||
|
*(.sdata)
|
||
|
+
|
||
|
+ . = ALIGN(16);
|
||
|
+ _init_array = .;
|
||
|
+ *(SORT_BY_NAME(.init_array))
|
||
|
+ _init_array_end = .;
|
||
|
+ __CTOR_LIST__ = .;
|
||
|
+ *(SORT_BY_NAME(.ctors))
|
||
|
+ __CTOR_END__ = .;
|
||
|
+ __DTOR_LIST__ = .;
|
||
|
+ *(SORT_BY_NAME(.dtors))
|
||
|
+ __DTOR_END__ = .;
|
||
|
+ _fini_array = .;
|
||
|
+ *(SORT_BY_NAME(.fini_array))
|
||
|
+ _fini_array_end = .;
|
||
|
+
|
||
|
/* the EFI loader doesn't seem to like a .bss section, so we stick
|
||
|
it all into .data: */
|
||
|
*(.sbss)
|
||
|
diff --git a/gnuefi/elf_x64_fbsd_efi.lds b/gnuefi/elf_x64_fbsd_efi.lds
|
||
|
index 705719bf68b..e371e5b784f 100644
|
||
|
--- a/gnuefi/elf_x64_fbsd_efi.lds
|
||
|
+++ b/gnuefi/elf_x64_fbsd_efi.lds
|
||
|
@@ -36,6 +36,21 @@ SECTIONS
|
||
|
*(.got)
|
||
|
*(.data*)
|
||
|
*(.sdata)
|
||
|
+
|
||
|
+ . = ALIGN(16);
|
||
|
+ _init_array = .;
|
||
|
+ *(SORT_BY_NAME(.init_array))
|
||
|
+ _init_array_end = .;
|
||
|
+ __CTOR_LIST__ = .;
|
||
|
+ *(SORT_BY_NAME(.ctors))
|
||
|
+ __CTOR_END__ = .;
|
||
|
+ __DTOR_LIST__ = .;
|
||
|
+ *(SORT_BY_NAME(.dtors))
|
||
|
+ __DTOR_END__ = .;
|
||
|
+ _fini_array = .;
|
||
|
+ *(SORT_BY_NAME(.fini_array))
|
||
|
+ _fini_array_end = .;
|
||
|
+
|
||
|
/* the EFI loader doesn't seem to like a .bss section, so we stick
|
||
|
it all into .data: */
|
||
|
*(.sbss)
|
||
|
diff --git a/lib/Makefile b/lib/Makefile
|
||
|
index 8bf94000e33..6d7896b0496 100644
|
||
|
--- a/lib/Makefile
|
||
|
+++ b/lib/Makefile
|
||
|
@@ -43,7 +43,7 @@ include $(SRCDIR)/../Make.defaults
|
||
|
TOPDIR = $(SRCDIR)/..
|
||
|
|
||
|
CDIR = $(TOPDIR)/..
|
||
|
-FILES = boxdraw smbios console crc data debug dpath \
|
||
|
+FILES = boxdraw smbios console crc ctors data debug dpath \
|
||
|
error event exit guid hand hw init lock \
|
||
|
misc print sread str cmdline \
|
||
|
runtime/rtlock runtime/efirtlib runtime/rtstr runtime/vm runtime/rtdata \
|
||
|
diff --git a/lib/ctors.c b/lib/ctors.c
|
||
|
new file mode 100644
|
||
|
index 00000000000..dc979e7b442
|
||
|
--- /dev/null
|
||
|
+++ b/lib/ctors.c
|
||
|
@@ -0,0 +1,45 @@
|
||
|
+/*
|
||
|
+ * ctors.c
|
||
|
+ * Copyright 2019 Peter Jones <pjones@redhat.com>
|
||
|
+ *
|
||
|
+ */
|
||
|
+
|
||
|
+#include <efi.h>
|
||
|
+#include <efilib.h>
|
||
|
+
|
||
|
+extern UINTN _init_array, _init_array_end;
|
||
|
+extern UINTN __CTOR_LIST__, __CTOR_END__;
|
||
|
+extern UINTN _fini_array, _fini_array_end;
|
||
|
+extern UINTN __DTOR_LIST__, __DTOR_END__;
|
||
|
+
|
||
|
+typedef void (*funcp)(void);
|
||
|
+
|
||
|
+void _ctors(EFI_HANDLE image, EFI_SYSTEM_TABLE *systab)
|
||
|
+{
|
||
|
+ InitializeLib(image, systab);
|
||
|
+
|
||
|
+ for (funcp *location = (void *)&_init_array; location < (funcp *)&_init_array_end; location++) {
|
||
|
+ funcp func = *location;
|
||
|
+ func();
|
||
|
+ }
|
||
|
+
|
||
|
+ for (funcp *location = (void *)&__CTOR_LIST__; location < (funcp *)&__CTOR_END__; location++) {
|
||
|
+ funcp func = *location;
|
||
|
+ func();
|
||
|
+ }
|
||
|
+}
|
||
|
+
|
||
|
+void _dtors(EFI_HANDLE image EFI_UNUSED, EFI_SYSTEM_TABLE *systab EFI_UNUSED)
|
||
|
+{
|
||
|
+ for (funcp *location = (void *)&__DTOR_LIST__; location < (funcp *)&__DTOR_END__; location++) {
|
||
|
+ funcp func = *location;
|
||
|
+ func();
|
||
|
+ }
|
||
|
+
|
||
|
+ for (funcp *location = (void *)&_fini_array; location < (funcp *)&_fini_array_end; location++) {
|
||
|
+ funcp func = *location;
|
||
|
+ func();
|
||
|
+ }
|
||
|
+}
|
||
|
+
|
||
|
+// vim:fenc=utf-8:tw=75:noet
|
||
|
diff --git a/lib/init.c b/lib/init.c
|
||
|
index 4f238c0a2cc..257366812ce 100644
|
||
|
--- a/lib/init.c
|
||
|
+++ b/lib/init.c
|
||
|
@@ -21,6 +21,13 @@ EFIDebugVariable (
|
||
|
VOID
|
||
|
);
|
||
|
|
||
|
+#if defined(__x86_64__) || defined(__i386__) || defined(__i686__)
|
||
|
+static inline void pause(void)
|
||
|
+{
|
||
|
+ __asm__ __volatile__("pause");
|
||
|
+}
|
||
|
+#endif
|
||
|
+
|
||
|
VOID
|
||
|
InitializeLib (
|
||
|
IN EFI_HANDLE ImageHandle,
|
||
|
@@ -46,53 +53,56 @@ Returns:
|
||
|
EFI_STATUS Status;
|
||
|
CHAR8 *LangCode;
|
||
|
|
||
|
- if (!LibInitialized) {
|
||
|
- LibInitialized = TRUE;
|
||
|
- LibFwInstance = FALSE;
|
||
|
- LibImageHandle = ImageHandle;
|
||
|
-
|
||
|
-
|
||
|
- //
|
||
|
- // Set up global pointer to the system table, boot services table,
|
||
|
- // and runtime services table
|
||
|
- //
|
||
|
-
|
||
|
- ST = SystemTable;
|
||
|
- BS = SystemTable->BootServices;
|
||
|
- RT = SystemTable->RuntimeServices;
|
||
|
-// ASSERT (CheckCrc(0, &ST->Hdr));
|
||
|
-// ASSERT (CheckCrc(0, &BS->Hdr));
|
||
|
-// ASSERT (CheckCrc(0, &RT->Hdr));
|
||
|
-
|
||
|
-
|
||
|
- //
|
||
|
- // Initialize pool allocation type
|
||
|
- //
|
||
|
-
|
||
|
- if (ImageHandle) {
|
||
|
- Status = uefi_call_wrapper(
|
||
|
- BS->HandleProtocol,
|
||
|
- 3,
|
||
|
- ImageHandle,
|
||
|
- &LoadedImageProtocol,
|
||
|
- (VOID*)&LoadedImage
|
||
|
- );
|
||
|
-
|
||
|
- if (!EFI_ERROR(Status)) {
|
||
|
- PoolAllocationType = LoadedImage->ImageDataType;
|
||
|
- }
|
||
|
- EFIDebugVariable ();
|
||
|
+ register volatile UINTN x = 0;
|
||
|
+ extern char _text, _data;
|
||
|
+
|
||
|
+ if (LibInitialized)
|
||
|
+ return;
|
||
|
+
|
||
|
+ LibInitialized = TRUE;
|
||
|
+ LibFwInstance = FALSE;
|
||
|
+ LibImageHandle = ImageHandle;
|
||
|
+
|
||
|
+ //
|
||
|
+ // Set up global pointer to the system table, boot services table,
|
||
|
+ // and runtime services table
|
||
|
+ //
|
||
|
+
|
||
|
+ ST = SystemTable;
|
||
|
+ BS = SystemTable->BootServices;
|
||
|
+ RT = SystemTable->RuntimeServices;
|
||
|
+ // ASSERT (CheckCrc(0, &ST->Hdr));
|
||
|
+ // ASSERT (CheckCrc(0, &BS->Hdr));
|
||
|
+ // ASSERT (CheckCrc(0, &RT->Hdr));
|
||
|
+
|
||
|
+
|
||
|
+ //
|
||
|
+ // Initialize pool allocation type
|
||
|
+ //
|
||
|
+
|
||
|
+ if (ImageHandle) {
|
||
|
+ Status = uefi_call_wrapper(
|
||
|
+ BS->HandleProtocol,
|
||
|
+ 3,
|
||
|
+ ImageHandle,
|
||
|
+ &LoadedImageProtocol,
|
||
|
+ (VOID*)&LoadedImage
|
||
|
+ );
|
||
|
+
|
||
|
+ if (!EFI_ERROR(Status)) {
|
||
|
+ PoolAllocationType = LoadedImage->ImageDataType;
|
||
|
}
|
||
|
-
|
||
|
- //
|
||
|
- // Initialize Guid table
|
||
|
- //
|
||
|
-
|
||
|
- InitializeGuid();
|
||
|
-
|
||
|
- InitializeLibPlatform(ImageHandle,SystemTable);
|
||
|
+ EFIDebugVariable ();
|
||
|
}
|
||
|
|
||
|
+ //
|
||
|
+ // Initialize Guid table
|
||
|
+ //
|
||
|
+
|
||
|
+ InitializeGuid();
|
||
|
+
|
||
|
+ InitializeLibPlatform(ImageHandle,SystemTable);
|
||
|
+
|
||
|
//
|
||
|
//
|
||
|
//
|
||
|
@@ -104,6 +114,20 @@ Returns:
|
||
|
FreePool (LangCode);
|
||
|
}
|
||
|
}
|
||
|
+
|
||
|
+ Print(L"add-symbol-file x86_64/apps/ctors_test.so 0x%08x -s .data 0x%08x\n",
|
||
|
+ &_text, &_data);
|
||
|
+ Print(L"Pausing for debugger attachment.\n");
|
||
|
+
|
||
|
+ x = 1;
|
||
|
+ while (x++) {
|
||
|
+ /* Make this so it can't /totally/ DoS us. */
|
||
|
+#if defined(__x86_64__) || defined(__i386__) || defined(__i686__)
|
||
|
+ if (x > 4294967294ULL)
|
||
|
+ break;
|
||
|
+#endif
|
||
|
+ pause();
|
||
|
+ }
|
||
|
}
|
||
|
|
||
|
VOID
|