diff options
author | Roland McGrath <roland@hack.frob.com> | 2015-01-05 14:01:49 -0800 |
---|---|---|
committer | Roland McGrath <roland@hack.frob.com> | 2015-01-05 15:42:16 -0800 |
commit | 46abb64d6287d09100b147d062f6810066389b7e (patch) | |
tree | 9102447cb3ce0baaf29cb4041d8bb915f1185225 | |
parent | 61695fb2bab724ed69057c3eff03253708f96517 (diff) | |
download | glibc-46abb64d6287d09100b147d062f6810066389b7e.zip glibc-46abb64d6287d09100b147d062f6810066389b7e.tar.gz glibc-46abb64d6287d09100b147d062f6810066389b7e.tar.bz2 |
ARM: Consolidate with generic unwinder wrapper code
-rw-r--r-- | ChangeLog | 28 | ||||
-rw-r--r-- | sysdeps/arm/Makefile | 12 | ||||
-rw-r--r-- | sysdeps/arm/arm-unwind-resume.S | 46 | ||||
-rw-r--r-- | sysdeps/arm/pt-arm-unwind-resume.S | 2 | ||||
-rw-r--r-- | sysdeps/arm/rt-arm-unwind-resume.S | 1 | ||||
-rw-r--r-- | sysdeps/arm/unwind-resume.h | 33 | ||||
-rw-r--r-- | sysdeps/generic/unwind-resume.h | 33 | ||||
-rw-r--r-- | sysdeps/gnu/unwind-resume.c | 35 | ||||
-rw-r--r-- | sysdeps/nptl/unwind-forcedunwind.c | 25 | ||||
-rw-r--r-- | sysdeps/unix/sysv/linux/arm/unwind-forcedunwind.c | 158 | ||||
-rw-r--r-- | sysdeps/unix/sysv/linux/arm/unwind-resume.c | 101 |
11 files changed, 181 insertions, 293 deletions
@@ -1,3 +1,31 @@ +2015-01-05 Roland McGrath <roland@hack.frob.com> + + * sysdeps/generic/unwind-resume.h: New file. + * sysdeps/gnu/unwind-resume.c: Include it. + (libgcc_s_personality): Use PERSONALITY_PROTO macro for the prototype. + (__gcc_personality_v0): Likewise, and PERSONALITY_ARGS for the callee + argument list. + (libgcc_s_resume): Variable renamed to __libgcc_s_resume, made hidden + global rather than static. + (_Unwind_Resume): Update user. + Conditionalize definition on [!HAVE_ARCH_UNWIND_RESUME]. + (init): Likewise. Renamed to __libgcc_s_init, made hidden global + rather than static. Add __attribute__ ((cold)). + (_Unwind_Resume, __gcc_personality_v0): Update callers. + * sysdeps/nptl/unwind-forcedunwind.c: Likewise. + * sysdeps/arm/arm-unwind-resume.S: New file. + * sysdeps/arm/rt-arm-unwind-resume.S: New file. + * sysdeps/arm/pt-arm-unwind-resume.S: New file. + * sysdeps/arm/Makefile [$(subdir) = csu] + (sysdep_routines, shared-only-routines): Add arm-unwind-resume. + [$(subdir) = rt] (librt-sysdep_routines, librt-shared-only-routines): + Add rt-arm-unwind-resume. + [$(subdir) = nptl] + (libpthread-sysdep_routines, libpthread-shared-only-routines): + Add pt-arm-unwind-resume. + * sysdeps/unix/sysv/linux/arm/unwind-resume.c: File removed. + * sysdeps/unix/sysv/linux/arm/unwind-forcedunwind.c: File removed. + 2015-01-05 Joseph Myers <joseph@codesourcery.com> [BZ #17748] diff --git a/sysdeps/arm/Makefile b/sysdeps/arm/Makefile index db60a17..f72cce0 100644 --- a/sysdeps/arm/Makefile +++ b/sysdeps/arm/Makefile @@ -50,6 +50,9 @@ shared-only-routines += libc-aeabi_read_tp # cantunwind marker. There's one in start.S. To make sure we reach it, add # unwind tables for __libc_start_main. CFLAGS-libc-start.c += -fexceptions + +sysdep_routines += arm-unwind-resume +shared-only-routines += arm-unwind-resume endif ifeq ($(subdir),gmon) @@ -61,6 +64,11 @@ CFLAGS-backtrace.c += -funwind-tables endif ifeq ($(subdir),rt) -librt-sysdep_routines += rt-aeabi_unwind_cpp_pr1 -librt-shared-only-routines += rt-aeabi_unwind_cpp_pr1 +librt-sysdep_routines += rt-aeabi_unwind_cpp_pr1 rt-arm-unwind-resume +librt-shared-only-routines += rt-aeabi_unwind_cpp_pr1 rt-arm-unwind-resume +endif + +ifeq ($(subdir),nptl) +libpthread-sysdep_routines += pt-arm-unwind-resume +libpthread-shared-only-routines += pt-arm-unwind-resume endif diff --git a/sysdeps/arm/arm-unwind-resume.S b/sysdeps/arm/arm-unwind-resume.S new file mode 100644 index 0000000..d201788 --- /dev/null +++ b/sysdeps/arm/arm-unwind-resume.S @@ -0,0 +1,46 @@ +/* _Unwind_Resume wrapper for ARM EABI. + Copyright (C) 2015 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public License as + published by the Free Software Foundation; either version 2.1 of the + License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library. If not, see + <http://www.gnu.org/licenses/>. */ + +#include <sysdep.h> + +/* This is just implementing exactly what the C version does. + We do it in assembly just to ensure that we get an unmolested tail + call to the libgcc function, which is necessary for the ARM unwinder. */ + +ENTRY (_Unwind_Resume) + LDR_HIDDEN (ip, ip, __libgcc_s_resume, 0) + cmp ip, #0 + beq 1f +0: PTR_DEMANGLE (ip, ip, r2, r3) + bx ip + + /* We need to save and restore LR (for our own return address) + and R0 (for the argument to _Unwind_Resume) around the call. */ +1: push {r0, lr} + cfi_adjust_cfa_offset (8) + cfi_rel_offset (r0, 0) + cfi_rel_offset (lr, 4) + bl __libgcc_s_init + pop {r0, lr} + cfi_adjust_cfa_offset (-8) + cfi_restore (r0) + cfi_restore (lr) + + LDR_HIDDEN (ip, ip, __libgcc_s_resume, 0) + b 0b +END (_Unwind_Resume) diff --git a/sysdeps/arm/pt-arm-unwind-resume.S b/sysdeps/arm/pt-arm-unwind-resume.S new file mode 100644 index 0000000..7cb555c --- /dev/null +++ b/sysdeps/arm/pt-arm-unwind-resume.S @@ -0,0 +1,2 @@ +#define __libgcc_s_init pthread_cancel_init +#include <arm-unwind-resume.S> diff --git a/sysdeps/arm/rt-arm-unwind-resume.S b/sysdeps/arm/rt-arm-unwind-resume.S new file mode 100644 index 0000000..9144b0c --- /dev/null +++ b/sysdeps/arm/rt-arm-unwind-resume.S @@ -0,0 +1 @@ +#include <arm-unwind-resume.S> diff --git a/sysdeps/arm/unwind-resume.h b/sysdeps/arm/unwind-resume.h new file mode 100644 index 0000000..1474bb0 --- /dev/null +++ b/sysdeps/arm/unwind-resume.h @@ -0,0 +1,33 @@ +/* Definitions for unwind-resume.c. ARM (EABI) version. + Copyright (C) 2014 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public License as + published by the Free Software Foundation; either version 2.1 of the + License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; see the file COPYING.LIB. If + not, see <http://www.gnu.org/licenses/>. */ + +/* The EABI personality routine has a different signature than the + canonical one. These macros tell sysdeps/gnu/unwind*.c how to + define __gcc_personality_v0. */ +#define PERSONALITY_PROTO \ + (_Unwind_State state, \ + struct _Unwind_Exception *ue_header, \ + struct _Unwind_Context *context) +#define PERSONALITY_ARGS \ + (state, ue_header, context) + +/* It's vitally important that _Unwind_Resume not have a stack frame; the + ARM unwinder relies on register state at entrance. So we write this in + assembly (see arm-unwind-resume.S). This macro tells the generic code + not to provide the generic C definition. */ +#define HAVE_ARCH_UNWIND_RESUME 1 diff --git a/sysdeps/generic/unwind-resume.h b/sysdeps/generic/unwind-resume.h new file mode 100644 index 0000000..74c1a51 --- /dev/null +++ b/sysdeps/generic/unwind-resume.h @@ -0,0 +1,33 @@ +/* Definitions for unwind-resume.c. Generic version. + Copyright (C) 2015 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public License as + published by the Free Software Foundation; either version 2.1 of the + License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with the GNU C Library; see the file COPYING.LIB. If + not, see <http://www.gnu.org/licenses/>. */ + +/* These describe the arguments to unwinder personality functions, + specifically __gcc_personality_v0. A machine-specific sysdeps + file might define them differently. */ +#define PERSONALITY_PROTO \ + (int version, _Unwind_Action actions, \ + _Unwind_Exception_Class exception_class, \ + struct _Unwind_Exception *ue_header, \ + struct _Unwind_Context *context) +#define PERSONALITY_ARGS \ + (version, actions, exception_class, ue_header, context) + +/* This is defined nonzero by a machine-specific sysdeps file if + _Unwind_Resume is provided separately and thus the generic C + version should not be defined. */ +#define HAVE_ARCH_UNWIND_RESUME 0 diff --git a/sysdeps/gnu/unwind-resume.c b/sysdeps/gnu/unwind-resume.c index 3f8b1de..267949e 100644 --- a/sysdeps/gnu/unwind-resume.c +++ b/sysdeps/gnu/unwind-resume.c @@ -21,15 +21,16 @@ #include <unwind.h> #include <gnu/lib-names.h> #include <sysdep.h> +#include <unwind-resume.h> -static void (*libgcc_s_resume) (struct _Unwind_Exception *exc) - __attribute__ ((noreturn)); -static _Unwind_Reason_Code (*libgcc_s_personality) - (int, _Unwind_Action, _Unwind_Exception_Class, struct _Unwind_Exception *, - struct _Unwind_Context *); -static void -init (void) +void (*__libgcc_s_resume) (struct _Unwind_Exception *exc) + attribute_hidden __attribute__ ((noreturn)); + +static _Unwind_Reason_Code (*libgcc_s_personality) PERSONALITY_PROTO; + +void attribute_hidden __attribute__ ((cold)) +__libgcc_s_init (void) { void *resume, *personality; void *handle; @@ -43,33 +44,31 @@ init (void) " must be installed for pthread_cancel to work\n"); PTR_MANGLE (resume); - libgcc_s_resume = resume; + __libgcc_s_resume = resume; PTR_MANGLE (personality); libgcc_s_personality = personality; } +#if !HAVE_ARCH_UNWIND_RESUME void _Unwind_Resume (struct _Unwind_Exception *exc) { - if (__glibc_unlikely (libgcc_s_resume == NULL)) - init (); + if (__glibc_unlikely (__libgcc_s_resume == NULL)) + __libgcc_s_init (); - __typeof (libgcc_s_resume) resume = libgcc_s_resume; + __typeof (__libgcc_s_resume) resume = __libgcc_s_resume; PTR_DEMANGLE (resume); (*resume) (exc); } +#endif _Unwind_Reason_Code -__gcc_personality_v0 (int version, _Unwind_Action actions, - _Unwind_Exception_Class exception_class, - struct _Unwind_Exception *ue_header, - struct _Unwind_Context *context) +__gcc_personality_v0 PERSONALITY_PROTO { if (__glibc_unlikely (libgcc_s_personality == NULL)) - init (); + __libgcc_s_init (); __typeof (libgcc_s_personality) personality = libgcc_s_personality; PTR_DEMANGLE (personality); - - return (*personality) (version, actions, exception_class, ue_header, context); + return (*personality) PERSONALITY_ARGS; } diff --git a/sysdeps/nptl/unwind-forcedunwind.c b/sysdeps/nptl/unwind-forcedunwind.c index 4c8ef97..55768a5 100644 --- a/sysdeps/nptl/unwind-forcedunwind.c +++ b/sysdeps/nptl/unwind-forcedunwind.c @@ -22,12 +22,12 @@ #include <pthreadP.h> #include <sysdep.h> #include <gnu/lib-names.h> +#include <unwind-resume.h> static void *libgcc_s_handle; -static void (*libgcc_s_resume) (struct _Unwind_Exception *exc); -static _Unwind_Reason_Code (*libgcc_s_personality) - (int, _Unwind_Action, _Unwind_Exception_Class, struct _Unwind_Exception *, - struct _Unwind_Context *); +void (*__libgcc_s_resume) (struct _Unwind_Exception *exc) + attribute_hidden __attribute__ ((noreturn)); +static _Unwind_Reason_Code (*libgcc_s_personality) PERSONALITY_PROTO; static _Unwind_Reason_Code (*libgcc_s_forcedunwind) (struct _Unwind_Exception *, _Unwind_Stop_Fn, void *); static _Unwind_Word (*libgcc_s_getcfa) (struct _Unwind_Context *); @@ -64,7 +64,7 @@ pthread_cancel_init (void) __libc_fatal (LIBGCC_S_SO " must be installed for pthread_cancel to work\n"); PTR_MANGLE (resume); - libgcc_s_resume = resume; + __libgcc_s_resume = resume; PTR_MANGLE (personality); libgcc_s_personality = personality; PTR_MANGLE (forcedunwind); @@ -90,6 +90,7 @@ __unwind_freeres (void) } } +#if !HAVE_ARCH_UNWIND_RESUME void _Unwind_Resume (struct _Unwind_Exception *exc) { @@ -98,27 +99,23 @@ _Unwind_Resume (struct _Unwind_Exception *exc) else atomic_read_barrier (); - void (*resume) (struct _Unwind_Exception *exc) = libgcc_s_resume; + void (*resume) (struct _Unwind_Exception *exc) = __libgcc_s_resume; PTR_DEMANGLE (resume); resume (exc); } +#endif _Unwind_Reason_Code -__gcc_personality_v0 (int version, _Unwind_Action actions, - _Unwind_Exception_Class exception_class, - struct _Unwind_Exception *ue_header, - struct _Unwind_Context *context) +__gcc_personality_v0 PERSONALITY_PROTO { if (__glibc_unlikely (libgcc_s_handle == NULL)) pthread_cancel_init (); else atomic_read_barrier (); - _Unwind_Reason_Code (*personality) - (int, _Unwind_Action, _Unwind_Exception_Class, struct _Unwind_Exception *, - struct _Unwind_Context *) = libgcc_s_personality; + __typeof (libgcc_s_personality) personality = libgcc_s_personality; PTR_DEMANGLE (personality); - return personality (version, actions, exception_class, ue_header, context); + return (*personality) PERSONALITY_ARGS; } _Unwind_Reason_Code diff --git a/sysdeps/unix/sysv/linux/arm/unwind-forcedunwind.c b/sysdeps/unix/sysv/linux/arm/unwind-forcedunwind.c deleted file mode 100644 index fab705e..0000000 --- a/sysdeps/unix/sysv/linux/arm/unwind-forcedunwind.c +++ /dev/null @@ -1,158 +0,0 @@ -/* Copyright (C) 2003-2015 Free Software Foundation, Inc. - This file is part of the GNU C Library. - Contributed by Jakub Jelinek <jakub@redhat.com>. - - The GNU C Library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public License as - published by the Free Software Foundation; either version 2.1 of the - License, or (at your option) any later version. - - The GNU C Library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with the GNU C Library. If not, see - <http://www.gnu.org/licenses/>. */ - -#include <dlfcn.h> -#include <stdio.h> -#include <unwind.h> -#include <pthreadP.h> - -static void *libgcc_s_handle; -static void (*libgcc_s_resume) (struct _Unwind_Exception *exc) - __attribute_used__; -static _Unwind_Reason_Code (*libgcc_s_personality) - (_Unwind_State, struct _Unwind_Exception *, struct _Unwind_Context *); -static _Unwind_Reason_Code (*libgcc_s_forcedunwind) - (struct _Unwind_Exception *, _Unwind_Stop_Fn, void *); -static _Unwind_Word (*libgcc_s_getcfa) (struct _Unwind_Context *); - -void -__attribute_noinline__ -pthread_cancel_init (void) -{ - void *resume, *personality, *forcedunwind, *getcfa; - void *handle; - - if (__builtin_expect (libgcc_s_handle != NULL, 1)) - { - /* Force gcc to reload all values. */ - asm volatile ("" ::: "memory"); - return; - } - - handle = __libc_dlopen ("libgcc_s.so.1"); - - if (handle == NULL - || (resume = __libc_dlsym (handle, "_Unwind_Resume")) == NULL - || (personality = __libc_dlsym (handle, "__gcc_personality_v0")) == NULL - || (forcedunwind = __libc_dlsym (handle, "_Unwind_ForcedUnwind")) - == NULL - || (getcfa = __libc_dlsym (handle, "_Unwind_GetCFA")) == NULL -#ifdef ARCH_CANCEL_INIT - || ARCH_CANCEL_INIT (handle) -#endif - ) - __libc_fatal ("libgcc_s.so.1 must be installed for pthread_cancel to work\n"); - - libgcc_s_resume = resume; - libgcc_s_personality = personality; - libgcc_s_forcedunwind = forcedunwind; - libgcc_s_getcfa = getcfa; - /* Make sure libgcc_s_getcfa is written last. Otherwise, - pthread_cancel_init might return early even when the pointer the - caller is interested in is not initialized yet. */ - atomic_write_barrier (); - libgcc_s_handle = handle; -} - -void -__libc_freeres_fn_section -__unwind_freeres (void) -{ - void *handle = libgcc_s_handle; - if (handle != NULL) - { - libgcc_s_handle = NULL; - __libc_dlclose (handle); - } -} - -/* It's vitally important that _Unwind_Resume not have a stack frame; the - ARM unwinder relies on register state at entrance. So we write this in - assembly. */ - -#define STR1(S) #S -#define STR(S) STR1(S) - -asm ( -" .globl _Unwind_Resume\n" -" .type _Unwind_Resume, %function\n" -"_Unwind_Resume:\n" -" .cfi_sections .debug_frame\n" -" " CFI_STARTPROC "\n" -" push {r4, r5, r6, lr}\n" -" " CFI_ADJUST_CFA_OFFSET (16)" \n" -" " CFI_REL_OFFSET (r4, 0) "\n" -" " CFI_REL_OFFSET (r5, 4) "\n" -" " CFI_REL_OFFSET (r6, 8) "\n" -" " CFI_REL_OFFSET (lr, 12) "\n" -" " CFI_REMEMBER_STATE "\n" -" ldr r4, 1f\n" -" ldr r5, 2f\n" -"3: add r4, pc, r4\n" -" ldr r3, [r4, r5]\n" -" mov r6, r0\n" -" cmp r3, #0\n" -" beq 4f\n" -"5: mov r0, r6\n" -" pop {r4, r5, r6, lr}\n" -" " CFI_ADJUST_CFA_OFFSET (-16) "\n" -" " CFI_RESTORE (r4) "\n" -" " CFI_RESTORE (r5) "\n" -" " CFI_RESTORE (r6) "\n" -" " CFI_RESTORE (lr) "\n" -" bx r3\n" -" " CFI_RESTORE_STATE "\n" -"4: bl pthread_cancel_init\n" -" ldr r3, [r4, r5]\n" -" b 5b\n" -" " CFI_ENDPROC "\n" -" .align 2\n" -"1: .word _GLOBAL_OFFSET_TABLE_ - 3b - " STR (PC_OFS) "\n" -"2: .word libgcc_s_resume(GOTOFF)\n" -" .size _Unwind_Resume, .-_Unwind_Resume\n" -); - -_Unwind_Reason_Code -__gcc_personality_v0 (_Unwind_State state, - struct _Unwind_Exception *ue_header, - struct _Unwind_Context *context) -{ - if (__builtin_expect (libgcc_s_personality == NULL, 0)) - pthread_cancel_init (); - - return libgcc_s_personality (state, ue_header, context); -} - -_Unwind_Reason_Code -_Unwind_ForcedUnwind (struct _Unwind_Exception *exc, _Unwind_Stop_Fn stop, - void *stop_argument) -{ - if (__builtin_expect (libgcc_s_forcedunwind == NULL, 0)) - pthread_cancel_init (); - - return libgcc_s_forcedunwind (exc, stop, stop_argument); -} - -_Unwind_Word -_Unwind_GetCFA (struct _Unwind_Context *context) -{ - if (__builtin_expect (libgcc_s_getcfa == NULL, 0)) - pthread_cancel_init (); - - return libgcc_s_getcfa (context); -} diff --git a/sysdeps/unix/sysv/linux/arm/unwind-resume.c b/sysdeps/unix/sysv/linux/arm/unwind-resume.c deleted file mode 100644 index 1a1e2df..0000000 --- a/sysdeps/unix/sysv/linux/arm/unwind-resume.c +++ /dev/null @@ -1,101 +0,0 @@ -/* Copyright (C) 2003-2015 Free Software Foundation, Inc. - This file is part of the GNU C Library. - Contributed by Jakub Jelinek <jakub@redhat.com>. - - The GNU C Library is free software; you can redistribute it and/or - modify it under the terms of the GNU Lesser General Public License as - published by the Free Software Foundation; either version 2.1 of the - License, or (at your option) any later version. - - The GNU C Library is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public - License along with the GNU C Library. If not, see - <http://www.gnu.org/licenses/>. */ - -#include <dlfcn.h> -#include <stdio.h> -#include <unwind.h> - -static void (*libgcc_s_resume) (struct _Unwind_Exception *exc) - __attribute_used__; -static _Unwind_Reason_Code (*libgcc_s_personality) - (_Unwind_State, struct _Unwind_Exception *, struct _Unwind_Context *); - -static void init (void) __attribute_used__; - -static void -init (void) -{ - void *resume, *personality; - void *handle; - - handle = __libc_dlopen ("libgcc_s.so.1"); - - if (handle == NULL - || (resume = __libc_dlsym (handle, "_Unwind_Resume")) == NULL - || (personality = __libc_dlsym (handle, "__gcc_personality_v0")) == NULL) - __libc_fatal ("libgcc_s.so.1 must be installed for pthread_cancel to work\n"); - - libgcc_s_resume = resume; - libgcc_s_personality = personality; -} - -/* It's vitally important that _Unwind_Resume not have a stack frame; the - ARM unwinder relies on register state at entrance. So we write this in - assembly. */ - -#define STR1(S) #S -#define STR(S) STR1(S) - -asm ( -" .globl _Unwind_Resume\n" -" .type _Unwind_Resume, %function\n" -"_Unwind_Resume:\n" -" .cfi_sections .debug_frame\n" -" " CFI_STARTPROC "\n" -" push {r4, r5, r6, lr}\n" -" " CFI_ADJUST_CFA_OFFSET (16)" \n" -" " CFI_REL_OFFSET (r4, 0) "\n" -" " CFI_REL_OFFSET (r5, 4) "\n" -" " CFI_REL_OFFSET (r6, 8) "\n" -" " CFI_REL_OFFSET (lr, 12) "\n" -" " CFI_REMEMBER_STATE "\n" -" ldr r4, 1f\n" -" ldr r5, 2f\n" -"3: add r4, pc, r4\n" -" ldr r3, [r4, r5]\n" -" mov r6, r0\n" -" cmp r3, #0\n" -" beq 4f\n" -"5: mov r0, r6\n" -" pop {r4, r5, r6, lr}\n" -" " CFI_ADJUST_CFA_OFFSET (-16) "\n" -" " CFI_RESTORE (r4) "\n" -" " CFI_RESTORE (r5) "\n" -" " CFI_RESTORE (r6) "\n" -" " CFI_RESTORE (lr) "\n" -" bx r3\n" -" " CFI_RESTORE_STATE "\n" -"4: bl init\n" -" ldr r3, [r4, r5]\n" -" b 5b\n" -" " CFI_ENDPROC "\n" -" .align 2\n" -"1: .word _GLOBAL_OFFSET_TABLE_ - 3b - " STR (PC_OFS) "\n" -"2: .word libgcc_s_resume(GOTOFF)\n" -" .size _Unwind_Resume, .-_Unwind_Resume\n" -); - -_Unwind_Reason_Code -__gcc_personality_v0 (_Unwind_State state, - struct _Unwind_Exception *ue_header, - struct _Unwind_Context *context) -{ - if (__builtin_expect (libgcc_s_personality == NULL, 0)) - init (); - return libgcc_s_personality (state, ue_header, context); -} |