aboutsummaryrefslogtreecommitdiff
path: root/gcc/config
diff options
context:
space:
mode:
authorRainer Orth <ro@gcc.gnu.org>2011-08-05 14:37:48 +0000
committerRainer Orth <ro@gcc.gnu.org>2011-08-05 14:37:48 +0000
commit201cdb743879cbffd38c53d8ebf85fa9fff1e0e4 (patch)
tree80376027cf518687afe9d3c715d908e42d42c267 /gcc/config
parentd50f4827c7062e3247baf493e646c365114c28cd (diff)
downloadgcc-201cdb743879cbffd38c53d8ebf85fa9fff1e0e4.zip
gcc-201cdb743879cbffd38c53d8ebf85fa9fff1e0e4.tar.gz
gcc-201cdb743879cbffd38c53d8ebf85fa9fff1e0e4.tar.bz2
Makefile.in (UNWIND_H): Remove.
gcc: * Makefile.in (UNWIND_H): Remove. (LIB2ADDEH, LIB2ADDEHSTATIC, LIB2ADDEHSHARED): Move to ../libgcc/Makefile.in. (LIBUNWIND, SHLIBUNWIND_LINK, SHLIBUNWIND_INSTALL): Likewise. (LIBUNWINDDEP): Remove. (libgcc-support): Remove LIB2ADDEH, $(srcdir)/emutls.c dependencies. (libgcc.mvars): Remove LIB2ADDEH, LIB2ADDEHSTATIC, LIB2ADDEHSHARED, LIBUNWIND, SHLIBUNWIND_LINK, SHLIBUNWIND_INSTALL. (stmp-int-hdrs): Remove $(UNWIND_H) dependency. Don't copy $(UNWIND_H). * config.gcc (ia64*-*-linux*): Remove with_system_libunwind handling. * configure.ac (GCC_CHECK_UNWIND_GETIPINFO): Remove. * aclocal.m4: Regenerate. * configure: Regenerate. * emutls.c, unwind-c.c, unwind-compat.c, unwind-compat.h, unwind-dw2-fde-compat.c, unwind-dw2-fde-glibc.c, unwind-dw2-fde.c, unwind-dw2-fde.h, unwind-dw2.c, unwind-dw2.h, unwind-generic.h, unwind-pe.h, unwind-sjlj.c, unwind.inc: Move to ../libgcc. * unwind-dw2-fde-darwin.c: Move to ../libgcc/config. * config/arm/libunwind.S, config/arm/pr-support.c, config/arm/unwind-arm.c, config/arm/unwind-arm.h: Move to ../libgcc/config/arm. * config/arm/t-bpabi (UNWIND_H, LIB2ADDEH): Remove. * config/arm/t-symbian (UNWIND_H, LIB2ADDEH): Remove. * config/frv/t-frv ($(T)frvbegin$(objext)): Use $(srcdir)/../libgcc to refer to unwind-dw2-fde.h. ($(T)frvend$(objext)): Likewise. * config/ia64/t-glibc (LIB2ADDEH): Remove. * config/ia64/t-glibc-libunwind: Move to ../libgcc/config/ia64. * config/ia64/fde-glibc.c, config/ia64/fde-vms.c, config/ia64/unwind-ia64.c, config/ia64/unwind-ia64.h: Move to ../libgcc/config/ia64. * config/ia64/t-hpux (LIB2ADDEH): Remove. * config/ia64/t-ia64 (LIB2ADDEH): Remove. * config/ia64/t-vms (LIB2ADDEH): Remove. * config/ia64/vms.h (UNW_IVMS_MODE, MD_UNW_COMPATIBLE_PERSONALITY_P): Remove. * config/picochip/t-picochip (LIB2ADDEH): Remove. * config/rs6000/aix.h (R_LR, MD_FROB_UPDATE_CONTEXT): Remove. * config/rs6000/t-darwin (LIB2ADDEH): Remove. * config/rs6000/darwin-fallback.c: Move to ../libgcc/config/rs6000. * config/sh/t-sh ($(T)unwind-dw2-Os-4-200.o): Use $(srcdir)/../libgcc to refer to unwinder sources. * config/spu/t-spu-elf (LIB2ADDEH): Remove. * config/t-darwin (LIB2ADDEH): Remove. * config/t-freebsd (LIB2ADDEH): Remove. * config/t-libunwind (LIB2ADDEH, LIB2ADDEHSTATIC): Remove. * config/t-libunwind-elf: Move to ../libgcc/config. * config/t-linux (LIB2ADDEH): Remove. * config/t-sol2 (LIB2ADDEH): Remove. * config/xtensa/t-xtensa (LIB2ADDEH): Remove. * system.h (MD_FROB_UPDATE_CONTEXT): Poison. gcc/po: * EXCLUDES (unwind-c.c, unwind-dw2-fde-darwin.c) (unwind-dw2-fde-glibc.c, unwind-dw2-fde.c, unwind-dw2-fde.h) (unwind-dw2.c, unwind-pe.h, unwind-sjlj.c, unwind.h): Remove. libgcc: * Makefile.in (LIB2ADDEH, LIB2ADDEHSTATIC, LIB2ADDEHSHARED): New variables. (LIBUNWIND, SHLIBUNWIND_LINK, SHLIBUNWIND_INSTALL): New variables. (LIB2ADDEH, LIB2ADDEHSTATIC, LIB2ADDEHSHARED): Add $(srcdir)/emutls.c. (install-unwind_h): New target. (all): Depend on it. * config.host (unwind_header): New variable. (*-*-freebsd*): Set tmake_file to t-eh-dw2-dip. (*-*-linux*, frv-*-*linux*, *-*-kfreebsd*-gnu, *-*-knetbsd*-gnu, *-*-gnu*): Likewise, also for *-*-kopensolaris*-gnu. (*-*-solaris2*): Add t-eh-dw2-dip to tmake_file. (arm*-*-linux*): Add arm/t-bpabi for arm*-*-linux-*eabi. Set unwind_header. (arm*-*-uclinux*): Add arm/t-bpabi for arm*-*-uclinux*eabi. Set unwind_header. (arm*-*-eabi*, arm*-*-symbianelf*): Add arm/t-bpabi for arm*-*-eabi*. Add arm/t-symbian to tmake_file for arm*-*-symbianelf*. Set unwind_header. (ia64*-*-elf*): Add ia64/t-eh-ia64 to tmake_file. (ia64*-*-freebsd*): Likewise. (ia64*-*-linux*): Add ia64/t-glibc, ia64/t-eh-ia64, t-libunwind to tmake_file. Add t-libunwind-elf, ia64/t-glibc-libunwind unless $with_system_libunwind. (ia64*-*-hpux*): Set tmake_file. (ia64-hp-*vms*): Add ia64/t-eh-ia64 to tmake_file. (picochip-*-*): Set tmake_file. (rs6000-ibm-aix4.[3456789]*, powerpc-ibm-aix4.[3456789]*): Set md_unwind_header. (rs6000-ibm-aix5.1.*, powerpc-ibm-aix5.1.*): Likewise. (rs6000-ibm-aix[56789].*, powerpc-ibm-aix[56789].*): Likewise. (s390x-ibm-tpf*): Add t-eh-dw2-dip to tmake_file. (xtensa*-*-elf*): Set tmake_file. (xtensa*-*-linux*): Likewise. * configure.ac: Include ../config/unwind_ipinfo.m4. Call GCC_CHECK_UNWIND_GETIPINFO. Link unwind.h to $unwind_header. * configure: Regenerate. * emutls.c, unwind-c.c, unwind-compat.c, unwind-compat.h, unwind-dw2-fde-compat.c, unwind-dw2-fde-dip.c, unwind-dw2-fde.c, unwind-dw2-fde.h, unwind-dw2.c, unwind-dw2.h, unwind-generic.h, unwind-pe.h, unwind-sjlj.c, unwind.inc: New files. * config/unwind-dw2-fde-darwin.c: New file. * config/arm/libunwind.S, config/arm/pr-support.c, config/arm/t-bpabi, config/arm/t-symbian, config/arm/unwind-arm.c, config/arm/unwind-arm.h,: New files. * config/ia64/fde-glibc.c, config/ia64/fde-vms.c, config/ia64/t-eh-ia64, config/ia64/t-glibc, config/ia64/t-glibc-libunwind, config/ia64/t-hpux, config/ia64/t-vms, config/ia64/unwind-ia64.c, config/ia64/unwind-ia64.h: New files. * config/picochip/t-picochip: New file. * config/rs6000/aix-unwind.h, config/rs6000/darwin-fallback.c: New files. * config/rs6000/t-darwin (LIB2ADDEH): Set. * config/s390/t-tpf (LIB2ADDEH): Remove. * config/t-darwin (LIB2ADDEH): Set. * config/t-eh-dw2-dip: New file. * config/t-libunwind, config/t-libunwind-elf: New files. * config/t-sol2 (LIB2ADDEH): Remove. * config/xtensa/t-xtensa: New file. gcc/ada: * gcc-interface/Makefile.in (raise-gcc.o): Search $(srcdir)/../libgcc. libgo: * Makefile.am (AM_CFLAGS): Search $(srcdir)/../libgcc. * Makefile.in: Regenerate. libjava: * configure.ac (GCC_UNWIND_INCLUDE): Rename to LIBGCC_UNWIND_INCLUDE. Point to $(multi_basedir)/./libjava/../libgcc. * configure: Regenerate. * Makefile.am (GCC_UNWIND_INCLUDE): Reflect this. * Makefile.in: Regenerate. libobjc: * Makefile.in (INCLUDES): Search $(srcdir)/$(MULTISRCTOP)../libgcc. libstdc++-v3: * acinclude.m4 (GLIBCXX_EXPORT_INCLUDES): Point TOPLEVEL_INCLUDES to $(toplevel_srcdir)/libgcc. * configure: Regenerate. From-SVN: r177447
Diffstat (limited to 'gcc/config')
-rw-r--r--gcc/config/arm/libunwind.S363
-rw-r--r--gcc/config/arm/pr-support.c401
-rw-r--r--gcc/config/arm/t-bpabi5
-rw-r--r--gcc/config/arm/t-symbian4
-rw-r--r--gcc/config/arm/unwind-arm.c1283
-rw-r--r--gcc/config/arm/unwind-arm.h281
-rw-r--r--gcc/config/frv/t-frv6
-rw-r--r--gcc/config/ia64/fde-glibc.c162
-rw-r--r--gcc/config/ia64/fde-vms.c157
-rw-r--r--gcc/config/ia64/t-glibc4
-rw-r--r--gcc/config/ia64/t-glibc-libunwind4
-rw-r--r--gcc/config/ia64/t-hpux4
-rw-r--r--gcc/config/ia64/t-ia643
-rw-r--r--gcc/config/ia64/t-vms2
-rw-r--r--gcc/config/ia64/unwind-ia64.c2458
-rw-r--r--gcc/config/ia64/unwind-ia64.h43
-rw-r--r--gcc/config/ia64/vms.h3
-rw-r--r--gcc/config/picochip/t-picochip3
-rw-r--r--gcc/config/rs6000/aix.h34
-rw-r--r--gcc/config/rs6000/darwin-fallback.c487
-rw-r--r--gcc/config/rs6000/t-darwin4
-rw-r--r--gcc/config/sh/t-sh4
-rw-r--r--gcc/config/spu/t-spu-elf3
-rw-r--r--gcc/config/t-darwin4
-rw-r--r--gcc/config/t-freebsd4
-rw-r--r--gcc/config/t-libunwind5
-rw-r--r--gcc/config/t-libunwind-elf49
-rw-r--r--gcc/config/t-linux4
-rw-r--r--gcc/config/t-sol25
-rw-r--r--gcc/config/xtensa/t-xtensa5
-rw-r--r--gcc/config/xtensa/unwind-dw2-xtensa.c544
-rw-r--r--gcc/config/xtensa/unwind-dw2-xtensa.h50
32 files changed, 10 insertions, 6378 deletions
diff --git a/gcc/config/arm/libunwind.S b/gcc/config/arm/libunwind.S
deleted file mode 100644
index 48eb592..0000000
--- a/gcc/config/arm/libunwind.S
+++ /dev/null
@@ -1,363 +0,0 @@
-/* Support functions for the unwinder.
- Copyright (C) 2003, 2004, 2005, 2007, 2008, 2009, 2010
- Free Software Foundation, Inc.
- Contributed by Paul Brook
-
- This file is free software; you can redistribute it and/or modify it
- under the terms of the GNU General Public License as published by the
- Free Software Foundation; either version 3, or (at your option) any
- later version.
-
- This file 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
- General Public License for more details.
-
- Under Section 7 of GPL version 3, you are granted additional
- permissions described in the GCC Runtime Library Exception, version
- 3.1, as published by the Free Software Foundation.
-
- You should have received a copy of the GNU General Public License and
- a copy of the GCC Runtime Library Exception along with this program;
- see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
- <http://www.gnu.org/licenses/>. */
-
-/* An executable stack is *not* required for these functions. */
-#if defined(__ELF__) && defined(__linux__)
-.section .note.GNU-stack,"",%progbits
-.previous
-#endif
-
-#ifdef __ARM_EABI__
-/* Some attributes that are common to all routines in this file. */
- /* Tag_ABI_align_needed: This code does not require 8-byte
- alignment from the caller. */
- /* .eabi_attribute 24, 0 -- default setting. */
- /* Tag_ABI_align_preserved: This code preserves 8-byte
- alignment in any callee. */
- .eabi_attribute 25, 1
-#endif /* __ARM_EABI__ */
-
-#ifndef __symbian__
-
-#include "lib1funcs.asm"
-
-.macro UNPREFIX name
- .global SYM (\name)
- EQUIV SYM (\name), SYM (__\name)
-.endm
-
-#if (__ARM_ARCH__ == 4)
-/* Some coprocessors require armv5. We know this code will never be run on
- other cpus. Tell gas to allow armv5, but only mark the objects as armv4.
- */
-.arch armv5t
-#ifdef __ARM_ARCH_4T__
-.object_arch armv4t
-#else
-.object_arch armv4
-#endif
-#endif
-
-#ifdef __ARM_ARCH_6M__
-
-/* r0 points to a 16-word block. Upload these values to the actual core
- state. */
-FUNC_START restore_core_regs
- mov r1, r0
- add r1, r1, #52
- ldmia r1!, {r3, r4, r5}
- sub r3, r3, #4
- mov ip, r3
- str r5, [r3]
- mov lr, r4
- /* Restore r8-r11. */
- mov r1, r0
- add r1, r1, #32
- ldmia r1!, {r2, r3, r4, r5}
- mov r8, r2
- mov r9, r3
- mov sl, r4
- mov fp, r5
- mov r1, r0
- add r1, r1, #8
- ldmia r1!, {r2, r3, r4, r5, r6, r7}
- ldr r1, [r0, #4]
- ldr r0, [r0]
- mov sp, ip
- pop {pc}
- FUNC_END restore_core_regs
- UNPREFIX restore_core_regs
-
-/* ARMV6M does not have coprocessors, so these should never be used. */
-FUNC_START gnu_Unwind_Restore_VFP
- RET
-
-/* Store VFR regsters d0-d15 to the address in r0. */
-FUNC_START gnu_Unwind_Save_VFP
- RET
-
-/* Load VFP registers d0-d15 from the address in r0.
- Use this to load from FSTMD format. */
-FUNC_START gnu_Unwind_Restore_VFP_D
- RET
-
-/* Store VFP registers d0-d15 to the address in r0.
- Use this to store in FLDMD format. */
-FUNC_START gnu_Unwind_Save_VFP_D
- RET
-
-/* Load VFP registers d16-d31 from the address in r0.
- Use this to load from FSTMD (=VSTM) format. Needs VFPv3. */
-FUNC_START gnu_Unwind_Restore_VFP_D_16_to_31
- RET
-
-/* Store VFP registers d16-d31 to the address in r0.
- Use this to store in FLDMD (=VLDM) format. Needs VFPv3. */
-FUNC_START gnu_Unwind_Save_VFP_D_16_to_31
- RET
-
-FUNC_START gnu_Unwind_Restore_WMMXD
- RET
-
-FUNC_START gnu_Unwind_Save_WMMXD
- RET
-
-FUNC_START gnu_Unwind_Restore_WMMXC
- RET
-
-FUNC_START gnu_Unwind_Save_WMMXC
- RET
-
-.macro UNWIND_WRAPPER name nargs
- FUNC_START \name
- /* Create a phase2_vrs structure. */
- /* Save r0 in the PC slot so we can use it as a scratch register. */
- push {r0}
- add r0, sp, #4
- push {r0, lr} /* Push original SP and LR. */
- /* Make space for r8-r12. */
- sub sp, sp, #20
- /* Save low registers. */
- push {r0, r1, r2, r3, r4, r5, r6, r7}
- /* Save high registers. */
- add r0, sp, #32
- mov r1, r8
- mov r2, r9
- mov r3, sl
- mov r4, fp
- mov r5, ip
- stmia r0!, {r1, r2, r3, r4, r5}
- /* Restore original low register values. */
- add r0, sp, #4
- ldmia r0!, {r1, r2, r3, r4, r5}
- /* Restore orginial r0. */
- ldr r0, [sp, #60]
- str r0, [sp]
- /* Demand-save flags, plus an extra word for alignment. */
- mov r3, #0
- push {r2, r3}
- /* Point r1 at the block. Pass r[0..nargs) unchanged. */
- add r\nargs, sp, #4
-
- bl SYM (__gnu\name)
-
- ldr r3, [sp, #64]
- add sp, sp, #72
- bx r3
-
- FUNC_END \name
- UNPREFIX \name
-.endm
-
-#else /* !__ARM_ARCH_6M__ */
-
-/* r0 points to a 16-word block. Upload these values to the actual core
- state. */
-ARM_FUNC_START restore_core_regs
- /* We must use sp as the base register when restoring sp. Push the
- last 3 registers onto the top of the current stack to achieve
- this. */
- add r1, r0, #52
- ldmia r1, {r3, r4, r5} /* {sp, lr, pc}. */
-#if defined(__thumb2__)
- /* Thumb-2 doesn't allow sp in a load-multiple instruction, so push
- the target address onto the target stack. This is safe as
- we're always returning to somewhere further up the call stack. */
- mov ip, r3
- mov lr, r4
- str r5, [ip, #-4]!
-#elif defined(__INTERWORKING__)
- /* Restore pc into ip. */
- mov r2, r5
- stmfd sp!, {r2, r3, r4}
-#else
- stmfd sp!, {r3, r4, r5}
-#endif
- /* Don't bother restoring ip. */
- ldmia r0, {r0, r1, r2, r3, r4, r5, r6, r7, r8, r9, sl, fp}
-#if defined(__thumb2__)
- /* Pop the return address off the target stack. */
- mov sp, ip
- pop {pc}
-#elif defined(__INTERWORKING__)
- /* Pop the three registers we pushed earlier. */
- ldmfd sp, {ip, sp, lr}
- bx ip
-#else
- ldmfd sp, {sp, lr, pc}
-#endif
- FUNC_END restore_core_regs
- UNPREFIX restore_core_regs
-
-/* Load VFP registers d0-d15 from the address in r0.
- Use this to load from FSTMX format. */
-ARM_FUNC_START gnu_Unwind_Restore_VFP
- /* Use the generic coprocessor form so that gas doesn't complain
- on soft-float targets. */
- ldc p11,cr0,[r0],{0x21} /* fldmiax r0, {d0-d15} */
- RET
-
-/* Store VFP registers d0-d15 to the address in r0.
- Use this to store in FSTMX format. */
-ARM_FUNC_START gnu_Unwind_Save_VFP
- /* Use the generic coprocessor form so that gas doesn't complain
- on soft-float targets. */
- stc p11,cr0,[r0],{0x21} /* fstmiax r0, {d0-d15} */
- RET
-
-/* Load VFP registers d0-d15 from the address in r0.
- Use this to load from FSTMD format. */
-ARM_FUNC_START gnu_Unwind_Restore_VFP_D
- ldc p11,cr0,[r0],{0x20} /* fldmiad r0, {d0-d15} */
- RET
-
-/* Store VFP registers d0-d15 to the address in r0.
- Use this to store in FLDMD format. */
-ARM_FUNC_START gnu_Unwind_Save_VFP_D
- stc p11,cr0,[r0],{0x20} /* fstmiad r0, {d0-d15} */
- RET
-
-/* Load VFP registers d16-d31 from the address in r0.
- Use this to load from FSTMD (=VSTM) format. Needs VFPv3. */
-ARM_FUNC_START gnu_Unwind_Restore_VFP_D_16_to_31
- ldcl p11,cr0,[r0],{0x20} /* vldm r0, {d16-d31} */
- RET
-
-/* Store VFP registers d16-d31 to the address in r0.
- Use this to store in FLDMD (=VLDM) format. Needs VFPv3. */
-ARM_FUNC_START gnu_Unwind_Save_VFP_D_16_to_31
- stcl p11,cr0,[r0],{0x20} /* vstm r0, {d16-d31} */
- RET
-
-ARM_FUNC_START gnu_Unwind_Restore_WMMXD
- /* Use the generic coprocessor form so that gas doesn't complain
- on non-iWMMXt targets. */
- ldcl p1, cr0, [r0], #8 /* wldrd wr0, [r0], #8 */
- ldcl p1, cr1, [r0], #8 /* wldrd wr1, [r0], #8 */
- ldcl p1, cr2, [r0], #8 /* wldrd wr2, [r0], #8 */
- ldcl p1, cr3, [r0], #8 /* wldrd wr3, [r0], #8 */
- ldcl p1, cr4, [r0], #8 /* wldrd wr4, [r0], #8 */
- ldcl p1, cr5, [r0], #8 /* wldrd wr5, [r0], #8 */
- ldcl p1, cr6, [r0], #8 /* wldrd wr6, [r0], #8 */
- ldcl p1, cr7, [r0], #8 /* wldrd wr7, [r0], #8 */
- ldcl p1, cr8, [r0], #8 /* wldrd wr8, [r0], #8 */
- ldcl p1, cr9, [r0], #8 /* wldrd wr9, [r0], #8 */
- ldcl p1, cr10, [r0], #8 /* wldrd wr10, [r0], #8 */
- ldcl p1, cr11, [r0], #8 /* wldrd wr11, [r0], #8 */
- ldcl p1, cr12, [r0], #8 /* wldrd wr12, [r0], #8 */
- ldcl p1, cr13, [r0], #8 /* wldrd wr13, [r0], #8 */
- ldcl p1, cr14, [r0], #8 /* wldrd wr14, [r0], #8 */
- ldcl p1, cr15, [r0], #8 /* wldrd wr15, [r0], #8 */
- RET
-
-ARM_FUNC_START gnu_Unwind_Save_WMMXD
- /* Use the generic coprocessor form so that gas doesn't complain
- on non-iWMMXt targets. */
- stcl p1, cr0, [r0], #8 /* wstrd wr0, [r0], #8 */
- stcl p1, cr1, [r0], #8 /* wstrd wr1, [r0], #8 */
- stcl p1, cr2, [r0], #8 /* wstrd wr2, [r0], #8 */
- stcl p1, cr3, [r0], #8 /* wstrd wr3, [r0], #8 */
- stcl p1, cr4, [r0], #8 /* wstrd wr4, [r0], #8 */
- stcl p1, cr5, [r0], #8 /* wstrd wr5, [r0], #8 */
- stcl p1, cr6, [r0], #8 /* wstrd wr6, [r0], #8 */
- stcl p1, cr7, [r0], #8 /* wstrd wr7, [r0], #8 */
- stcl p1, cr8, [r0], #8 /* wstrd wr8, [r0], #8 */
- stcl p1, cr9, [r0], #8 /* wstrd wr9, [r0], #8 */
- stcl p1, cr10, [r0], #8 /* wstrd wr10, [r0], #8 */
- stcl p1, cr11, [r0], #8 /* wstrd wr11, [r0], #8 */
- stcl p1, cr12, [r0], #8 /* wstrd wr12, [r0], #8 */
- stcl p1, cr13, [r0], #8 /* wstrd wr13, [r0], #8 */
- stcl p1, cr14, [r0], #8 /* wstrd wr14, [r0], #8 */
- stcl p1, cr15, [r0], #8 /* wstrd wr15, [r0], #8 */
- RET
-
-ARM_FUNC_START gnu_Unwind_Restore_WMMXC
- /* Use the generic coprocessor form so that gas doesn't complain
- on non-iWMMXt targets. */
- ldc2 p1, cr8, [r0], #4 /* wldrw wcgr0, [r0], #4 */
- ldc2 p1, cr9, [r0], #4 /* wldrw wcgr1, [r0], #4 */
- ldc2 p1, cr10, [r0], #4 /* wldrw wcgr2, [r0], #4 */
- ldc2 p1, cr11, [r0], #4 /* wldrw wcgr3, [r0], #4 */
- RET
-
-ARM_FUNC_START gnu_Unwind_Save_WMMXC
- /* Use the generic coprocessor form so that gas doesn't complain
- on non-iWMMXt targets. */
- stc2 p1, cr8, [r0], #4 /* wstrw wcgr0, [r0], #4 */
- stc2 p1, cr9, [r0], #4 /* wstrw wcgr1, [r0], #4 */
- stc2 p1, cr10, [r0], #4 /* wstrw wcgr2, [r0], #4 */
- stc2 p1, cr11, [r0], #4 /* wstrw wcgr3, [r0], #4 */
- RET
-
-/* Wrappers to save core registers, then call the real routine. */
-
-.macro UNWIND_WRAPPER name nargs
- ARM_FUNC_START \name
- /* Create a phase2_vrs structure. */
- /* Split reg push in two to ensure the correct value for sp. */
-#if defined(__thumb2__)
- mov ip, sp
- push {lr} /* PC is ignored. */
- push {ip, lr} /* Push original SP and LR. */
-#else
- stmfd sp!, {sp, lr, pc}
-#endif
- stmfd sp!, {r0, r1, r2, r3, r4, r5, r6, r7, r8, r9, sl, fp, ip}
-
- /* Demand-save flags, plus an extra word for alignment. */
- mov r3, #0
- stmfd sp!, {r2, r3}
-
- /* Point r1 at the block. Pass r[0..nargs) unchanged. */
- add r\nargs, sp, #4
-#if defined(__thumb__) && !defined(__thumb2__)
- /* Switch back to thumb mode to avoid interworking hassle. */
- adr ip, .L1_\name
- orr ip, ip, #1
- bx ip
- .thumb
-.L1_\name:
- bl SYM (__gnu\name) __PLT__
- ldr r3, [sp, #64]
- add sp, #72
- bx r3
-#else
- bl SYM (__gnu\name) __PLT__
- ldr lr, [sp, #64]
- add sp, sp, #72
- RET
-#endif
- FUNC_END \name
- UNPREFIX \name
-.endm
-
-#endif /* !__ARM_ARCH_6M__ */
-
-UNWIND_WRAPPER _Unwind_RaiseException 1
-UNWIND_WRAPPER _Unwind_Resume 1
-UNWIND_WRAPPER _Unwind_Resume_or_Rethrow 1
-UNWIND_WRAPPER _Unwind_ForcedUnwind 3
-UNWIND_WRAPPER _Unwind_Backtrace 2
-
-#endif /* ndef __symbian__ */
diff --git a/gcc/config/arm/pr-support.c b/gcc/config/arm/pr-support.c
deleted file mode 100644
index deee661..0000000
--- a/gcc/config/arm/pr-support.c
+++ /dev/null
@@ -1,401 +0,0 @@
-/* ARM EABI compliant unwinding routines
- Copyright (C) 2004, 2005, 2009 Free Software Foundation, Inc.
- Contributed by Paul Brook
-
- This file is free software; you can redistribute it and/or modify it
- under the terms of the GNU General Public License as published by the
- Free Software Foundation; either version 3, or (at your option) any
- later version.
-
- This file 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
- General Public License for more details.
-
- Under Section 7 of GPL version 3, you are granted additional
- permissions described in the GCC Runtime Library Exception, version
- 3.1, as published by the Free Software Foundation.
-
- You should have received a copy of the GNU General Public License and
- a copy of the GCC Runtime Library Exception along with this program;
- see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
- <http://www.gnu.org/licenses/>. */
-
-#include "unwind.h"
-
-/* We add a prototype for abort here to avoid creating a dependency on
- target headers. */
-extern void abort (void);
-
-typedef struct _ZSt9type_info type_info; /* This names C++ type_info type */
-
-/* Misc constants. */
-#define R_IP 12
-#define R_SP 13
-#define R_LR 14
-#define R_PC 15
-
-#define uint32_highbit (((_uw) 1) << 31)
-
-void __attribute__((weak)) __cxa_call_unexpected(_Unwind_Control_Block *ucbp);
-
-/* Unwind descriptors. */
-
-typedef struct
-{
- _uw16 length;
- _uw16 offset;
-} EHT16;
-
-typedef struct
-{
- _uw length;
- _uw offset;
-} EHT32;
-
-/* Calculate the address encoded by a 31-bit self-relative offset at address
- P. Copy of routine in unwind-arm.c. */
-
-static inline _uw
-selfrel_offset31 (const _uw *p)
-{
- _uw offset;
-
- offset = *p;
- /* Sign extend to 32 bits. */
- if (offset & (1 << 30))
- offset |= 1u << 31;
-
- return offset + (_uw) p;
-}
-
-
-/* Personality routine helper functions. */
-
-#define CODE_FINISH (0xb0)
-
-/* Return the next byte of unwinding information, or CODE_FINISH if there is
- no data remaining. */
-static inline _uw8
-next_unwind_byte (__gnu_unwind_state * uws)
-{
- _uw8 b;
-
- if (uws->bytes_left == 0)
- {
- /* Load another word */
- if (uws->words_left == 0)
- return CODE_FINISH; /* Nothing left. */
- uws->words_left--;
- uws->data = *(uws->next++);
- uws->bytes_left = 3;
- }
- else
- uws->bytes_left--;
-
- /* Extract the most significant byte. */
- b = (uws->data >> 24) & 0xff;
- uws->data <<= 8;
- return b;
-}
-
-/* Execute the unwinding instructions described by UWS. */
-_Unwind_Reason_Code
-__gnu_unwind_execute (_Unwind_Context * context, __gnu_unwind_state * uws)
-{
- _uw op;
- int set_pc;
- _uw reg;
-
- set_pc = 0;
- for (;;)
- {
- op = next_unwind_byte (uws);
- if (op == CODE_FINISH)
- {
- /* If we haven't already set pc then copy it from lr. */
- if (!set_pc)
- {
- _Unwind_VRS_Get (context, _UVRSC_CORE, R_LR, _UVRSD_UINT32,
- &reg);
- _Unwind_VRS_Set (context, _UVRSC_CORE, R_PC, _UVRSD_UINT32,
- &reg);
- set_pc = 1;
- }
- /* Drop out of the loop. */
- break;
- }
- if ((op & 0x80) == 0)
- {
- /* vsp = vsp +- (imm6 << 2 + 4). */
- _uw offset;
-
- offset = ((op & 0x3f) << 2) + 4;
- _Unwind_VRS_Get (context, _UVRSC_CORE, R_SP, _UVRSD_UINT32, &reg);
- if (op & 0x40)
- reg -= offset;
- else
- reg += offset;
- _Unwind_VRS_Set (context, _UVRSC_CORE, R_SP, _UVRSD_UINT32, &reg);
- continue;
- }
-
- if ((op & 0xf0) == 0x80)
- {
- op = (op << 8) | next_unwind_byte (uws);
- if (op == 0x8000)
- {
- /* Refuse to unwind. */
- return _URC_FAILURE;
- }
- /* Pop r4-r15 under mask. */
- op = (op << 4) & 0xfff0;
- if (_Unwind_VRS_Pop (context, _UVRSC_CORE, op, _UVRSD_UINT32)
- != _UVRSR_OK)
- return _URC_FAILURE;
- if (op & (1 << R_PC))
- set_pc = 1;
- continue;
- }
- if ((op & 0xf0) == 0x90)
- {
- op &= 0xf;
- if (op == 13 || op == 15)
- /* Reserved. */
- return _URC_FAILURE;
- /* vsp = r[nnnn]. */
- _Unwind_VRS_Get (context, _UVRSC_CORE, op, _UVRSD_UINT32, &reg);
- _Unwind_VRS_Set (context, _UVRSC_CORE, R_SP, _UVRSD_UINT32, &reg);
- continue;
- }
- if ((op & 0xf0) == 0xa0)
- {
- /* Pop r4-r[4+nnn], [lr]. */
- _uw mask;
-
- mask = (0xff0 >> (7 - (op & 7))) & 0xff0;
- if (op & 8)
- mask |= (1 << R_LR);
- if (_Unwind_VRS_Pop (context, _UVRSC_CORE, mask, _UVRSD_UINT32)
- != _UVRSR_OK)
- return _URC_FAILURE;
- continue;
- }
- if ((op & 0xf0) == 0xb0)
- {
- /* op == 0xb0 already handled. */
- if (op == 0xb1)
- {
- op = next_unwind_byte (uws);
- if (op == 0 || ((op & 0xf0) != 0))
- /* Spare. */
- return _URC_FAILURE;
- /* Pop r0-r4 under mask. */
- if (_Unwind_VRS_Pop (context, _UVRSC_CORE, op, _UVRSD_UINT32)
- != _UVRSR_OK)
- return _URC_FAILURE;
- continue;
- }
- if (op == 0xb2)
- {
- /* vsp = vsp + 0x204 + (uleb128 << 2). */
- int shift;
-
- _Unwind_VRS_Get (context, _UVRSC_CORE, R_SP, _UVRSD_UINT32,
- &reg);
- op = next_unwind_byte (uws);
- shift = 2;
- while (op & 0x80)
- {
- reg += ((op & 0x7f) << shift);
- shift += 7;
- op = next_unwind_byte (uws);
- }
- reg += ((op & 0x7f) << shift) + 0x204;
- _Unwind_VRS_Set (context, _UVRSC_CORE, R_SP, _UVRSD_UINT32,
- &reg);
- continue;
- }
- if (op == 0xb3)
- {
- /* Pop VFP registers with fldmx. */
- op = next_unwind_byte (uws);
- op = ((op & 0xf0) << 12) | ((op & 0xf) + 1);
- if (_Unwind_VRS_Pop (context, _UVRSC_VFP, op, _UVRSD_VFPX)
- != _UVRSR_OK)
- return _URC_FAILURE;
- continue;
- }
- if ((op & 0xfc) == 0xb4)
- {
- /* Pop FPA E[4]-E[4+nn]. */
- op = 0x40000 | ((op & 3) + 1);
- if (_Unwind_VRS_Pop (context, _UVRSC_FPA, op, _UVRSD_FPAX)
- != _UVRSR_OK)
- return _URC_FAILURE;
- continue;
- }
- /* op & 0xf8 == 0xb8. */
- /* Pop VFP D[8]-D[8+nnn] with fldmx. */
- op = 0x80000 | ((op & 7) + 1);
- if (_Unwind_VRS_Pop (context, _UVRSC_VFP, op, _UVRSD_VFPX)
- != _UVRSR_OK)
- return _URC_FAILURE;
- continue;
- }
- if ((op & 0xf0) == 0xc0)
- {
- if (op == 0xc6)
- {
- /* Pop iWMMXt D registers. */
- op = next_unwind_byte (uws);
- op = ((op & 0xf0) << 12) | ((op & 0xf) + 1);
- if (_Unwind_VRS_Pop (context, _UVRSC_WMMXD, op, _UVRSD_UINT64)
- != _UVRSR_OK)
- return _URC_FAILURE;
- continue;
- }
- if (op == 0xc7)
- {
- op = next_unwind_byte (uws);
- if (op == 0 || (op & 0xf0) != 0)
- /* Spare. */
- return _URC_FAILURE;
- /* Pop iWMMXt wCGR{3,2,1,0} under mask. */
- if (_Unwind_VRS_Pop (context, _UVRSC_WMMXC, op, _UVRSD_UINT32)
- != _UVRSR_OK)
- return _URC_FAILURE;
- continue;
- }
- if ((op & 0xf8) == 0xc0)
- {
- /* Pop iWMMXt wR[10]-wR[10+nnn]. */
- op = 0xa0000 | ((op & 0xf) + 1);
- if (_Unwind_VRS_Pop (context, _UVRSC_WMMXD, op, _UVRSD_UINT64)
- != _UVRSR_OK)
- return _URC_FAILURE;
- continue;
- }
- if (op == 0xc8)
- {
-#ifndef __VFP_FP__
- /* Pop FPA registers. */
- op = next_unwind_byte (uws);
- op = ((op & 0xf0) << 12) | ((op & 0xf) + 1);
- if (_Unwind_VRS_Pop (context, _UVRSC_FPA, op, _UVRSD_FPAX)
- != _UVRSR_OK)
- return _URC_FAILURE;
- continue;
-#else
- /* Pop VFPv3 registers D[16+ssss]-D[16+ssss+cccc] with vldm. */
- op = next_unwind_byte (uws);
- op = (((op & 0xf0) + 16) << 12) | ((op & 0xf) + 1);
- if (_Unwind_VRS_Pop (context, _UVRSC_VFP, op, _UVRSD_DOUBLE)
- != _UVRSR_OK)
- return _URC_FAILURE;
- continue;
-#endif
- }
- if (op == 0xc9)
- {
- /* Pop VFP registers with fldmd. */
- op = next_unwind_byte (uws);
- op = ((op & 0xf0) << 12) | ((op & 0xf) + 1);
- if (_Unwind_VRS_Pop (context, _UVRSC_VFP, op, _UVRSD_DOUBLE)
- != _UVRSR_OK)
- return _URC_FAILURE;
- continue;
- }
- /* Spare. */
- return _URC_FAILURE;
- }
- if ((op & 0xf8) == 0xd0)
- {
- /* Pop VFP D[8]-D[8+nnn] with fldmd. */
- op = 0x80000 | ((op & 7) + 1);
- if (_Unwind_VRS_Pop (context, _UVRSC_VFP, op, _UVRSD_DOUBLE)
- != _UVRSR_OK)
- return _URC_FAILURE;
- continue;
- }
- /* Spare. */
- return _URC_FAILURE;
- }
- return _URC_OK;
-}
-
-
-/* Execute the unwinding instructions associated with a frame. UCBP and
- CONTEXT are the current exception object and virtual CPU state
- respectively. */
-
-_Unwind_Reason_Code
-__gnu_unwind_frame (_Unwind_Control_Block * ucbp, _Unwind_Context * context)
-{
- _uw *ptr;
- __gnu_unwind_state uws;
-
- ptr = (_uw *) ucbp->pr_cache.ehtp;
- /* Skip over the personality routine address. */
- ptr++;
- /* Setup the unwinder state. */
- uws.data = (*ptr) << 8;
- uws.next = ptr + 1;
- uws.bytes_left = 3;
- uws.words_left = ((*ptr) >> 24) & 0xff;
-
- return __gnu_unwind_execute (context, &uws);
-}
-
-/* Get the _Unwind_Control_Block from an _Unwind_Context. */
-
-static inline _Unwind_Control_Block *
-unwind_UCB_from_context (_Unwind_Context * context)
-{
- return (_Unwind_Control_Block *) _Unwind_GetGR (context, R_IP);
-}
-
-/* Get the start address of the function being unwound. */
-
-_Unwind_Ptr
-_Unwind_GetRegionStart (_Unwind_Context * context)
-{
- _Unwind_Control_Block *ucbp;
-
- ucbp = unwind_UCB_from_context (context);
- return (_Unwind_Ptr) ucbp->pr_cache.fnstart;
-}
-
-/* Find the Language specific exception data. */
-
-void *
-_Unwind_GetLanguageSpecificData (_Unwind_Context * context)
-{
- _Unwind_Control_Block *ucbp;
- _uw *ptr;
-
- /* Get a pointer to the exception table entry. */
- ucbp = unwind_UCB_from_context (context);
- ptr = (_uw *) ucbp->pr_cache.ehtp;
- /* Skip the personality routine address. */
- ptr++;
- /* Skip the unwind opcodes. */
- ptr += (((*ptr) >> 24) & 0xff) + 1;
-
- return ptr;
-}
-
-
-/* These two should never be used. */
-
-_Unwind_Ptr
-_Unwind_GetDataRelBase (_Unwind_Context *context __attribute__ ((unused)))
-{
- abort ();
-}
-
-_Unwind_Ptr
-_Unwind_GetTextRelBase (_Unwind_Context *context __attribute__ ((unused)))
-{
- abort ();
-}
diff --git a/gcc/config/arm/t-bpabi b/gcc/config/arm/t-bpabi
index 78812b3..b6b5f40 100644
--- a/gcc/config/arm/t-bpabi
+++ b/gcc/config/arm/t-bpabi
@@ -25,11 +25,6 @@ LIB2FUNCS_EXTRA = $(srcdir)/config/arm/bpabi.c \
LIB2FUNCS_STATIC_EXTRA = $(srcdir)/config/arm/fp16.c
-UNWIND_H = $(srcdir)/config/arm/unwind-arm.h
-LIB2ADDEH = $(srcdir)/config/arm/unwind-arm.c \
- $(srcdir)/config/arm/libunwind.S \
- $(srcdir)/config/arm/pr-support.c $(srcdir)/unwind-c.c
-
# Add the BPABI names.
SHLIB_MAPFILES += $(srcdir)/config/arm/libgcc-bpabi.ver
diff --git a/gcc/config/arm/t-symbian b/gcc/config/arm/t-symbian
index 3be83f4..f074591 100644
--- a/gcc/config/arm/t-symbian
+++ b/gcc/config/arm/t-symbian
@@ -30,10 +30,6 @@ LIB1ASMFUNCS += \
_truncdfsf2 _negsf2 _addsubsf3 _muldivsf3 _cmpsf2 _unordsf2 \
_fixsfsi _fixunssfsi
-# Include the gcc personality routine
-UNWIND_H = $(srcdir)/config/arm/unwind-arm.h
-LIB2ADDEH = $(srcdir)/unwind-c.c $(srcdir)/config/arm/pr-support.c
-
# Include half-float helpers.
LIB2FUNCS_STATIC_EXTRA = $(srcdir)/config/arm/fp16.c
diff --git a/gcc/config/arm/unwind-arm.c b/gcc/config/arm/unwind-arm.c
deleted file mode 100644
index 90d258d..0000000
--- a/gcc/config/arm/unwind-arm.c
+++ /dev/null
@@ -1,1283 +0,0 @@
-/* ARM EABI compliant unwinding routines.
- Copyright (C) 2004, 2005, 2009 Free Software Foundation, Inc.
- Contributed by Paul Brook
-
- This file is free software; you can redistribute it and/or modify it
- under the terms of the GNU General Public License as published by the
- Free Software Foundation; either version 3, or (at your option) any
- later version.
-
- This file 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
- General Public License for more details.
-
- Under Section 7 of GPL version 3, you are granted additional
- permissions described in the GCC Runtime Library Exception, version
- 3.1, as published by the Free Software Foundation.
-
- You should have received a copy of the GNU General Public License and
- a copy of the GCC Runtime Library Exception along with this program;
- see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
- <http://www.gnu.org/licenses/>. */
-
-#include "unwind.h"
-
-/* We add a prototype for abort here to avoid creating a dependency on
- target headers. */
-extern void abort (void);
-
-/* Definitions for C++ runtime support routines. We make these weak
- declarations to avoid pulling in libsupc++ unnecessarily. */
-typedef unsigned char bool;
-
-typedef struct _ZSt9type_info type_info; /* This names C++ type_info type */
-enum __cxa_type_match_result
- {
- ctm_failed = 0,
- ctm_succeeded = 1,
- ctm_succeeded_with_ptr_to_base = 2
- };
-
-void __attribute__((weak)) __cxa_call_unexpected(_Unwind_Control_Block *ucbp);
-bool __attribute__((weak)) __cxa_begin_cleanup(_Unwind_Control_Block *ucbp);
-enum __cxa_type_match_result __attribute__((weak)) __cxa_type_match
- (_Unwind_Control_Block *ucbp, const type_info *rttip,
- bool is_reference, void **matched_object);
-
-_Unwind_Ptr __attribute__((weak))
-__gnu_Unwind_Find_exidx (_Unwind_Ptr, int *);
-
-/* Misc constants. */
-#define R_IP 12
-#define R_SP 13
-#define R_LR 14
-#define R_PC 15
-
-#define EXIDX_CANTUNWIND 1
-#define uint32_highbit (((_uw) 1) << 31)
-
-#define UCB_FORCED_STOP_FN(ucbp) ((ucbp)->unwinder_cache.reserved1)
-#define UCB_PR_ADDR(ucbp) ((ucbp)->unwinder_cache.reserved2)
-#define UCB_SAVED_CALLSITE_ADDR(ucbp) ((ucbp)->unwinder_cache.reserved3)
-#define UCB_FORCED_STOP_ARG(ucbp) ((ucbp)->unwinder_cache.reserved4)
-
-struct core_regs
-{
- _uw r[16];
-};
-
-/* We use normal integer types here to avoid the compiler generating
- coprocessor instructions. */
-struct vfp_regs
-{
- _uw64 d[16];
- _uw pad;
-};
-
-struct vfpv3_regs
-{
- /* Always populated via VSTM, so no need for the "pad" field from
- vfp_regs (which is used to store the format word for FSTMX). */
- _uw64 d[16];
-};
-
-struct fpa_reg
-{
- _uw w[3];
-};
-
-struct fpa_regs
-{
- struct fpa_reg f[8];
-};
-
-struct wmmxd_regs
-{
- _uw64 wd[16];
-};
-
-struct wmmxc_regs
-{
- _uw wc[4];
-};
-
-/* Unwind descriptors. */
-
-typedef struct
-{
- _uw16 length;
- _uw16 offset;
-} EHT16;
-
-typedef struct
-{
- _uw length;
- _uw offset;
-} EHT32;
-
-/* The ABI specifies that the unwind routines may only use core registers,
- except when actually manipulating coprocessor state. This allows
- us to write one implementation that works on all platforms by
- demand-saving coprocessor registers.
-
- During unwinding we hold the coprocessor state in the actual hardware
- registers and allocate demand-save areas for use during phase1
- unwinding. */
-
-typedef struct
-{
- /* The first fields must be the same as a phase2_vrs. */
- _uw demand_save_flags;
- struct core_regs core;
- _uw prev_sp; /* Only valid during forced unwinding. */
- struct vfp_regs vfp;
- struct vfpv3_regs vfp_regs_16_to_31;
- struct fpa_regs fpa;
- struct wmmxd_regs wmmxd;
- struct wmmxc_regs wmmxc;
-} phase1_vrs;
-
-#define DEMAND_SAVE_VFP 1 /* VFP state has been saved if not set */
-#define DEMAND_SAVE_VFP_D 2 /* VFP state is for FLDMD/FSTMD if set */
-#define DEMAND_SAVE_VFP_V3 4 /* VFPv3 state for regs 16 .. 31 has
- been saved if not set */
-#define DEMAND_SAVE_WMMXD 8 /* iWMMXt data registers have been
- saved if not set. */
-#define DEMAND_SAVE_WMMXC 16 /* iWMMXt control registers have been
- saved if not set. */
-
-/* This must match the structure created by the assembly wrappers. */
-typedef struct
-{
- _uw demand_save_flags;
- struct core_regs core;
-} phase2_vrs;
-
-
-/* An exception index table entry. */
-
-typedef struct __EIT_entry
-{
- _uw fnoffset;
- _uw content;
-} __EIT_entry;
-
-/* Assembly helper functions. */
-
-/* Restore core register state. Never returns. */
-void __attribute__((noreturn)) restore_core_regs (struct core_regs *);
-
-
-/* Coprocessor register state manipulation functions. */
-
-/* Routines for FLDMX/FSTMX format... */
-void __gnu_Unwind_Save_VFP (struct vfp_regs * p);
-void __gnu_Unwind_Restore_VFP (struct vfp_regs * p);
-void __gnu_Unwind_Save_WMMXD (struct wmmxd_regs * p);
-void __gnu_Unwind_Restore_WMMXD (struct wmmxd_regs * p);
-void __gnu_Unwind_Save_WMMXC (struct wmmxc_regs * p);
-void __gnu_Unwind_Restore_WMMXC (struct wmmxc_regs * p);
-
-/* ...and those for FLDMD/FSTMD format... */
-void __gnu_Unwind_Save_VFP_D (struct vfp_regs * p);
-void __gnu_Unwind_Restore_VFP_D (struct vfp_regs * p);
-
-/* ...and those for VLDM/VSTM format, saving/restoring only registers
- 16 through 31. */
-void __gnu_Unwind_Save_VFP_D_16_to_31 (struct vfpv3_regs * p);
-void __gnu_Unwind_Restore_VFP_D_16_to_31 (struct vfpv3_regs * p);
-
-/* Restore coprocessor state after phase1 unwinding. */
-static void
-restore_non_core_regs (phase1_vrs * vrs)
-{
- if ((vrs->demand_save_flags & DEMAND_SAVE_VFP) == 0)
- {
- if (vrs->demand_save_flags & DEMAND_SAVE_VFP_D)
- __gnu_Unwind_Restore_VFP_D (&vrs->vfp);
- else
- __gnu_Unwind_Restore_VFP (&vrs->vfp);
- }
-
- if ((vrs->demand_save_flags & DEMAND_SAVE_VFP_V3) == 0)
- __gnu_Unwind_Restore_VFP_D_16_to_31 (&vrs->vfp_regs_16_to_31);
-
- if ((vrs->demand_save_flags & DEMAND_SAVE_WMMXD) == 0)
- __gnu_Unwind_Restore_WMMXD (&vrs->wmmxd);
- if ((vrs->demand_save_flags & DEMAND_SAVE_WMMXC) == 0)
- __gnu_Unwind_Restore_WMMXC (&vrs->wmmxc);
-}
-
-/* A better way to do this would probably be to compare the absolute address
- with a segment relative relocation of the same symbol. */
-
-extern int __text_start;
-extern int __data_start;
-
-/* The exception index table location. */
-extern __EIT_entry __exidx_start;
-extern __EIT_entry __exidx_end;
-
-/* ABI defined personality routines. */
-extern _Unwind_Reason_Code __aeabi_unwind_cpp_pr0 (_Unwind_State,
- _Unwind_Control_Block *, _Unwind_Context *);// __attribute__((weak));
-extern _Unwind_Reason_Code __aeabi_unwind_cpp_pr1 (_Unwind_State,
- _Unwind_Control_Block *, _Unwind_Context *) __attribute__((weak));
-extern _Unwind_Reason_Code __aeabi_unwind_cpp_pr2 (_Unwind_State,
- _Unwind_Control_Block *, _Unwind_Context *) __attribute__((weak));
-
-/* ABI defined routine to store a virtual register to memory. */
-
-_Unwind_VRS_Result _Unwind_VRS_Get (_Unwind_Context *context,
- _Unwind_VRS_RegClass regclass,
- _uw regno,
- _Unwind_VRS_DataRepresentation representation,
- void *valuep)
-{
- phase1_vrs *vrs = (phase1_vrs *) context;
-
- switch (regclass)
- {
- case _UVRSC_CORE:
- if (representation != _UVRSD_UINT32
- || regno > 15)
- return _UVRSR_FAILED;
- *(_uw *) valuep = vrs->core.r[regno];
- return _UVRSR_OK;
-
- case _UVRSC_VFP:
- case _UVRSC_FPA:
- case _UVRSC_WMMXD:
- case _UVRSC_WMMXC:
- return _UVRSR_NOT_IMPLEMENTED;
-
- default:
- return _UVRSR_FAILED;
- }
-}
-
-
-/* ABI defined function to load a virtual register from memory. */
-
-_Unwind_VRS_Result _Unwind_VRS_Set (_Unwind_Context *context,
- _Unwind_VRS_RegClass regclass,
- _uw regno,
- _Unwind_VRS_DataRepresentation representation,
- void *valuep)
-{
- phase1_vrs *vrs = (phase1_vrs *) context;
-
- switch (regclass)
- {
- case _UVRSC_CORE:
- if (representation != _UVRSD_UINT32
- || regno > 15)
- return _UVRSR_FAILED;
-
- vrs->core.r[regno] = *(_uw *) valuep;
- return _UVRSR_OK;
-
- case _UVRSC_VFP:
- case _UVRSC_FPA:
- case _UVRSC_WMMXD:
- case _UVRSC_WMMXC:
- return _UVRSR_NOT_IMPLEMENTED;
-
- default:
- return _UVRSR_FAILED;
- }
-}
-
-
-/* ABI defined function to pop registers off the stack. */
-
-_Unwind_VRS_Result _Unwind_VRS_Pop (_Unwind_Context *context,
- _Unwind_VRS_RegClass regclass,
- _uw discriminator,
- _Unwind_VRS_DataRepresentation representation)
-{
- phase1_vrs *vrs = (phase1_vrs *) context;
-
- switch (regclass)
- {
- case _UVRSC_CORE:
- {
- _uw *ptr;
- _uw mask;
- int i;
-
- if (representation != _UVRSD_UINT32)
- return _UVRSR_FAILED;
-
- mask = discriminator & 0xffff;
- ptr = (_uw *) vrs->core.r[R_SP];
- /* Pop the requested registers. */
- for (i = 0; i < 16; i++)
- {
- if (mask & (1 << i))
- vrs->core.r[i] = *(ptr++);
- }
- /* Writeback the stack pointer value if it wasn't restored. */
- if ((mask & (1 << R_SP)) == 0)
- vrs->core.r[R_SP] = (_uw) ptr;
- }
- return _UVRSR_OK;
-
- case _UVRSC_VFP:
- {
- _uw start = discriminator >> 16;
- _uw count = discriminator & 0xffff;
- struct vfp_regs tmp;
- struct vfpv3_regs tmp_16_to_31;
- int tmp_count;
- _uw *sp;
- _uw *dest;
- int num_vfpv3_regs = 0;
-
- /* We use an approximation here by bounding _UVRSD_DOUBLE
- register numbers at 32 always, since we can't detect if
- VFPv3 isn't present (in such a case the upper limit is 16). */
- if ((representation != _UVRSD_VFPX && representation != _UVRSD_DOUBLE)
- || start + count > (representation == _UVRSD_VFPX ? 16 : 32)
- || (representation == _UVRSD_VFPX && start >= 16))
- return _UVRSR_FAILED;
-
- /* Check if we're being asked to pop VFPv3-only registers
- (numbers 16 through 31). */
- if (start >= 16)
- num_vfpv3_regs = count;
- else if (start + count > 16)
- num_vfpv3_regs = start + count - 16;
-
- if (num_vfpv3_regs && representation != _UVRSD_DOUBLE)
- return _UVRSR_FAILED;
-
- /* Demand-save coprocessor registers for stage1. */
- if (start < 16 && (vrs->demand_save_flags & DEMAND_SAVE_VFP))
- {
- vrs->demand_save_flags &= ~DEMAND_SAVE_VFP;
-
- if (representation == _UVRSD_DOUBLE)
- {
- /* Save in FLDMD/FSTMD format. */
- vrs->demand_save_flags |= DEMAND_SAVE_VFP_D;
- __gnu_Unwind_Save_VFP_D (&vrs->vfp);
- }
- else
- {
- /* Save in FLDMX/FSTMX format. */
- vrs->demand_save_flags &= ~DEMAND_SAVE_VFP_D;
- __gnu_Unwind_Save_VFP (&vrs->vfp);
- }
- }
-
- if (num_vfpv3_regs > 0
- && (vrs->demand_save_flags & DEMAND_SAVE_VFP_V3))
- {
- vrs->demand_save_flags &= ~DEMAND_SAVE_VFP_V3;
- __gnu_Unwind_Save_VFP_D_16_to_31 (&vrs->vfp_regs_16_to_31);
- }
-
- /* Restore the registers from the stack. Do this by saving the
- current VFP registers to a memory area, moving the in-memory
- values into that area, and restoring from the whole area.
- For _UVRSD_VFPX we assume FSTMX standard format 1. */
- if (representation == _UVRSD_VFPX)
- __gnu_Unwind_Save_VFP (&tmp);
- else
- {
- /* Save registers 0 .. 15 if required. */
- if (start < 16)
- __gnu_Unwind_Save_VFP_D (&tmp);
-
- /* Save VFPv3 registers 16 .. 31 if required. */
- if (num_vfpv3_regs)
- __gnu_Unwind_Save_VFP_D_16_to_31 (&tmp_16_to_31);
- }
-
- /* Work out how many registers below register 16 need popping. */
- tmp_count = num_vfpv3_regs > 0 ? 16 - start : count;
-
- /* Copy registers below 16, if needed.
- The stack address is only guaranteed to be word aligned, so
- we can't use doubleword copies. */
- sp = (_uw *) vrs->core.r[R_SP];
- if (tmp_count > 0)
- {
- tmp_count *= 2;
- dest = (_uw *) &tmp.d[start];
- while (tmp_count--)
- *(dest++) = *(sp++);
- }
-
- /* Copy VFPv3 registers numbered >= 16, if needed. */
- if (num_vfpv3_regs > 0)
- {
- /* num_vfpv3_regs is needed below, so copy it. */
- int tmp_count_2 = num_vfpv3_regs * 2;
- int vfpv3_start = start < 16 ? 16 : start;
-
- dest = (_uw *) &tmp_16_to_31.d[vfpv3_start - 16];
- while (tmp_count_2--)
- *(dest++) = *(sp++);
- }
-
- /* Skip the format word space if using FLDMX/FSTMX format. */
- if (representation == _UVRSD_VFPX)
- sp++;
-
- /* Set the new stack pointer. */
- vrs->core.r[R_SP] = (_uw) sp;
-
- /* Reload the registers. */
- if (representation == _UVRSD_VFPX)
- __gnu_Unwind_Restore_VFP (&tmp);
- else
- {
- /* Restore registers 0 .. 15 if required. */
- if (start < 16)
- __gnu_Unwind_Restore_VFP_D (&tmp);
-
- /* Restore VFPv3 registers 16 .. 31 if required. */
- if (num_vfpv3_regs > 0)
- __gnu_Unwind_Restore_VFP_D_16_to_31 (&tmp_16_to_31);
- }
- }
- return _UVRSR_OK;
-
- case _UVRSC_FPA:
- return _UVRSR_NOT_IMPLEMENTED;
-
- case _UVRSC_WMMXD:
- {
- _uw start = discriminator >> 16;
- _uw count = discriminator & 0xffff;
- struct wmmxd_regs tmp;
- _uw *sp;
- _uw *dest;
-
- if ((representation != _UVRSD_UINT64) || start + count > 16)
- return _UVRSR_FAILED;
-
- if (vrs->demand_save_flags & DEMAND_SAVE_WMMXD)
- {
- /* Demand-save resisters for stage1. */
- vrs->demand_save_flags &= ~DEMAND_SAVE_WMMXD;
- __gnu_Unwind_Save_WMMXD (&vrs->wmmxd);
- }
-
- /* Restore the registers from the stack. Do this by saving the
- current WMMXD registers to a memory area, moving the in-memory
- values into that area, and restoring from the whole area. */
- __gnu_Unwind_Save_WMMXD (&tmp);
-
- /* The stack address is only guaranteed to be word aligned, so
- we can't use doubleword copies. */
- sp = (_uw *) vrs->core.r[R_SP];
- dest = (_uw *) &tmp.wd[start];
- count *= 2;
- while (count--)
- *(dest++) = *(sp++);
-
- /* Set the new stack pointer. */
- vrs->core.r[R_SP] = (_uw) sp;
-
- /* Reload the registers. */
- __gnu_Unwind_Restore_WMMXD (&tmp);
- }
- return _UVRSR_OK;
-
- case _UVRSC_WMMXC:
- {
- int i;
- struct wmmxc_regs tmp;
- _uw *sp;
-
- if ((representation != _UVRSD_UINT32) || discriminator > 16)
- return _UVRSR_FAILED;
-
- if (vrs->demand_save_flags & DEMAND_SAVE_WMMXC)
- {
- /* Demand-save resisters for stage1. */
- vrs->demand_save_flags &= ~DEMAND_SAVE_WMMXC;
- __gnu_Unwind_Save_WMMXC (&vrs->wmmxc);
- }
-
- /* Restore the registers from the stack. Do this by saving the
- current WMMXC registers to a memory area, moving the in-memory
- values into that area, and restoring from the whole area. */
- __gnu_Unwind_Save_WMMXC (&tmp);
-
- sp = (_uw *) vrs->core.r[R_SP];
- for (i = 0; i < 4; i++)
- if (discriminator & (1 << i))
- tmp.wc[i] = *(sp++);
-
- /* Set the new stack pointer. */
- vrs->core.r[R_SP] = (_uw) sp;
-
- /* Reload the registers. */
- __gnu_Unwind_Restore_WMMXC (&tmp);
- }
- return _UVRSR_OK;
-
- default:
- return _UVRSR_FAILED;
- }
-}
-
-
-/* Core unwinding functions. */
-
-/* Calculate the address encoded by a 31-bit self-relative offset at address
- P. */
-static inline _uw
-selfrel_offset31 (const _uw *p)
-{
- _uw offset;
-
- offset = *p;
- /* Sign extend to 32 bits. */
- if (offset & (1 << 30))
- offset |= 1u << 31;
- else
- offset &= ~(1u << 31);
-
- return offset + (_uw) p;
-}
-
-
-/* Perform a binary search for RETURN_ADDRESS in TABLE. The table contains
- NREC entries. */
-
-static const __EIT_entry *
-search_EIT_table (const __EIT_entry * table, int nrec, _uw return_address)
-{
- _uw next_fn;
- _uw this_fn;
- int n, left, right;
-
- if (nrec == 0)
- return (__EIT_entry *) 0;
-
- left = 0;
- right = nrec - 1;
-
- while (1)
- {
- n = (left + right) / 2;
- this_fn = selfrel_offset31 (&table[n].fnoffset);
- if (n != nrec - 1)
- next_fn = selfrel_offset31 (&table[n + 1].fnoffset) - 1;
- else
- next_fn = (_uw)0 - 1;
-
- if (return_address < this_fn)
- {
- if (n == left)
- return (__EIT_entry *) 0;
- right = n - 1;
- }
- else if (return_address <= next_fn)
- return &table[n];
- else
- left = n + 1;
- }
-}
-
-/* Find the exception index table eintry for the given address.
- Fill in the relevant fields of the UCB.
- Returns _URC_FAILURE if an error occurred, _URC_OK on success. */
-
-static _Unwind_Reason_Code
-get_eit_entry (_Unwind_Control_Block *ucbp, _uw return_address)
-{
- const __EIT_entry * eitp;
- int nrec;
-
- /* The return address is the address of the instruction following the
- call instruction (plus one in thumb mode). If this was the last
- instruction in the function the address will lie in the following
- function. Subtract 2 from the address so that it points within the call
- instruction itself. */
- return_address -= 2;
-
- if (__gnu_Unwind_Find_exidx)
- {
- eitp = (const __EIT_entry *) __gnu_Unwind_Find_exidx (return_address,
- &nrec);
- if (!eitp)
- {
- UCB_PR_ADDR (ucbp) = 0;
- return _URC_FAILURE;
- }
- }
- else
- {
- eitp = &__exidx_start;
- nrec = &__exidx_end - &__exidx_start;
- }
-
- eitp = search_EIT_table (eitp, nrec, return_address);
-
- if (!eitp)
- {
- UCB_PR_ADDR (ucbp) = 0;
- return _URC_FAILURE;
- }
- ucbp->pr_cache.fnstart = selfrel_offset31 (&eitp->fnoffset);
-
- /* Can this frame be unwound at all? */
- if (eitp->content == EXIDX_CANTUNWIND)
- {
- UCB_PR_ADDR (ucbp) = 0;
- return _URC_END_OF_STACK;
- }
-
- /* Obtain the address of the "real" __EHT_Header word. */
-
- if (eitp->content & uint32_highbit)
- {
- /* It is immediate data. */
- ucbp->pr_cache.ehtp = (_Unwind_EHT_Header *)&eitp->content;
- ucbp->pr_cache.additional = 1;
- }
- else
- {
- /* The low 31 bits of the content field are a self-relative
- offset to an _Unwind_EHT_Entry structure. */
- ucbp->pr_cache.ehtp =
- (_Unwind_EHT_Header *) selfrel_offset31 (&eitp->content);
- ucbp->pr_cache.additional = 0;
- }
-
- /* Discover the personality routine address. */
- if (*ucbp->pr_cache.ehtp & (1u << 31))
- {
- /* One of the predefined standard routines. */
- _uw idx = (*(_uw *) ucbp->pr_cache.ehtp >> 24) & 0xf;
- if (idx == 0)
- UCB_PR_ADDR (ucbp) = (_uw) &__aeabi_unwind_cpp_pr0;
- else if (idx == 1)
- UCB_PR_ADDR (ucbp) = (_uw) &__aeabi_unwind_cpp_pr1;
- else if (idx == 2)
- UCB_PR_ADDR (ucbp) = (_uw) &__aeabi_unwind_cpp_pr2;
- else
- { /* Failed */
- UCB_PR_ADDR (ucbp) = 0;
- return _URC_FAILURE;
- }
- }
- else
- {
- /* Execute region offset to PR */
- UCB_PR_ADDR (ucbp) = selfrel_offset31 (ucbp->pr_cache.ehtp);
- }
- return _URC_OK;
-}
-
-
-/* Perform phase2 unwinding. VRS is the initial virtual register state. */
-
-static void __attribute__((noreturn))
-unwind_phase2 (_Unwind_Control_Block * ucbp, phase2_vrs * vrs)
-{
- _Unwind_Reason_Code pr_result;
-
- do
- {
- /* Find the entry for this routine. */
- if (get_eit_entry (ucbp, vrs->core.r[R_PC]) != _URC_OK)
- abort ();
-
- UCB_SAVED_CALLSITE_ADDR (ucbp) = vrs->core.r[R_PC];
-
- /* Call the pr to decide what to do. */
- pr_result = ((personality_routine) UCB_PR_ADDR (ucbp))
- (_US_UNWIND_FRAME_STARTING, ucbp, (_Unwind_Context *) vrs);
- }
- while (pr_result == _URC_CONTINUE_UNWIND);
-
- if (pr_result != _URC_INSTALL_CONTEXT)
- abort();
-
- restore_core_regs (&vrs->core);
-}
-
-/* Perform phase2 forced unwinding. */
-
-static _Unwind_Reason_Code
-unwind_phase2_forced (_Unwind_Control_Block *ucbp, phase2_vrs *entry_vrs,
- int resuming)
-{
- _Unwind_Stop_Fn stop_fn = (_Unwind_Stop_Fn) UCB_FORCED_STOP_FN (ucbp);
- void *stop_arg = (void *)UCB_FORCED_STOP_ARG (ucbp);
- _Unwind_Reason_Code pr_result = 0;
- /* We use phase1_vrs here even though we do not demand save, for the
- prev_sp field. */
- phase1_vrs saved_vrs, next_vrs;
-
- /* Save the core registers. */
- saved_vrs.core = entry_vrs->core;
- /* We don't need to demand-save the non-core registers, because we
- unwind in a single pass. */
- saved_vrs.demand_save_flags = 0;
-
- /* Unwind until we reach a propagation barrier. */
- do
- {
- _Unwind_State action;
- _Unwind_Reason_Code entry_code;
- _Unwind_Reason_Code stop_code;
-
- /* Find the entry for this routine. */
- entry_code = get_eit_entry (ucbp, saved_vrs.core.r[R_PC]);
-
- if (resuming)
- {
- action = _US_UNWIND_FRAME_RESUME | _US_FORCE_UNWIND;
- resuming = 0;
- }
- else
- action = _US_UNWIND_FRAME_STARTING | _US_FORCE_UNWIND;
-
- if (entry_code == _URC_OK)
- {
- UCB_SAVED_CALLSITE_ADDR (ucbp) = saved_vrs.core.r[R_PC];
-
- next_vrs = saved_vrs;
-
- /* Call the pr to decide what to do. */
- pr_result = ((personality_routine) UCB_PR_ADDR (ucbp))
- (action, ucbp, (void *) &next_vrs);
-
- saved_vrs.prev_sp = next_vrs.core.r[R_SP];
- }
- else
- {
- /* Treat any failure as the end of unwinding, to cope more
- gracefully with missing EH information. Mixed EH and
- non-EH within one object will usually result in failure,
- because the .ARM.exidx tables do not indicate the end
- of the code to which they apply; but mixed EH and non-EH
- shared objects should return an unwind failure at the
- entry of a non-EH shared object. */
- action |= _US_END_OF_STACK;
-
- saved_vrs.prev_sp = saved_vrs.core.r[R_SP];
- }
-
- stop_code = stop_fn (1, action, ucbp->exception_class, ucbp,
- (void *)&saved_vrs, stop_arg);
- if (stop_code != _URC_NO_REASON)
- return _URC_FAILURE;
-
- if (entry_code != _URC_OK)
- return entry_code;
-
- saved_vrs = next_vrs;
- }
- while (pr_result == _URC_CONTINUE_UNWIND);
-
- if (pr_result != _URC_INSTALL_CONTEXT)
- {
- /* Some sort of failure has occurred in the pr and probably the
- pr returned _URC_FAILURE. */
- return _URC_FAILURE;
- }
-
- restore_core_regs (&saved_vrs.core);
-}
-
-/* This is a very limited implementation of _Unwind_GetCFA. It returns
- the stack pointer as it is about to be unwound, and is only valid
- while calling the stop function during forced unwinding. If the
- current personality routine result is going to run a cleanup, this
- will not be the CFA; but when the frame is really unwound, it will
- be. */
-
-_Unwind_Word
-_Unwind_GetCFA (_Unwind_Context *context)
-{
- return ((phase1_vrs *) context)->prev_sp;
-}
-
-/* Perform phase1 unwinding. UCBP is the exception being thrown, and
- entry_VRS is the register state on entry to _Unwind_RaiseException. */
-
-_Unwind_Reason_Code
-__gnu_Unwind_RaiseException (_Unwind_Control_Block *, phase2_vrs *);
-
-_Unwind_Reason_Code
-__gnu_Unwind_RaiseException (_Unwind_Control_Block * ucbp,
- phase2_vrs * entry_vrs)
-{
- phase1_vrs saved_vrs;
- _Unwind_Reason_Code pr_result;
-
- /* Set the pc to the call site. */
- entry_vrs->core.r[R_PC] = entry_vrs->core.r[R_LR];
-
- /* Save the core registers. */
- saved_vrs.core = entry_vrs->core;
- /* Set demand-save flags. */
- saved_vrs.demand_save_flags = ~(_uw) 0;
-
- /* Unwind until we reach a propagation barrier. */
- do
- {
- /* Find the entry for this routine. */
- if (get_eit_entry (ucbp, saved_vrs.core.r[R_PC]) != _URC_OK)
- return _URC_FAILURE;
-
- /* Call the pr to decide what to do. */
- pr_result = ((personality_routine) UCB_PR_ADDR (ucbp))
- (_US_VIRTUAL_UNWIND_FRAME, ucbp, (void *) &saved_vrs);
- }
- while (pr_result == _URC_CONTINUE_UNWIND);
-
- /* We've unwound as far as we want to go, so restore the original
- register state. */
- restore_non_core_regs (&saved_vrs);
- if (pr_result != _URC_HANDLER_FOUND)
- {
- /* Some sort of failure has occurred in the pr and probably the
- pr returned _URC_FAILURE. */
- return _URC_FAILURE;
- }
-
- unwind_phase2 (ucbp, entry_vrs);
-}
-
-/* Resume unwinding after a cleanup has been run. UCBP is the exception
- being thrown and ENTRY_VRS is the register state on entry to
- _Unwind_Resume. */
-_Unwind_Reason_Code
-__gnu_Unwind_ForcedUnwind (_Unwind_Control_Block *,
- _Unwind_Stop_Fn, void *, phase2_vrs *);
-
-_Unwind_Reason_Code
-__gnu_Unwind_ForcedUnwind (_Unwind_Control_Block *ucbp,
- _Unwind_Stop_Fn stop_fn, void *stop_arg,
- phase2_vrs *entry_vrs)
-{
- UCB_FORCED_STOP_FN (ucbp) = (_uw) stop_fn;
- UCB_FORCED_STOP_ARG (ucbp) = (_uw) stop_arg;
-
- /* Set the pc to the call site. */
- entry_vrs->core.r[R_PC] = entry_vrs->core.r[R_LR];
-
- return unwind_phase2_forced (ucbp, entry_vrs, 0);
-}
-
-_Unwind_Reason_Code
-__gnu_Unwind_Resume (_Unwind_Control_Block *, phase2_vrs *);
-
-_Unwind_Reason_Code
-__gnu_Unwind_Resume (_Unwind_Control_Block * ucbp, phase2_vrs * entry_vrs)
-{
- _Unwind_Reason_Code pr_result;
-
- /* Recover the saved address. */
- entry_vrs->core.r[R_PC] = UCB_SAVED_CALLSITE_ADDR (ucbp);
-
- if (UCB_FORCED_STOP_FN (ucbp))
- {
- unwind_phase2_forced (ucbp, entry_vrs, 1);
-
- /* We can't return failure at this point. */
- abort ();
- }
-
- /* Call the cached PR. */
- pr_result = ((personality_routine) UCB_PR_ADDR (ucbp))
- (_US_UNWIND_FRAME_RESUME, ucbp, (_Unwind_Context *) entry_vrs);
-
- switch (pr_result)
- {
- case _URC_INSTALL_CONTEXT:
- /* Upload the registers to enter the landing pad. */
- restore_core_regs (&entry_vrs->core);
-
- case _URC_CONTINUE_UNWIND:
- /* Continue unwinding the next frame. */
- unwind_phase2 (ucbp, entry_vrs);
-
- default:
- abort ();
- }
-}
-
-_Unwind_Reason_Code
-__gnu_Unwind_Resume_or_Rethrow (_Unwind_Control_Block *, phase2_vrs *);
-
-_Unwind_Reason_Code
-__gnu_Unwind_Resume_or_Rethrow (_Unwind_Control_Block * ucbp,
- phase2_vrs * entry_vrs)
-{
- if (!UCB_FORCED_STOP_FN (ucbp))
- return __gnu_Unwind_RaiseException (ucbp, entry_vrs);
-
- /* Set the pc to the call site. */
- entry_vrs->core.r[R_PC] = entry_vrs->core.r[R_LR];
- /* Continue unwinding the next frame. */
- return unwind_phase2_forced (ucbp, entry_vrs, 0);
-}
-
-/* Clean up an exception object when unwinding is complete. */
-void
-_Unwind_Complete (_Unwind_Control_Block * ucbp __attribute__((unused)))
-{
-}
-
-
-/* Get the _Unwind_Control_Block from an _Unwind_Context. */
-
-static inline _Unwind_Control_Block *
-unwind_UCB_from_context (_Unwind_Context * context)
-{
- return (_Unwind_Control_Block *) _Unwind_GetGR (context, R_IP);
-}
-
-
-/* Free an exception. */
-
-void
-_Unwind_DeleteException (_Unwind_Exception * exc)
-{
- if (exc->exception_cleanup)
- (*exc->exception_cleanup) (_URC_FOREIGN_EXCEPTION_CAUGHT, exc);
-}
-
-
-/* Perform stack backtrace through unwind data. */
-_Unwind_Reason_Code
-__gnu_Unwind_Backtrace(_Unwind_Trace_Fn trace, void * trace_argument,
- phase2_vrs * entry_vrs);
-_Unwind_Reason_Code
-__gnu_Unwind_Backtrace(_Unwind_Trace_Fn trace, void * trace_argument,
- phase2_vrs * entry_vrs)
-{
- phase1_vrs saved_vrs;
- _Unwind_Reason_Code code;
-
- _Unwind_Control_Block ucb;
- _Unwind_Control_Block *ucbp = &ucb;
-
- /* Set the pc to the call site. */
- entry_vrs->core.r[R_PC] = entry_vrs->core.r[R_LR];
-
- /* Save the core registers. */
- saved_vrs.core = entry_vrs->core;
- /* Set demand-save flags. */
- saved_vrs.demand_save_flags = ~(_uw) 0;
-
- do
- {
- /* Find the entry for this routine. */
- if (get_eit_entry (ucbp, saved_vrs.core.r[R_PC]) != _URC_OK)
- {
- code = _URC_FAILURE;
- break;
- }
-
- /* The dwarf unwinder assumes the context structure holds things
- like the function and LSDA pointers. The ARM implementation
- caches these in the exception header (UCB). To avoid
- rewriting everything we make the virtual IP register point at
- the UCB. */
- _Unwind_SetGR((_Unwind_Context *)&saved_vrs, 12, (_Unwind_Ptr) ucbp);
-
- /* Call trace function. */
- if ((*trace) ((_Unwind_Context *) &saved_vrs, trace_argument)
- != _URC_NO_REASON)
- {
- code = _URC_FAILURE;
- break;
- }
-
- /* Call the pr to decide what to do. */
- code = ((personality_routine) UCB_PR_ADDR (ucbp))
- (_US_VIRTUAL_UNWIND_FRAME | _US_FORCE_UNWIND,
- ucbp, (void *) &saved_vrs);
- }
- while (code != _URC_END_OF_STACK
- && code != _URC_FAILURE);
-
- restore_non_core_regs (&saved_vrs);
- return code;
-}
-
-
-/* Common implementation for ARM ABI defined personality routines.
- ID is the index of the personality routine, other arguments are as defined
- by __aeabi_unwind_cpp_pr{0,1,2}. */
-
-static _Unwind_Reason_Code
-__gnu_unwind_pr_common (_Unwind_State state,
- _Unwind_Control_Block *ucbp,
- _Unwind_Context *context,
- int id)
-{
- __gnu_unwind_state uws;
- _uw *data;
- _uw offset;
- _uw len;
- _uw rtti_count;
- int phase2_call_unexpected_after_unwind = 0;
- int in_range = 0;
- int forced_unwind = state & _US_FORCE_UNWIND;
-
- state &= _US_ACTION_MASK;
-
- data = (_uw *) ucbp->pr_cache.ehtp;
- uws.data = *(data++);
- uws.next = data;
- if (id == 0)
- {
- uws.data <<= 8;
- uws.words_left = 0;
- uws.bytes_left = 3;
- }
- else
- {
- uws.words_left = (uws.data >> 16) & 0xff;
- uws.data <<= 16;
- uws.bytes_left = 2;
- data += uws.words_left;
- }
-
- /* Restore the saved pointer. */
- if (state == _US_UNWIND_FRAME_RESUME)
- data = (_uw *) ucbp->cleanup_cache.bitpattern[0];
-
- if ((ucbp->pr_cache.additional & 1) == 0)
- {
- /* Process descriptors. */
- while (*data)
- {
- _uw addr;
- _uw fnstart;
-
- if (id == 2)
- {
- len = ((EHT32 *) data)->length;
- offset = ((EHT32 *) data)->offset;
- data += 2;
- }
- else
- {
- len = ((EHT16 *) data)->length;
- offset = ((EHT16 *) data)->offset;
- data++;
- }
-
- fnstart = ucbp->pr_cache.fnstart + (offset & ~1);
- addr = _Unwind_GetGR (context, R_PC);
- in_range = (fnstart <= addr && addr < fnstart + (len & ~1));
-
- switch (((offset & 1) << 1) | (len & 1))
- {
- case 0:
- /* Cleanup. */
- if (state != _US_VIRTUAL_UNWIND_FRAME
- && in_range)
- {
- /* Cleanup in range, and we are running cleanups. */
- _uw lp;
-
- /* Landing pad address is 31-bit pc-relative offset. */
- lp = selfrel_offset31 (data);
- data++;
- /* Save the exception data pointer. */
- ucbp->cleanup_cache.bitpattern[0] = (_uw) data;
- if (!__cxa_begin_cleanup (ucbp))
- return _URC_FAILURE;
- /* Setup the VRS to enter the landing pad. */
- _Unwind_SetGR (context, R_PC, lp);
- return _URC_INSTALL_CONTEXT;
- }
- /* Cleanup not in range, or we are in stage 1. */
- data++;
- break;
-
- case 1:
- /* Catch handler. */
- if (state == _US_VIRTUAL_UNWIND_FRAME)
- {
- if (in_range)
- {
- /* Check for a barrier. */
- _uw rtti;
- bool is_reference = (data[0] & uint32_highbit) != 0;
- void *matched;
- enum __cxa_type_match_result match_type;
-
- /* Check for no-throw areas. */
- if (data[1] == (_uw) -2)
- return _URC_FAILURE;
-
- /* The thrown object immediately follows the ECB. */
- matched = (void *)(ucbp + 1);
- if (data[1] != (_uw) -1)
- {
- /* Match a catch specification. */
- rtti = _Unwind_decode_target2 ((_uw) &data[1]);
- match_type = __cxa_type_match (ucbp,
- (type_info *) rtti,
- is_reference,
- &matched);
- }
- else
- match_type = ctm_succeeded;
-
- if (match_type)
- {
- ucbp->barrier_cache.sp =
- _Unwind_GetGR (context, R_SP);
- // ctm_succeeded_with_ptr_to_base really
- // means _c_t_m indirected the pointer
- // object. We have to reconstruct the
- // additional pointer layer by using a temporary.
- if (match_type == ctm_succeeded_with_ptr_to_base)
- {
- ucbp->barrier_cache.bitpattern[2]
- = (_uw) matched;
- ucbp->barrier_cache.bitpattern[0]
- = (_uw) &ucbp->barrier_cache.bitpattern[2];
- }
- else
- ucbp->barrier_cache.bitpattern[0] = (_uw) matched;
- ucbp->barrier_cache.bitpattern[1] = (_uw) data;
- return _URC_HANDLER_FOUND;
- }
- }
- /* Handler out of range, or not matched. */
- }
- else if (ucbp->barrier_cache.sp == _Unwind_GetGR (context, R_SP)
- && ucbp->barrier_cache.bitpattern[1] == (_uw) data)
- {
- /* Matched a previous propagation barrier. */
- _uw lp;
-
- /* Setup for entry to the handler. */
- lp = selfrel_offset31 (data);
- _Unwind_SetGR (context, R_PC, lp);
- _Unwind_SetGR (context, 0, (_uw) ucbp);
- return _URC_INSTALL_CONTEXT;
- }
- /* Catch handler not matched. Advance to the next descriptor. */
- data += 2;
- break;
-
- case 2:
- rtti_count = data[0] & 0x7fffffff;
- /* Exception specification. */
- if (state == _US_VIRTUAL_UNWIND_FRAME)
- {
- if (in_range && (!forced_unwind || !rtti_count))
- {
- /* Match against the exception specification. */
- _uw i;
- _uw rtti;
- void *matched;
-
- for (i = 0; i < rtti_count; i++)
- {
- matched = (void *)(ucbp + 1);
- rtti = _Unwind_decode_target2 ((_uw) &data[i + 1]);
- if (__cxa_type_match (ucbp, (type_info *) rtti, 0,
- &matched))
- break;
- }
-
- if (i == rtti_count)
- {
- /* Exception does not match the spec. */
- ucbp->barrier_cache.sp =
- _Unwind_GetGR (context, R_SP);
- ucbp->barrier_cache.bitpattern[0] = (_uw) matched;
- ucbp->barrier_cache.bitpattern[1] = (_uw) data;
- return _URC_HANDLER_FOUND;
- }
- }
- /* Handler out of range, or exception is permitted. */
- }
- else if (ucbp->barrier_cache.sp == _Unwind_GetGR (context, R_SP)
- && ucbp->barrier_cache.bitpattern[1] == (_uw) data)
- {
- /* Matched a previous propagation barrier. */
- _uw lp;
- /* Record the RTTI list for __cxa_call_unexpected. */
- ucbp->barrier_cache.bitpattern[1] = rtti_count;
- ucbp->barrier_cache.bitpattern[2] = 0;
- ucbp->barrier_cache.bitpattern[3] = 4;
- ucbp->barrier_cache.bitpattern[4] = (_uw) &data[1];
-
- if (data[0] & uint32_highbit)
- {
- data += rtti_count + 1;
- /* Setup for entry to the handler. */
- lp = selfrel_offset31 (data);
- data++;
- _Unwind_SetGR (context, R_PC, lp);
- _Unwind_SetGR (context, 0, (_uw) ucbp);
- return _URC_INSTALL_CONTEXT;
- }
- else
- phase2_call_unexpected_after_unwind = 1;
- }
- if (data[0] & uint32_highbit)
- data++;
- data += rtti_count + 1;
- break;
-
- default:
- /* Should never happen. */
- return _URC_FAILURE;
- }
- /* Finished processing this descriptor. */
- }
- }
-
- if (__gnu_unwind_execute (context, &uws) != _URC_OK)
- return _URC_FAILURE;
-
- if (phase2_call_unexpected_after_unwind)
- {
- /* Enter __cxa_unexpected as if called from the call site. */
- _Unwind_SetGR (context, R_LR, _Unwind_GetGR (context, R_PC));
- _Unwind_SetGR (context, R_PC, (_uw) &__cxa_call_unexpected);
- return _URC_INSTALL_CONTEXT;
- }
-
- return _URC_CONTINUE_UNWIND;
-}
-
-
-/* ABI defined personality routine entry points. */
-
-_Unwind_Reason_Code
-__aeabi_unwind_cpp_pr0 (_Unwind_State state,
- _Unwind_Control_Block *ucbp,
- _Unwind_Context *context)
-{
- return __gnu_unwind_pr_common (state, ucbp, context, 0);
-}
-
-_Unwind_Reason_Code
-__aeabi_unwind_cpp_pr1 (_Unwind_State state,
- _Unwind_Control_Block *ucbp,
- _Unwind_Context *context)
-{
- return __gnu_unwind_pr_common (state, ucbp, context, 1);
-}
-
-_Unwind_Reason_Code
-__aeabi_unwind_cpp_pr2 (_Unwind_State state,
- _Unwind_Control_Block *ucbp,
- _Unwind_Context *context)
-{
- return __gnu_unwind_pr_common (state, ucbp, context, 2);
-}
diff --git a/gcc/config/arm/unwind-arm.h b/gcc/config/arm/unwind-arm.h
deleted file mode 100644
index 1a51d8d..0000000
--- a/gcc/config/arm/unwind-arm.h
+++ /dev/null
@@ -1,281 +0,0 @@
-/* Header file for the ARM EABI unwinder
- Copyright (C) 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2011
- Free Software Foundation, Inc.
- Contributed by Paul Brook
-
- This file is free software; you can redistribute it and/or modify it
- under the terms of the GNU General Public License as published by the
- Free Software Foundation; either version 3, or (at your option) any
- later version.
-
- This file 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
- General Public License for more details.
-
- Under Section 7 of GPL version 3, you are granted additional
- permissions described in the GCC Runtime Library Exception, version
- 3.1, as published by the Free Software Foundation.
-
- You should have received a copy of the GNU General Public License and
- a copy of the GCC Runtime Library Exception along with this program;
- see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
- <http://www.gnu.org/licenses/>. */
-
-/* Language-independent unwinder header public defines. This contains both
- ABI defined objects, and GNU support routines. */
-
-#ifndef UNWIND_ARM_H
-#define UNWIND_ARM_H
-
-#define __ARM_EABI_UNWINDER__ 1
-
-#ifdef __cplusplus
-extern "C" {
-#endif
- typedef unsigned _Unwind_Word __attribute__((__mode__(__word__)));
- typedef signed _Unwind_Sword __attribute__((__mode__(__word__)));
- typedef unsigned _Unwind_Ptr __attribute__((__mode__(__pointer__)));
- typedef unsigned _Unwind_Internal_Ptr __attribute__((__mode__(__pointer__)));
- typedef _Unwind_Word _uw;
- typedef unsigned _uw64 __attribute__((mode(__DI__)));
- typedef unsigned _uw16 __attribute__((mode(__HI__)));
- typedef unsigned _uw8 __attribute__((mode(__QI__)));
-
- typedef enum
- {
- _URC_OK = 0, /* operation completed successfully */
- _URC_FOREIGN_EXCEPTION_CAUGHT = 1,
- _URC_END_OF_STACK = 5,
- _URC_HANDLER_FOUND = 6,
- _URC_INSTALL_CONTEXT = 7,
- _URC_CONTINUE_UNWIND = 8,
- _URC_FAILURE = 9 /* unspecified failure of some kind */
- }
- _Unwind_Reason_Code;
-
- typedef enum
- {
- _US_VIRTUAL_UNWIND_FRAME = 0,
- _US_UNWIND_FRAME_STARTING = 1,
- _US_UNWIND_FRAME_RESUME = 2,
- _US_ACTION_MASK = 3,
- _US_FORCE_UNWIND = 8,
- _US_END_OF_STACK = 16
- }
- _Unwind_State;
-
- /* Provided only for compatibility with existing code. */
- typedef int _Unwind_Action;
-#define _UA_SEARCH_PHASE 1
-#define _UA_CLEANUP_PHASE 2
-#define _UA_HANDLER_FRAME 4
-#define _UA_FORCE_UNWIND 8
-#define _UA_END_OF_STACK 16
-#define _URC_NO_REASON _URC_OK
-
- typedef struct _Unwind_Control_Block _Unwind_Control_Block;
- typedef struct _Unwind_Context _Unwind_Context;
- typedef _uw _Unwind_EHT_Header;
-
-
- /* UCB: */
-
- struct _Unwind_Control_Block
- {
- char exception_class[8];
- void (*exception_cleanup)(_Unwind_Reason_Code, _Unwind_Control_Block *);
- /* Unwinder cache, private fields for the unwinder's use */
- struct
- {
- _uw reserved1; /* Forced unwind stop fn, 0 if not forced */
- _uw reserved2; /* Personality routine address */
- _uw reserved3; /* Saved callsite address */
- _uw reserved4; /* Forced unwind stop arg */
- _uw reserved5;
- }
- unwinder_cache;
- /* Propagation barrier cache (valid after phase 1): */
- struct
- {
- _uw sp;
- _uw bitpattern[5];
- }
- barrier_cache;
- /* Cleanup cache (preserved over cleanup): */
- struct
- {
- _uw bitpattern[4];
- }
- cleanup_cache;
- /* Pr cache (for pr's benefit): */
- struct
- {
- _uw fnstart; /* function start address */
- _Unwind_EHT_Header *ehtp; /* pointer to EHT entry header word */
- _uw additional; /* additional data */
- _uw reserved1;
- }
- pr_cache;
- long long int :0; /* Force alignment to 8-byte boundary */
- };
-
- /* Virtual Register Set*/
-
- typedef enum
- {
- _UVRSC_CORE = 0, /* integer register */
- _UVRSC_VFP = 1, /* vfp */
- _UVRSC_FPA = 2, /* fpa */
- _UVRSC_WMMXD = 3, /* Intel WMMX data register */
- _UVRSC_WMMXC = 4 /* Intel WMMX control register */
- }
- _Unwind_VRS_RegClass;
-
- typedef enum
- {
- _UVRSD_UINT32 = 0,
- _UVRSD_VFPX = 1,
- _UVRSD_FPAX = 2,
- _UVRSD_UINT64 = 3,
- _UVRSD_FLOAT = 4,
- _UVRSD_DOUBLE = 5
- }
- _Unwind_VRS_DataRepresentation;
-
- typedef enum
- {
- _UVRSR_OK = 0,
- _UVRSR_NOT_IMPLEMENTED = 1,
- _UVRSR_FAILED = 2
- }
- _Unwind_VRS_Result;
-
- /* Frame unwinding state. */
- typedef struct
- {
- /* The current word (bytes packed msb first). */
- _uw data;
- /* Pointer to the next word of data. */
- _uw *next;
- /* The number of bytes left in this word. */
- _uw8 bytes_left;
- /* The number of words pointed to by ptr. */
- _uw8 words_left;
- }
- __gnu_unwind_state;
-
- typedef _Unwind_Reason_Code (*personality_routine) (_Unwind_State,
- _Unwind_Control_Block *, _Unwind_Context *);
-
- _Unwind_VRS_Result _Unwind_VRS_Set(_Unwind_Context *, _Unwind_VRS_RegClass,
- _uw, _Unwind_VRS_DataRepresentation,
- void *);
-
- _Unwind_VRS_Result _Unwind_VRS_Get(_Unwind_Context *, _Unwind_VRS_RegClass,
- _uw, _Unwind_VRS_DataRepresentation,
- void *);
-
- _Unwind_VRS_Result _Unwind_VRS_Pop(_Unwind_Context *, _Unwind_VRS_RegClass,
- _uw, _Unwind_VRS_DataRepresentation);
-
-
- /* Support functions for the PR. */
-#define _Unwind_Exception _Unwind_Control_Block
- typedef char _Unwind_Exception_Class[8];
-
- void * _Unwind_GetLanguageSpecificData (_Unwind_Context *);
- _Unwind_Ptr _Unwind_GetRegionStart (_Unwind_Context *);
-
- /* These two should never be used. */
- _Unwind_Ptr _Unwind_GetDataRelBase (_Unwind_Context *);
- _Unwind_Ptr _Unwind_GetTextRelBase (_Unwind_Context *);
-
- /* Interface functions: */
- _Unwind_Reason_Code _Unwind_RaiseException(_Unwind_Control_Block *ucbp);
- void __attribute__((noreturn)) _Unwind_Resume(_Unwind_Control_Block *ucbp);
- _Unwind_Reason_Code _Unwind_Resume_or_Rethrow (_Unwind_Control_Block *ucbp);
-
- typedef _Unwind_Reason_Code (*_Unwind_Stop_Fn)
- (int, _Unwind_Action, _Unwind_Exception_Class,
- _Unwind_Control_Block *, struct _Unwind_Context *, void *);
- _Unwind_Reason_Code _Unwind_ForcedUnwind (_Unwind_Control_Block *,
- _Unwind_Stop_Fn, void *);
- /* @@@ Use unwind data to perform a stack backtrace. The trace callback
- is called for every stack frame in the call chain, but no cleanup
- actions are performed. */
- typedef _Unwind_Reason_Code (*_Unwind_Trace_Fn) (_Unwind_Context *, void *);
- _Unwind_Reason_Code _Unwind_Backtrace(_Unwind_Trace_Fn,
- void*);
-
- _Unwind_Word _Unwind_GetCFA (struct _Unwind_Context *);
- void _Unwind_Complete(_Unwind_Control_Block *ucbp);
- void _Unwind_DeleteException (_Unwind_Exception *);
-
- _Unwind_Reason_Code __gnu_unwind_frame (_Unwind_Control_Block *,
- _Unwind_Context *);
- _Unwind_Reason_Code __gnu_unwind_execute (_Unwind_Context *,
- __gnu_unwind_state *);
-
- /* Decode an R_ARM_TARGET2 relocation. */
- static inline _Unwind_Word
- _Unwind_decode_target2 (_Unwind_Word ptr)
- {
- _Unwind_Word tmp;
-
- tmp = *(_Unwind_Word *) ptr;
- /* Zero values are always NULL. */
- if (!tmp)
- return 0;
-
-#if (defined(linux) && !defined(__uClinux__)) || defined(__NetBSD__)
- /* Pc-relative indirect. */
- tmp += ptr;
- tmp = *(_Unwind_Word *) tmp;
-#elif defined(__symbian__) || defined(__uClinux__)
- /* Absolute pointer. Nothing more to do. */
-#else
- /* Pc-relative pointer. */
- tmp += ptr;
-#endif
- return tmp;
- }
-
- static inline _Unwind_Word
- _Unwind_GetGR (_Unwind_Context *context, int regno)
- {
- _uw val;
- _Unwind_VRS_Get (context, _UVRSC_CORE, regno, _UVRSD_UINT32, &val);
- return val;
- }
-
- /* Return the address of the instruction, not the actual IP value. */
-#define _Unwind_GetIP(context) \
- (_Unwind_GetGR (context, 15) & ~(_Unwind_Word)1)
-
-#define _Unwind_GetIPInfo(context, ip_before_insn) \
- (*ip_before_insn = 0, _Unwind_GetGR (context, 15) & ~(_Unwind_Word)1)
-
- static inline void
- _Unwind_SetGR (_Unwind_Context *context, int regno, _Unwind_Word val)
- {
- _Unwind_VRS_Set (context, _UVRSC_CORE, regno, _UVRSD_UINT32, &val);
- }
-
- /* The dwarf unwinder doesn't understand arm/thumb state. We assume the
- landing pad uses the same instruction set as the call site. */
-#define _Unwind_SetIP(context, val) \
- _Unwind_SetGR (context, 15, val | (_Unwind_GetGR (context, 15) & 1))
-
-/* leb128 type numbers have a potentially unlimited size.
- The target of the following definitions of _sleb128_t and _uleb128_t
- is to have efficient data types large enough to hold the leb128 type
- numbers used in the unwind code. */
-typedef long _sleb128_t;
-typedef unsigned long _uleb128_t;
-
-#ifdef __cplusplus
-} /* extern "C" */
-#endif
-
-#endif /* defined UNWIND_ARM_H */
diff --git a/gcc/config/frv/t-frv b/gcc/config/frv/t-frv
index 0c58bb1..2729008 100644
--- a/gcc/config/frv/t-frv
+++ b/gcc/config/frv/t-frv
@@ -1,4 +1,4 @@
-# Copyright (C) 2002, 2003, 2004 Free Software Foundation, Inc.
+# Copyright (C) 2002, 2003, 2004, 2011 Free Software Foundation, Inc.
#
# This file is part of GCC.
#
@@ -81,12 +81,12 @@ EXTRA_MULTILIB_PARTS=frvbegin.o frvend.o
FRVSTUFF_CFLAGS = $(TARGET_LIBGCC2_CFLAGS)
$(T)frvbegin$(objext): $(srcdir)/config/frv/frvbegin.c $(GCC_PASSES) \
- $(CONFIG_H) defaults.h unwind-dw2-fde.h gbl-ctors.h
+ $(CONFIG_H) defaults.h $(srcdir)/../libgcc/unwind-dw2-fde.h gbl-ctors.h
$(GCC_FOR_TARGET) $(GCC_CFLAGS) $(INCLUDES) $(MULTILIB_CFLAGS) $(FRVSTUFF_CFLAGS) \
-c $(srcdir)/config/frv/frvbegin.c -o $(T)frvbegin$(objext)
$(T)frvend$(objext): $(srcdir)/config/frv/frvend.c $(GCC_PASSES) \
- $(CONFIG_H) defaults.h unwind-dw2-fde.h gbl-ctors.h
+ $(CONFIG_H) defaults.h $(srcdir)/../libgcc/unwind-dw2-fde.h gbl-ctors.h
$(GCC_FOR_TARGET) $(GCC_CFLAGS) $(INCLUDES) $(MULTILIB_CFLAGS) $(FRVSTUFF_CFLAGS) \
-c $(srcdir)/config/frv/frvend.c -o $(T)frvend$(objext)
diff --git a/gcc/config/ia64/fde-glibc.c b/gcc/config/ia64/fde-glibc.c
deleted file mode 100644
index 12760b9..0000000
--- a/gcc/config/ia64/fde-glibc.c
+++ /dev/null
@@ -1,162 +0,0 @@
-/* Copyright (C) 2000, 2001, 2003, 2009 Free Software Foundation, Inc.
- Contributed by Richard Henderson <rth@cygnus.com>.
-
- This file is part of GCC.
-
- GCC is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 3, or (at your option)
- any later version.
-
- GCC 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 General Public License for more details.
-
- Under Section 7 of GPL version 3, you are granted additional
- permissions described in the GCC Runtime Library Exception, version
- 3.1, as published by the Free Software Foundation.
-
- You should have received a copy of the GNU General Public License and
- a copy of the GCC Runtime Library Exception along with this program;
- see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
- <http://www.gnu.org/licenses/>. */
-
-/* Locate the FDE entry for a given address, using glibc ld.so routines
- to avoid register/deregister calls at DSO load/unload. */
-
-#ifndef _GNU_SOURCE
-#define _GNU_SOURCE 1
-#endif
-#include "config.h"
-#include <stddef.h>
-#include <stdlib.h>
-#include <link.h>
-#include "unwind-ia64.h"
-
-#if __GLIBC__ < 2 || (__GLIBC__ == 2 && __GLIBC_MINOR__ < 2) \
- || (__GLIBC__ == 2 && __GLIBC_MINOR__ == 2 && !defined(DT_CONFIG))
-# error You need GLIBC 2.2.4 or later on IA-64 Linux
-#endif
-
-struct unw_ia64_callback_data
-{
- Elf64_Addr pc;
- unsigned long *segment_base;
- unsigned long *gp;
- struct unw_table_entry *ret;
-};
-
-static int
-_Unwind_IteratePhdrCallback (struct dl_phdr_info *info, size_t size, void *ptr)
-{
- struct unw_ia64_callback_data *data = (struct unw_ia64_callback_data *) ptr;
- const Elf64_Phdr *phdr, *p_unwind, *p_dynamic;
- long n, match;
- Elf64_Addr load_base, seg_base;
- struct unw_table_entry *f_base, *f;
- size_t lo, hi;
-
- /* Make sure struct dl_phdr_info is at least as big as we need. */
- if (size < offsetof (struct dl_phdr_info, dlpi_phnum)
- + sizeof (info->dlpi_phnum))
- return -1;
-
- match = 0;
- phdr = info->dlpi_phdr;
- load_base = info->dlpi_addr;
- p_unwind = NULL;
- p_dynamic = NULL;
- seg_base = ~(Elf64_Addr) 0;
-
- /* See if PC falls into one of the loaded segments. Find the unwind
- segment at the same time. */
- for (n = info->dlpi_phnum; --n >= 0; phdr++)
- {
- if (phdr->p_type == PT_LOAD)
- {
- Elf64_Addr vaddr = phdr->p_vaddr + load_base;
- if (data->pc >= vaddr && data->pc < vaddr + phdr->p_memsz)
- match = 1;
- if (vaddr < seg_base)
- seg_base = vaddr;
- }
- else if (phdr->p_type == PT_IA_64_UNWIND)
- p_unwind = phdr;
- else if (phdr->p_type == PT_DYNAMIC)
- p_dynamic = phdr;
- }
- if (!match || !p_unwind)
- return 0;
-
- /* Search for the FDE within the unwind segment. */
-
- f_base = (struct unw_table_entry *) (p_unwind->p_vaddr + load_base);
- lo = 0;
- hi = p_unwind->p_memsz / sizeof (struct unw_table_entry);
-
- while (lo < hi)
- {
- size_t mid = (lo + hi) / 2;
-
- f = f_base + mid;
- if (data->pc < f->start_offset + seg_base)
- hi = mid;
- else if (data->pc >= f->end_offset + seg_base)
- lo = mid + 1;
- else
- goto found;
- }
- /* No need to search for further libraries when we know pc is contained
- in this library. */
- return 1;
-
- found:
- *data->segment_base = seg_base;
- *data->gp = 0;
- data->ret = f;
-
- if (p_dynamic)
- {
- /* For dynamically linked executables and shared libraries,
- DT_PLTGOT is the gp value for that object. */
- Elf64_Dyn *dyn = (Elf64_Dyn *)(p_dynamic->p_vaddr + load_base);
- for (; dyn->d_tag != DT_NULL ; dyn++)
- if (dyn->d_tag == DT_PLTGOT)
- {
- /* On IA-64, _DYNAMIC is writable and GLIBC has relocated it. */
- *data->gp = dyn->d_un.d_ptr;
- break;
- }
- }
- else
- {
- /* Otherwise this is a static executable with no _DYNAMIC.
- The gp is constant program-wide. */
- register unsigned long gp __asm__("gp");
- *data->gp = gp;
- }
-
- return 1;
-}
-
-/* Return a pointer to the unwind table entry for the function
- containing PC. */
-
-struct unw_table_entry *
-_Unwind_FindTableEntry (void *pc, unsigned long *segment_base,
- unsigned long *gp,
- struct unw_table_entry *ent ATTRIBUTE_UNUSED)
-{
- struct unw_ia64_callback_data data;
-
- data.pc = (Elf64_Addr) pc;
- data.segment_base = segment_base;
- data.gp = gp;
- data.ret = NULL;
-
- if (dl_iterate_phdr (_Unwind_IteratePhdrCallback, &data) < 0)
- return NULL;
-
- return data.ret;
-}
diff --git a/gcc/config/ia64/fde-vms.c b/gcc/config/ia64/fde-vms.c
deleted file mode 100644
index b310f0d..0000000
--- a/gcc/config/ia64/fde-vms.c
+++ /dev/null
@@ -1,157 +0,0 @@
-/* Copyright (C) 2004, 2009 Free Software Foundation, Inc.
- Contributed by Douglas B Rupp <rupp@gnat.com>
-
- This file is part of GCC.
-
- GCC is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 3, or (at your option)
- any later version.
-
- GCC 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 General Public License for more details.
-
- Under Section 7 of GPL version 3, you are granted additional
- permissions described in the GCC Runtime Library Exception, version
- 3.1, as published by the Free Software Foundation.
-
- You should have received a copy of the GNU General Public License and
- a copy of the GCC Runtime Library Exception along with this program;
- see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
- <http://www.gnu.org/licenses/>. */
-
-/* Locate the FDE entry for a given address, using VMS Starlet routines
- to avoid register/deregister calls at DSO load/unload. */
-
-#include "tconfig.h"
-#include "tsystem.h"
-#include "coretypes.h"
-#include "tm.h"
-#include <stddef.h>
-#include <stdlib.h>
-#include <stdio.h>
-#include "unwind-ia64.h"
-
-#define __int64 long
-#include <vms/ossddef.h>
-#ifndef SS$_NORMAL
-#define SS$_NORMAL 1
-#endif
-
-typedef struct
-{
- unsigned long start_offset;
- unsigned long end_offset;
- unsigned long info_offset;
- unsigned long gp_value;
-} vms_unw_table_entry;
-
-typedef unsigned long long uqword;
-
-/* ENTRY is the unwind table entry found for a PC part of call chain we're
- unwinding through. Return whether we should force the generic unwinder
- to resort to "fallback" processing. */
-
-static int
-force_fallback_processing_for (void * pc, vms_unw_table_entry * entry)
-{
- static int eh_debug = -1;
-
- uqword * unw_info_block = (uqword *)entry->info_offset;
- uqword header = *unw_info_block;
-
- /* We need to force fallback processing in two cases:
-
- 1/ The exception dispatch frame, since only our fallback
- processing knows how to properly unwind through it, and
-
- 2/ A bottom of stack frame, since only our fallback processing
- will ensure we don't try to unwind further past it, which
- would get us into unknown territory and likely cause a severe
- crash along the way.
-
- The two cases are indicated by non-default values for specific
- bits in the OS Specific Data (OSSD) General Information block
- associated with such frames. */
-
- ossddef * ossd;
-
- if (eh_debug == -1)
- {
- char * EH_DEBUG = getenv ("EH_DEBUG");
- eh_debug = EH_DEBUG ? atoi (EH_DEBUG) : 0;
- }
-
- if (eh_debug)
- {
- printf ("pc @ 0x%p, block @ 0x%p, header = 0x%016llx\n",
- pc, unw_info_block, header);
- printf ("mode = %d, length = %ld, handler = %d\n",
- (int)UNW_IVMS_MODE (header), UNW_LENGTH (header),
- UNW_FLAG_EHANDLER (header) || UNW_FLAG_EHANDLER (header));
- }
-
- /* An OSSD block is there for IVMS_MODE == 3 only. */
- if (UNW_IVMS_MODE (header) != 3)
- return 0;
-
- /* The OSSD block is found past the header, unwind descriptor area
- and condition handler pointer, if any. */
- ossd = (ossddef *)
- /* Beware: uqword pointer arithmetic below. */
- (unw_info_block
- + 1
- + UNW_LENGTH (header)
- + (UNW_FLAG_EHANDLER (header) || UNW_FLAG_EHANDLER (header)));
-
- /* "A General Information segment may be omitted if all of its fields
- would have their default values. If a General Information segment
- is present, it must be the first in the OSSD area." So ... */
-
- if (eh_debug)
- printf ("ossd @ 0x%p\n", ossd);
-
- if (eh_debug && ossd->ossd$v_type == OSSD$K_GENERAL_INFO)
- printf ("exc_frame = %d - bot_frame = %d - base_frame = %d\n",
- ossd->ossd$v_exception_frame,
- ossd->ossd$v_bottom_of_stack,
- ossd->ossd$v_base_frame);
-
- return
- ossd->ossd$v_type == OSSD$K_GENERAL_INFO
- && (ossd->ossd$v_exception_frame
- || ossd->ossd$v_bottom_of_stack || ossd->ossd$v_base_frame);
-}
-
-/* Return a pointer to the unwind table entry for the function
- containing PC, 0 if we cannot find an entry or if the one we find
- calls for fallback processing. */
-
-struct unw_table_entry *
-_Unwind_FindTableEntry (void *pc, unsigned long *segment_base,
- unsigned long *gp, struct unw_table_entry *ent)
-{
- vms_unw_table_entry vueblock;
-
- if (SYS$GET_UNWIND_ENTRY_INFO (pc, &vueblock, 0) != SS$_NORMAL)
- return 0;
-
- /* If there is no unwind information, use fallback. */
- if (vueblock.info_offset == 0)
- return 0;
-
- /* If we need to force fallback processing, just pretend there is
- no entry. */
- if (force_fallback_processing_for (pc, &vueblock))
- return 0;
-
- *segment_base = 0; /* ??? Fixme. ??? */
- *gp = vueblock.gp_value;
- ent->start_offset = vueblock.start_offset;
- ent->end_offset = vueblock.end_offset;
- ent->info_offset = vueblock.info_offset;
-
- return ent;
-}
diff --git a/gcc/config/ia64/t-glibc b/gcc/config/ia64/t-glibc
index e6d72b9..ce18a92 100644
--- a/gcc/config/ia64/t-glibc
+++ b/gcc/config/ia64/t-glibc
@@ -1,5 +1 @@
-# Use system libunwind library on IA-64 GLIBC based system.
-LIB2ADDEH = $(srcdir)/unwind-sjlj.c $(srcdir)/unwind-c.c \
- $(srcdir)/unwind-compat.c
-
SHLIB_MAPFILES += $(srcdir)/config/ia64/libgcc-glibc.ver
diff --git a/gcc/config/ia64/t-glibc-libunwind b/gcc/config/ia64/t-glibc-libunwind
deleted file mode 100644
index df78f1d..0000000
--- a/gcc/config/ia64/t-glibc-libunwind
+++ /dev/null
@@ -1,4 +0,0 @@
-# Build libunwind for IA-64 GLIBC based system.
-LIBUNWIND = $(srcdir)/config/ia64/fde-glibc.c \
- $(srcdir)/config/ia64/unwind-ia64.c
-LIBUNWINDDEP = unwind.inc
diff --git a/gcc/config/ia64/t-hpux b/gcc/config/ia64/t-hpux
index a97ab5c..4aa6614 100644
--- a/gcc/config/ia64/t-hpux
+++ b/gcc/config/ia64/t-hpux
@@ -1,5 +1,5 @@
# Copyright (C) 2001, 2002, 2003, 2004, 2005,
-# 2006 Free Software Foundation, Inc.
+# 2006, 2011 Free Software Foundation, Inc.
#
# This file is part of GCC.
#
@@ -50,8 +50,6 @@ LIBGCC1_TEST =
T_CFLAGS += -DUSE_LIBUNWIND_EXCEPTIONS
-LIB2ADDEH = $(srcdir)/unwind-c.c
-
SHLIB_EXT = .so
# Must include -lunwind in the link, so that libgcc_s.so has the necessary
# DT_NEEDED entry for libunwind.
diff --git a/gcc/config/ia64/t-ia64 b/gcc/config/ia64/t-ia64
index 4f013e2..f130f7c 100644
--- a/gcc/config/ia64/t-ia64
+++ b/gcc/config/ia64/t-ia64
@@ -43,9 +43,6 @@ SHLIB_MAPFILES += $(srcdir)/config/ia64/libgcc-ia64.ver
# Effectively disable the crtbegin/end rules using crtstuff.c
T = disable
-LIB2ADDEH = $(srcdir)/config/ia64/unwind-ia64.c $(srcdir)/unwind-sjlj.c \
- $(srcdir)/unwind-c.c
-
ia64-c.o: $(srcdir)/config/ia64/ia64-c.c $(CONFIG_H) $(SYSTEM_H) \
coretypes.h $(TM_H) $(TREE_H) $(CPPLIB_H) $(C_COMMON_H) $(C_PRAGMA_H)
$(COMPILER) -c $(ALL_COMPILERFLAGS) $(ALL_CPPFLAGS) $(INCLUDES) \
diff --git a/gcc/config/ia64/t-vms b/gcc/config/ia64/t-vms
index bcd7534..094d534 100644
--- a/gcc/config/ia64/t-vms
+++ b/gcc/config/ia64/t-vms
@@ -32,8 +32,6 @@ $(T)crtinitS.o: $(srcdir)/config/ia64/vms-crtinit.asm $(GCC_PASSES)
$(GCC_FOR_TARGET) -I. -c -o $(T)crtinitS.o -x assembler-with-cpp \
$(srcdir)/config/ia64/vms-crtinit.asm
-LIB2ADDEH += $(srcdir)/config/ia64/fde-vms.c
-
# Shared library macros
shlib_version:=$(shell echo $(BASEVER_c) | sed -e 's/\./,/' -e 's/\.//g')
SHLIB_EXT = .exe
diff --git a/gcc/config/ia64/unwind-ia64.c b/gcc/config/ia64/unwind-ia64.c
deleted file mode 100644
index 061bd4b..0000000
--- a/gcc/config/ia64/unwind-ia64.c
+++ /dev/null
@@ -1,2458 +0,0 @@
-/* Subroutines needed for unwinding IA-64 standard format stack frame
- info for exception handling.
- Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002, 2004, 2005, 2006,
- 2009, 2011 Free Software Foundation, Inc.
- Contributed by Andrew MacLeod <amacleod@cygnus.com>
- Andrew Haley <aph@cygnus.com>
- David Mosberger-Tang <davidm@hpl.hp.com>
-
- This file is part of GCC.
-
- GCC is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 3, or (at your option)
- any later version.
-
- GCC 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 General Public License for more details.
-
- Under Section 7 of GPL version 3, you are granted additional
- permissions described in the GCC Runtime Library Exception, version
- 3.1, as published by the Free Software Foundation.
-
- You should have received a copy of the GNU General Public License and
- a copy of the GCC Runtime Library Exception along with this program;
- see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
- <http://www.gnu.org/licenses/>. */
-
-#include "tconfig.h"
-#include "tsystem.h"
-#include "coretypes.h"
-#include "tm.h"
-#include "unwind.h"
-#include "unwind-ia64.h"
-#include "unwind-compat.h"
-#include "ia64intrin.h"
-
-/* This isn't thread safe, but nice for occasional tests. */
-#undef ENABLE_MALLOC_CHECKING
-
-#ifndef __USING_SJLJ_EXCEPTIONS__
-
-
-/* By default, assume personality routine interface compatibility with
- our expectations. */
-#ifndef MD_UNW_COMPATIBLE_PERSONALITY_P
-#define MD_UNW_COMPATIBLE_PERSONALITY_P(HEADER) 1
-#endif
-
-enum unw_application_register
-{
- UNW_AR_BSP,
- UNW_AR_BSPSTORE,
- UNW_AR_PFS,
- UNW_AR_RNAT,
- UNW_AR_UNAT,
- UNW_AR_LC,
- UNW_AR_EC,
- UNW_AR_FPSR,
- UNW_AR_RSC,
- UNW_AR_CCV
-};
-
-enum unw_register_index
-{
- /* Primary UNAT. */
- UNW_REG_PRI_UNAT_GR,
- UNW_REG_PRI_UNAT_MEM,
-
- /* Memory Stack. */
- UNW_REG_PSP, /* previous memory stack pointer */
-
- /* Register Stack. */
- UNW_REG_BSP, /* register stack pointer */
- UNW_REG_BSPSTORE,
- UNW_REG_PFS, /* previous function state */
- UNW_REG_RNAT,
- /* Return Pointer. */
- UNW_REG_RP,
-
- /* Special preserved registers. */
- UNW_REG_UNAT, UNW_REG_PR, UNW_REG_LC, UNW_REG_FPSR,
-
- /* Non-stacked general registers. */
- UNW_REG_R2,
- UNW_REG_R4 = UNW_REG_R2 + 2,
- UNW_REG_R7 = UNW_REG_R2 + 5,
- UNW_REG_R31 = UNW_REG_R2 + 29,
-
- /* Non-stacked floating point registers. */
- UNW_REG_F2,
- UNW_REG_F5 = UNW_REG_F2 + 3,
- UNW_REG_F16 = UNW_REG_F2 + 14,
- UNW_REG_F31 = UNW_REG_F2 + 29,
-
- /* Branch registers. */
- UNW_REG_B0, UNW_REG_B1,
- UNW_REG_B5 = UNW_REG_B1 + 4,
-
- UNW_NUM_REGS
-};
-
-enum unw_where
-{
- UNW_WHERE_NONE, /* register isn't saved at all */
- UNW_WHERE_GR, /* register is saved in a general register */
- UNW_WHERE_FR, /* register is saved in a floating-point register */
- UNW_WHERE_BR, /* register is saved in a branch register */
- UNW_WHERE_SPREL, /* register is saved on memstack (sp-relative) */
- UNW_WHERE_PSPREL, /* register is saved on memstack (psp-relative) */
-
- /* At the end of each prologue these locations get resolved to
- UNW_WHERE_PSPREL and UNW_WHERE_GR, respectively. */
- UNW_WHERE_SPILL_HOME, /* register is saved in its spill home */
- UNW_WHERE_GR_SAVE /* register is saved in next general register */
-};
-
-#define UNW_WHEN_NEVER 0x7fffffff
-
-struct unw_reg_info
-{
- unsigned long val; /* save location: register number or offset */
- enum unw_where where; /* where the register gets saved */
- int when; /* when the register gets saved */
-};
-
-struct unw_reg_state {
- struct unw_reg_state *next; /* next (outer) element on state stack */
- struct unw_reg_info reg[UNW_NUM_REGS]; /* register save locations */
-};
-
-struct unw_labeled_state {
- struct unw_labeled_state *next; /* next labeled state (or NULL) */
- unsigned long label; /* label for this state */
- struct unw_reg_state saved_state;
-};
-
-typedef struct unw_state_record
-{
- unsigned int first_region : 1; /* is this the first region? */
- unsigned int done : 1; /* are we done scanning descriptors? */
- unsigned int any_spills : 1; /* got any register spills? */
- unsigned int in_body : 1; /* are we inside a body? */
- unsigned int no_reg_stack_frame : 1; /* Don't adjust bsp for i&l regs */
- unsigned char *imask; /* imask of spill_mask record or NULL */
- unsigned long pr_val; /* predicate values */
- unsigned long pr_mask; /* predicate mask */
- long spill_offset; /* psp-relative offset for spill base */
- int region_start;
- int region_len;
- int epilogue_start;
- int epilogue_count;
- int when_target;
-
- unsigned char gr_save_loc; /* next general register to use for saving */
- unsigned char return_link_reg; /* branch register for return link */
- unsigned short unwabi;
-
- struct unw_labeled_state *labeled_states; /* list of all labeled states */
- struct unw_reg_state curr; /* current state */
-
- _Unwind_Personality_Fn personality;
-
-} _Unwind_FrameState;
-
-enum unw_nat_type
-{
- UNW_NAT_NONE, /* NaT not represented */
- UNW_NAT_VAL, /* NaT represented by NaT value (fp reg) */
- UNW_NAT_MEMSTK, /* NaT value is in unat word at offset OFF */
- UNW_NAT_REGSTK /* NaT is in rnat */
-};
-
-struct unw_stack
-{
- unsigned long limit;
- unsigned long top;
-};
-
-struct _Unwind_Context
-{
- /* Initial frame info. */
- unsigned long rnat; /* rse nat collection */
- unsigned long regstk_top; /* lowest address of rbs stored register
- which uses context->rnat collection */
-
- /* Current frame info. */
- unsigned long bsp; /* backing store pointer value
- corresponding to psp. */
- unsigned long sp; /* stack pointer value */
- unsigned long psp; /* previous sp value */
- unsigned long rp; /* return pointer */
- unsigned long pr; /* predicate collection */
-
- unsigned long region_start; /* start of unwind region */
- unsigned long gp; /* global pointer value */
- void *lsda; /* language specific data area */
-
- /* Preserved state. */
- unsigned long *bsp_loc; /* previous bsp save location
- Appears to be write-only? */
- unsigned long *bspstore_loc;
- unsigned long *pfs_loc; /* Save location for pfs in current
- (corr. to sp) frame. Target
- contains cfm for caller. */
- unsigned long *signal_pfs_loc;/* Save location for pfs in current
- signal frame. Target contains
- pfs for caller. */
- unsigned long *pri_unat_loc;
- unsigned long *unat_loc;
- unsigned long *lc_loc;
- unsigned long *fpsr_loc;
-
- unsigned long eh_data[4];
-
- struct unw_ireg
- {
- unsigned long *loc;
- struct unw_ireg_nat
- {
- enum unw_nat_type type : 3;
- signed long off : 61; /* NaT word is at loc+nat.off */
- } nat;
- } ireg[32 - 2]; /* Indexed by <register number> - 2 */
-
- unsigned long *br_loc[8];
- void *fr_loc[32 - 2];
-
- /* ??? We initially point pri_unat_loc here. The entire NAT bit
- logic needs work. */
- unsigned long initial_unat;
-};
-
-typedef unsigned long unw_word;
-
-/* Implicit register save order. See section 11.4.2.3 Rules for Using
- Unwind Descriptors, rule 3. */
-
-static unsigned char const save_order[] =
-{
- UNW_REG_RP, UNW_REG_PFS, UNW_REG_PSP, UNW_REG_PR,
- UNW_REG_UNAT, UNW_REG_LC, UNW_REG_FPSR, UNW_REG_PRI_UNAT_GR
-};
-
-
-#define MIN(X, Y) ((X) < (Y) ? (X) : (Y))
-
-/* MASK is a bitmap describing the allocation state of emergency buffers,
- with bit set indicating free. Return >= 0 if allocation is successful;
- < 0 if failure. */
-
-static inline int
-atomic_alloc (unsigned int *mask)
-{
- unsigned int old = *mask, ret, new;
-
- while (1)
- {
- if (old == 0)
- return -1;
- ret = old & -old;
- new = old & ~ret;
- new = __sync_val_compare_and_swap (mask, old, new);
- if (old == new)
- break;
- old = new;
- }
-
- return __builtin_ffs (ret) - 1;
-}
-
-/* Similarly, free an emergency buffer. */
-
-static inline void
-atomic_free (unsigned int *mask, int bit)
-{
- __sync_xor_and_fetch (mask, 1 << bit);
-}
-
-
-#define SIZE(X) (sizeof(X) / sizeof(*(X)))
-#define MASK_FOR(X) ((2U << (SIZE (X) - 1)) - 1)
-#define PTR_IN(X, P) ((P) >= (X) && (P) < (X) + SIZE (X))
-
-static struct unw_reg_state emergency_reg_state[32];
-static unsigned int emergency_reg_state_free = MASK_FOR (emergency_reg_state);
-
-static struct unw_labeled_state emergency_labeled_state[8];
-static unsigned int emergency_labeled_state_free = MASK_FOR (emergency_labeled_state);
-
-#ifdef ENABLE_MALLOC_CHECKING
-static int reg_state_alloced;
-static int labeled_state_alloced;
-#endif
-
-/* Allocation and deallocation of structures. */
-
-static struct unw_reg_state *
-alloc_reg_state (void)
-{
- struct unw_reg_state *rs;
-
-#ifdef ENABLE_MALLOC_CHECKING
- reg_state_alloced++;
-#endif
-
- rs = malloc (sizeof (struct unw_reg_state));
- if (!rs)
- {
- int n = atomic_alloc (&emergency_reg_state_free);
- if (n >= 0)
- rs = &emergency_reg_state[n];
- }
-
- return rs;
-}
-
-static void
-free_reg_state (struct unw_reg_state *rs)
-{
-#ifdef ENABLE_MALLOC_CHECKING
- reg_state_alloced--;
-#endif
-
- if (PTR_IN (emergency_reg_state, rs))
- atomic_free (&emergency_reg_state_free, rs - emergency_reg_state);
- else
- free (rs);
-}
-
-static struct unw_labeled_state *
-alloc_label_state (void)
-{
- struct unw_labeled_state *ls;
-
-#ifdef ENABLE_MALLOC_CHECKING
- labeled_state_alloced++;
-#endif
-
- ls = malloc(sizeof(struct unw_labeled_state));
- if (!ls)
- {
- int n = atomic_alloc (&emergency_labeled_state_free);
- if (n >= 0)
- ls = &emergency_labeled_state[n];
- }
-
- return ls;
-}
-
-static void
-free_label_state (struct unw_labeled_state *ls)
-{
-#ifdef ENABLE_MALLOC_CHECKING
- labeled_state_alloced--;
-#endif
-
- if (PTR_IN (emergency_labeled_state, ls))
- atomic_free (&emergency_labeled_state_free, emergency_labeled_state - ls);
- else
- free (ls);
-}
-
-/* Routines to manipulate the state stack. */
-
-static void
-push (struct unw_state_record *sr)
-{
- struct unw_reg_state *rs = alloc_reg_state ();
- memcpy (rs, &sr->curr, sizeof (*rs));
- sr->curr.next = rs;
-}
-
-static void
-pop (struct unw_state_record *sr)
-{
- struct unw_reg_state *rs = sr->curr.next;
-
- if (!rs)
- abort ();
- memcpy (&sr->curr, rs, sizeof(*rs));
- free_reg_state (rs);
-}
-
-/* Make a copy of the state stack. Non-recursive to avoid stack overflows. */
-
-static struct unw_reg_state *
-dup_state_stack (struct unw_reg_state *rs)
-{
- struct unw_reg_state *copy, *prev = NULL, *first = NULL;
-
- while (rs)
- {
- copy = alloc_reg_state ();
- memcpy (copy, rs, sizeof(*copy));
- if (first)
- prev->next = copy;
- else
- first = copy;
- rs = rs->next;
- prev = copy;
- }
-
- return first;
-}
-
-/* Free all stacked register states (but not RS itself). */
-static void
-free_state_stack (struct unw_reg_state *rs)
-{
- struct unw_reg_state *p, *next;
-
- for (p = rs->next; p != NULL; p = next)
- {
- next = p->next;
- free_reg_state (p);
- }
- rs->next = NULL;
-}
-
-/* Free all labeled states. */
-
-static void
-free_label_states (struct unw_labeled_state *ls)
-{
- struct unw_labeled_state *next;
-
- for (; ls ; ls = next)
- {
- next = ls->next;
-
- free_state_stack (&ls->saved_state);
- free_label_state (ls);
- }
-}
-
-/* Unwind decoder routines */
-
-static enum unw_register_index __attribute__((const))
-decode_abreg (unsigned char abreg, int memory)
-{
- switch (abreg)
- {
-#if TARGET_ABI_OPEN_VMS
- /* OpenVMS Calling Standard specifies R3 - R31. */
- case 0x03 ... 0x1f: return UNW_REG_R2 + (abreg - 0x02);
-#else
- /* Standard Intel ABI specifies GR 4 - 7. */
- case 0x04 ... 0x07: return UNW_REG_R4 + (abreg - 0x04);
-#endif
- case 0x22 ... 0x25: return UNW_REG_F2 + (abreg - 0x22);
- case 0x30 ... 0x3f: return UNW_REG_F16 + (abreg - 0x30);
- case 0x41 ... 0x45: return UNW_REG_B1 + (abreg - 0x41);
- case 0x60: return UNW_REG_PR;
- case 0x61: return UNW_REG_PSP;
- case 0x62: return memory ? UNW_REG_PRI_UNAT_MEM : UNW_REG_PRI_UNAT_GR;
- case 0x63: return UNW_REG_RP;
- case 0x64: return UNW_REG_BSP;
- case 0x65: return UNW_REG_BSPSTORE;
- case 0x66: return UNW_REG_RNAT;
- case 0x67: return UNW_REG_UNAT;
- case 0x68: return UNW_REG_FPSR;
- case 0x69: return UNW_REG_PFS;
- case 0x6a: return UNW_REG_LC;
- default:
- abort ();
- }
-}
-
-static void
-set_reg (struct unw_reg_info *reg, enum unw_where where,
- int when, unsigned long val)
-{
- reg->val = val;
- reg->where = where;
- if (reg->when == UNW_WHEN_NEVER)
- reg->when = when;
-}
-
-static void
-alloc_spill_area (unsigned long *offp, unsigned long regsize,
- struct unw_reg_info *lo, struct unw_reg_info *hi)
-{
- struct unw_reg_info *reg;
-
- for (reg = hi; reg >= lo; --reg)
- {
- if (reg->where == UNW_WHERE_SPILL_HOME)
- {
- reg->where = UNW_WHERE_PSPREL;
- *offp -= regsize;
- reg->val = *offp;
- }
- }
-}
-
-static inline void
-spill_next_when (struct unw_reg_info **regp, struct unw_reg_info *lim,
- unw_word t)
-{
- struct unw_reg_info *reg;
-
- for (reg = *regp; reg <= lim; ++reg)
- {
- if (reg->where == UNW_WHERE_SPILL_HOME)
- {
- reg->when = t;
- *regp = reg + 1;
- return;
- }
- }
- /* Excess spill. */
- abort ();
-}
-
-static void
-finish_prologue (struct unw_state_record *sr)
-{
- struct unw_reg_info *reg;
- unsigned long off;
- int i;
-
- /* First, resolve implicit register save locations
- (see Section "11.4.2.3 Rules for Using Unwind Descriptors", rule 3). */
-
- for (i = 0; i < (int) sizeof (save_order); ++i)
- {
- reg = sr->curr.reg + save_order[i];
- if (reg->where == UNW_WHERE_GR_SAVE)
- {
- reg->where = UNW_WHERE_GR;
- reg->val = sr->gr_save_loc++;
- }
- }
-
- /* Next, compute when the fp, general, and branch registers get saved.
- This must come before alloc_spill_area() because we need to know
- which registers are spilled to their home locations. */
- if (sr->imask)
- {
- static unsigned char const limit[3] = {
- UNW_REG_F31, UNW_REG_R7, UNW_REG_B5
- };
-
- unsigned char kind, mask = 0, *cp = sr->imask;
- int t;
- struct unw_reg_info *(regs[3]);
-
- regs[0] = sr->curr.reg + UNW_REG_F2;
- regs[1] = sr->curr.reg + UNW_REG_R4;
- regs[2] = sr->curr.reg + UNW_REG_B1;
-
- for (t = 0; t < sr->region_len; ++t)
- {
- if ((t & 3) == 0)
- mask = *cp++;
- kind = (mask >> 2*(3-(t & 3))) & 3;
- if (kind > 0)
- spill_next_when (&regs[kind - 1], sr->curr.reg + limit[kind - 1],
- sr->region_start + t);
- }
- }
-
- /* Next, lay out the memory stack spill area. */
- if (sr->any_spills)
- {
- off = sr->spill_offset;
- alloc_spill_area (&off, 16, sr->curr.reg + UNW_REG_F2,
- sr->curr.reg + UNW_REG_F31);
- alloc_spill_area (&off, 8, sr->curr.reg + UNW_REG_B1,
- sr->curr.reg + UNW_REG_B5);
- alloc_spill_area (&off, 8, sr->curr.reg + UNW_REG_R4,
- sr->curr.reg + UNW_REG_R7);
- }
-}
-
-/*
- * Region header descriptors.
- */
-
-static void
-desc_prologue (int body, unw_word rlen, unsigned char mask,
- unsigned char grsave, struct unw_state_record *sr)
-{
- int i;
-
- if (!(sr->in_body || sr->first_region))
- finish_prologue (sr);
- sr->first_region = 0;
-
- /* Check if we're done. */
- if (sr->when_target < sr->region_start + sr->region_len)
- {
- sr->done = 1;
- return;
- }
-
- for (i = 0; i < sr->epilogue_count; ++i)
- pop (sr);
-
- sr->epilogue_count = 0;
- sr->epilogue_start = UNW_WHEN_NEVER;
-
- if (!body)
- push (sr);
-
- sr->region_start += sr->region_len;
- sr->region_len = rlen;
- sr->in_body = body;
-
- if (!body)
- {
- for (i = 0; i < 4; ++i)
- {
- if (mask & 0x8)
- set_reg (sr->curr.reg + save_order[i], UNW_WHERE_GR,
- sr->region_start + sr->region_len - 1, grsave++);
- mask <<= 1;
- }
- sr->gr_save_loc = grsave;
- sr->any_spills = 0;
- sr->imask = 0;
- sr->spill_offset = 0x10; /* default to psp+16 */
- }
-}
-
-/*
- * Prologue descriptors.
- */
-
-static inline void
-desc_abi (unsigned char abi,
- unsigned char context,
- struct unw_state_record *sr)
-{
- sr->unwabi = (abi << 8) | context;
-}
-
-static inline void
-desc_br_gr (unsigned char brmask, unsigned char gr,
- struct unw_state_record *sr)
-{
- int i;
-
- for (i = 0; i < 5; ++i)
- {
- if (brmask & 1)
- set_reg (sr->curr.reg + UNW_REG_B1 + i, UNW_WHERE_GR,
- sr->region_start + sr->region_len - 1, gr++);
- brmask >>= 1;
- }
-}
-
-static inline void
-desc_br_mem (unsigned char brmask, struct unw_state_record *sr)
-{
- int i;
-
- for (i = 0; i < 5; ++i)
- {
- if (brmask & 1)
- {
- set_reg (sr->curr.reg + UNW_REG_B1 + i, UNW_WHERE_SPILL_HOME,
- sr->region_start + sr->region_len - 1, 0);
- sr->any_spills = 1;
- }
- brmask >>= 1;
- }
-}
-
-static inline void
-desc_frgr_mem (unsigned char grmask, unw_word frmask,
- struct unw_state_record *sr)
-{
- int i;
-
- for (i = 0; i < 4; ++i)
- {
- if ((grmask & 1) != 0)
- {
- set_reg (sr->curr.reg + UNW_REG_R4 + i, UNW_WHERE_SPILL_HOME,
- sr->region_start + sr->region_len - 1, 0);
- sr->any_spills = 1;
- }
- grmask >>= 1;
- }
- for (i = 0; i < 20; ++i)
- {
- if ((frmask & 1) != 0)
- {
- enum unw_register_index base = i < 4 ? UNW_REG_F2 : UNW_REG_F16 - 4;
- set_reg (sr->curr.reg + base + i, UNW_WHERE_SPILL_HOME,
- sr->region_start + sr->region_len - 1, 0);
- sr->any_spills = 1;
- }
- frmask >>= 1;
- }
-}
-
-static inline void
-desc_fr_mem (unsigned char frmask, struct unw_state_record *sr)
-{
- int i;
-
- for (i = 0; i < 4; ++i)
- {
- if ((frmask & 1) != 0)
- {
- set_reg (sr->curr.reg + UNW_REG_F2 + i, UNW_WHERE_SPILL_HOME,
- sr->region_start + sr->region_len - 1, 0);
- sr->any_spills = 1;
- }
- frmask >>= 1;
- }
-}
-
-static inline void
-desc_gr_gr (unsigned char grmask, unsigned char gr,
- struct unw_state_record *sr)
-{
- int i;
-
- for (i = 0; i < 4; ++i)
- {
- if ((grmask & 1) != 0)
- set_reg (sr->curr.reg + UNW_REG_R4 + i, UNW_WHERE_GR,
- sr->region_start + sr->region_len - 1, gr++);
- grmask >>= 1;
- }
-}
-
-static inline void
-desc_gr_mem (unsigned char grmask, struct unw_state_record *sr)
-{
- int i;
-
- for (i = 0; i < 4; ++i)
- {
- if ((grmask & 1) != 0)
- {
- set_reg (sr->curr.reg + UNW_REG_R4 + i, UNW_WHERE_SPILL_HOME,
- sr->region_start + sr->region_len - 1, 0);
- sr->any_spills = 1;
- }
- grmask >>= 1;
- }
-}
-
-static inline void
-desc_mem_stack_f (unw_word t, unw_word size, struct unw_state_record *sr)
-{
- set_reg (sr->curr.reg + UNW_REG_PSP, UNW_WHERE_NONE,
- sr->region_start + MIN ((int)t, sr->region_len - 1), 16*size);
-}
-
-static inline void
-desc_mem_stack_v (unw_word t, struct unw_state_record *sr)
-{
- sr->curr.reg[UNW_REG_PSP].when
- = sr->region_start + MIN ((int)t, sr->region_len - 1);
-}
-
-static inline void
-desc_reg_gr (unsigned char reg, unsigned char dst, struct unw_state_record *sr)
-{
- set_reg (sr->curr.reg + reg, UNW_WHERE_GR,
- sr->region_start + sr->region_len - 1, dst);
-}
-
-static inline void
-desc_reg_psprel (unsigned char reg, unw_word pspoff,
- struct unw_state_record *sr)
-{
- set_reg (sr->curr.reg + reg, UNW_WHERE_PSPREL,
- sr->region_start + sr->region_len - 1,
- 0x10 - 4*pspoff);
-}
-
-static inline void
-desc_reg_sprel (unsigned char reg, unw_word spoff, struct unw_state_record *sr)
-{
- set_reg (sr->curr.reg + reg, UNW_WHERE_SPREL,
- sr->region_start + sr->region_len - 1,
- 4*spoff);
-}
-
-static inline void
-desc_rp_br (unsigned char dst, struct unw_state_record *sr)
-{
- sr->return_link_reg = dst;
-}
-
-static inline void
-desc_reg_when (unsigned char regnum, unw_word t, struct unw_state_record *sr)
-{
- struct unw_reg_info *reg = sr->curr.reg + regnum;
-
- if (reg->where == UNW_WHERE_NONE)
- reg->where = UNW_WHERE_GR_SAVE;
- reg->when = sr->region_start + MIN ((int)t, sr->region_len - 1);
-}
-
-static inline void
-desc_spill_base (unw_word pspoff, struct unw_state_record *sr)
-{
- sr->spill_offset = 0x10 - 4*pspoff;
-}
-
-static inline unsigned char *
-desc_spill_mask (unsigned char *imaskp, struct unw_state_record *sr)
-{
- sr->imask = imaskp;
- return imaskp + (2*sr->region_len + 7)/8;
-}
-
-/*
- * Body descriptors.
- */
-static inline void
-desc_epilogue (unw_word t, unw_word ecount, struct unw_state_record *sr)
-{
- sr->epilogue_start = sr->region_start + sr->region_len - 1 - t;
- sr->epilogue_count = ecount + 1;
-}
-
-static inline void
-desc_copy_state (unw_word label, struct unw_state_record *sr)
-{
- struct unw_labeled_state *ls;
-
- for (ls = sr->labeled_states; ls; ls = ls->next)
- {
- if (ls->label == label)
- {
- free_state_stack (&sr->curr);
- memcpy (&sr->curr, &ls->saved_state, sizeof (sr->curr));
- sr->curr.next = dup_state_stack (ls->saved_state.next);
- return;
- }
- }
- abort ();
-}
-
-static inline void
-desc_label_state (unw_word label, struct unw_state_record *sr)
-{
- struct unw_labeled_state *ls = alloc_label_state ();
-
- ls->label = label;
- memcpy (&ls->saved_state, &sr->curr, sizeof (ls->saved_state));
- ls->saved_state.next = dup_state_stack (sr->curr.next);
-
- /* Insert into list of labeled states. */
- ls->next = sr->labeled_states;
- sr->labeled_states = ls;
-}
-
-/*
- * General descriptors.
- */
-
-static inline int
-desc_is_active (unsigned char qp, unw_word t, struct unw_state_record *sr)
-{
- if (sr->when_target <= sr->region_start + MIN ((int)t, sr->region_len - 1))
- return 0;
- if (qp > 0)
- {
- if ((sr->pr_val & (1UL << qp)) == 0)
- return 0;
- sr->pr_mask |= (1UL << qp);
- }
- return 1;
-}
-
-static inline void
-desc_restore_p (unsigned char qp, unw_word t, unsigned char abreg,
- struct unw_state_record *sr)
-{
- struct unw_reg_info *r;
-
- if (! desc_is_active (qp, t, sr))
- return;
-
- r = sr->curr.reg + decode_abreg (abreg, 0);
- r->where = UNW_WHERE_NONE;
- r->when = sr->region_start + MIN ((int)t, sr->region_len - 1);
- r->val = 0;
-}
-
-static inline void
-desc_spill_reg_p (unsigned char qp, unw_word t, unsigned char abreg,
- unsigned char x, unsigned char ytreg,
- struct unw_state_record *sr)
-{
- enum unw_where where = UNW_WHERE_GR;
- struct unw_reg_info *r;
-
- if (! desc_is_active (qp, t, sr))
- return;
-
- if (x)
- where = UNW_WHERE_BR;
- else if (ytreg & 0x80)
- where = UNW_WHERE_FR;
-
- r = sr->curr.reg + decode_abreg (abreg, 0);
- r->where = where;
- r->when = sr->region_start + MIN ((int)t, sr->region_len - 1);
- r->val = ytreg & 0x7f;
-}
-
-static inline void
-desc_spill_psprel_p (unsigned char qp, unw_word t, unsigned char abreg,
- unw_word pspoff, struct unw_state_record *sr)
-{
- struct unw_reg_info *r;
-
- if (! desc_is_active (qp, t, sr))
- return;
-
- r = sr->curr.reg + decode_abreg (abreg, 1);
- r->where = UNW_WHERE_PSPREL;
- r->when = sr->region_start + MIN((int)t, sr->region_len - 1);
- r->val = 0x10 - 4*pspoff;
-}
-
-static inline void
-desc_spill_sprel_p (unsigned char qp, unw_word t, unsigned char abreg,
- unw_word spoff, struct unw_state_record *sr)
-{
- struct unw_reg_info *r;
-
- if (! desc_is_active (qp, t, sr))
- return;
-
- r = sr->curr.reg + decode_abreg (abreg, 1);
- r->where = UNW_WHERE_SPREL;
- r->when = sr->region_start + MIN ((int)t, sr->region_len - 1);
- r->val = 4*spoff;
-}
-
-
-#define UNW_DEC_BAD_CODE(code) abort ();
-
-/* Region headers. */
-#define UNW_DEC_PROLOGUE_GR(fmt,r,m,gr,arg) desc_prologue(0,r,m,gr,arg)
-#define UNW_DEC_PROLOGUE(fmt,b,r,arg) desc_prologue(b,r,0,32,arg)
-
-/* Prologue descriptors. */
-#define UNW_DEC_ABI(fmt,a,c,arg) desc_abi(a,c,arg)
-#define UNW_DEC_BR_GR(fmt,b,g,arg) desc_br_gr(b,g,arg)
-#define UNW_DEC_BR_MEM(fmt,b,arg) desc_br_mem(b,arg)
-#define UNW_DEC_FRGR_MEM(fmt,g,f,arg) desc_frgr_mem(g,f,arg)
-#define UNW_DEC_FR_MEM(fmt,f,arg) desc_fr_mem(f,arg)
-#define UNW_DEC_GR_GR(fmt,m,g,arg) desc_gr_gr(m,g,arg)
-#define UNW_DEC_GR_MEM(fmt,m,arg) desc_gr_mem(m,arg)
-#define UNW_DEC_MEM_STACK_F(fmt,t,s,arg) desc_mem_stack_f(t,s,arg)
-#define UNW_DEC_MEM_STACK_V(fmt,t,arg) desc_mem_stack_v(t,arg)
-#define UNW_DEC_REG_GR(fmt,r,d,arg) desc_reg_gr(r,d,arg)
-#define UNW_DEC_REG_PSPREL(fmt,r,o,arg) desc_reg_psprel(r,o,arg)
-#define UNW_DEC_REG_SPREL(fmt,r,o,arg) desc_reg_sprel(r,o,arg)
-#define UNW_DEC_REG_WHEN(fmt,r,t,arg) desc_reg_when(r,t,arg)
-#define UNW_DEC_PRIUNAT_WHEN_GR(fmt,t,arg) desc_reg_when(UNW_REG_PRI_UNAT_GR,t,arg)
-#define UNW_DEC_PRIUNAT_WHEN_MEM(fmt,t,arg) desc_reg_when(UNW_REG_PRI_UNAT_MEM,t,arg)
-#define UNW_DEC_PRIUNAT_GR(fmt,r,arg) desc_reg_gr(UNW_REG_PRI_UNAT_GR,r,arg)
-#define UNW_DEC_PRIUNAT_PSPREL(fmt,o,arg) desc_reg_psprel(UNW_REG_PRI_UNAT_MEM,o,arg)
-#define UNW_DEC_PRIUNAT_SPREL(fmt,o,arg) desc_reg_sprel(UNW_REG_PRI_UNAT_MEM,o,arg)
-#define UNW_DEC_RP_BR(fmt,d,arg) desc_rp_br(d,arg)
-#define UNW_DEC_SPILL_BASE(fmt,o,arg) desc_spill_base(o,arg)
-#define UNW_DEC_SPILL_MASK(fmt,m,arg) (m = desc_spill_mask(m,arg))
-
-/* Body descriptors. */
-#define UNW_DEC_EPILOGUE(fmt,t,c,arg) desc_epilogue(t,c,arg)
-#define UNW_DEC_COPY_STATE(fmt,l,arg) desc_copy_state(l,arg)
-#define UNW_DEC_LABEL_STATE(fmt,l,arg) desc_label_state(l,arg)
-
-/* General unwind descriptors. */
-#define UNW_DEC_SPILL_REG_P(f,p,t,a,x,y,arg) desc_spill_reg_p(p,t,a,x,y,arg)
-#define UNW_DEC_SPILL_REG(f,t,a,x,y,arg) desc_spill_reg_p(0,t,a,x,y,arg)
-#define UNW_DEC_SPILL_PSPREL_P(f,p,t,a,o,arg) desc_spill_psprel_p(p,t,a,o,arg)
-#define UNW_DEC_SPILL_PSPREL(f,t,a,o,arg) desc_spill_psprel_p(0,t,a,o,arg)
-#define UNW_DEC_SPILL_SPREL_P(f,p,t,a,o,arg) desc_spill_sprel_p(p,t,a,o,arg)
-#define UNW_DEC_SPILL_SPREL(f,t,a,o,arg) desc_spill_sprel_p(0,t,a,o,arg)
-#define UNW_DEC_RESTORE_P(f,p,t,a,arg) desc_restore_p(p,t,a,arg)
-#define UNW_DEC_RESTORE(f,t,a,arg) desc_restore_p(0,t,a,arg)
-
-
-/*
- * Generic IA-64 unwind info decoder.
- *
- * This file is used both by the Linux kernel and objdump. Please keep
- * the copies of this file in sync.
- *
- * You need to customize the decoder by defining the following
- * macros/constants before including this file:
- *
- * Types:
- * unw_word Unsigned integer type with at least 64 bits
- *
- * Register names:
- * UNW_REG_BSP
- * UNW_REG_BSPSTORE
- * UNW_REG_FPSR
- * UNW_REG_LC
- * UNW_REG_PFS
- * UNW_REG_PR
- * UNW_REG_RNAT
- * UNW_REG_PSP
- * UNW_REG_RP
- * UNW_REG_UNAT
- *
- * Decoder action macros:
- * UNW_DEC_BAD_CODE(code)
- * UNW_DEC_ABI(fmt,abi,context,arg)
- * UNW_DEC_BR_GR(fmt,brmask,gr,arg)
- * UNW_DEC_BR_MEM(fmt,brmask,arg)
- * UNW_DEC_COPY_STATE(fmt,label,arg)
- * UNW_DEC_EPILOGUE(fmt,t,ecount,arg)
- * UNW_DEC_FRGR_MEM(fmt,grmask,frmask,arg)
- * UNW_DEC_FR_MEM(fmt,frmask,arg)
- * UNW_DEC_GR_GR(fmt,grmask,gr,arg)
- * UNW_DEC_GR_MEM(fmt,grmask,arg)
- * UNW_DEC_LABEL_STATE(fmt,label,arg)
- * UNW_DEC_MEM_STACK_F(fmt,t,size,arg)
- * UNW_DEC_MEM_STACK_V(fmt,t,arg)
- * UNW_DEC_PRIUNAT_GR(fmt,r,arg)
- * UNW_DEC_PRIUNAT_WHEN_GR(fmt,t,arg)
- * UNW_DEC_PRIUNAT_WHEN_MEM(fmt,t,arg)
- * UNW_DEC_PRIUNAT_WHEN_PSPREL(fmt,pspoff,arg)
- * UNW_DEC_PRIUNAT_WHEN_SPREL(fmt,spoff,arg)
- * UNW_DEC_PROLOGUE(fmt,body,rlen,arg)
- * UNW_DEC_PROLOGUE_GR(fmt,rlen,mask,grsave,arg)
- * UNW_DEC_REG_PSPREL(fmt,reg,pspoff,arg)
- * UNW_DEC_REG_REG(fmt,src,dst,arg)
- * UNW_DEC_REG_SPREL(fmt,reg,spoff,arg)
- * UNW_DEC_REG_WHEN(fmt,reg,t,arg)
- * UNW_DEC_RESTORE(fmt,t,abreg,arg)
- * UNW_DEC_RESTORE_P(fmt,qp,t,abreg,arg)
- * UNW_DEC_SPILL_BASE(fmt,pspoff,arg)
- * UNW_DEC_SPILL_MASK(fmt,imaskp,arg)
- * UNW_DEC_SPILL_PSPREL(fmt,t,abreg,pspoff,arg)
- * UNW_DEC_SPILL_PSPREL_P(fmt,qp,t,abreg,pspoff,arg)
- * UNW_DEC_SPILL_REG(fmt,t,abreg,x,ytreg,arg)
- * UNW_DEC_SPILL_REG_P(fmt,qp,t,abreg,x,ytreg,arg)
- * UNW_DEC_SPILL_SPREL(fmt,t,abreg,spoff,arg)
- * UNW_DEC_SPILL_SPREL_P(fmt,qp,t,abreg,pspoff,arg)
- */
-
-static unw_word
-unw_decode_uleb128 (unsigned char **dpp)
-{
- unsigned shift = 0;
- unw_word byte, result = 0;
- unsigned char *bp = *dpp;
-
- while (1)
- {
- byte = *bp++;
- result |= (byte & 0x7f) << shift;
- if ((byte & 0x80) == 0)
- break;
- shift += 7;
- }
- *dpp = bp;
- return result;
-}
-
-static unsigned char *
-unw_decode_x1 (unsigned char *dp,
- unsigned char code __attribute__((unused)),
- void *arg)
-{
- unsigned char byte1, abreg;
- unw_word t, off;
-
- byte1 = *dp++;
- t = unw_decode_uleb128 (&dp);
- off = unw_decode_uleb128 (&dp);
- abreg = (byte1 & 0x7f);
- if (byte1 & 0x80)
- UNW_DEC_SPILL_SPREL(X1, t, abreg, off, arg);
- else
- UNW_DEC_SPILL_PSPREL(X1, t, abreg, off, arg);
- return dp;
-}
-
-static unsigned char *
-unw_decode_x2 (unsigned char *dp,
- unsigned char code __attribute__((unused)),
- void *arg)
-{
- unsigned char byte1, byte2, abreg, x, ytreg;
- unw_word t;
-
- byte1 = *dp++; byte2 = *dp++;
- t = unw_decode_uleb128 (&dp);
- abreg = (byte1 & 0x7f);
- ytreg = byte2;
- x = (byte1 >> 7) & 1;
- if ((byte1 & 0x80) == 0 && ytreg == 0)
- UNW_DEC_RESTORE(X2, t, abreg, arg);
- else
- UNW_DEC_SPILL_REG(X2, t, abreg, x, ytreg, arg);
- return dp;
-}
-
-static unsigned char *
-unw_decode_x3 (unsigned char *dp,
- unsigned char code __attribute__((unused)),
- void *arg)
-{
- unsigned char byte1, byte2, abreg, qp;
- unw_word t, off;
-
- byte1 = *dp++; byte2 = *dp++;
- t = unw_decode_uleb128 (&dp);
- off = unw_decode_uleb128 (&dp);
-
- qp = (byte1 & 0x3f);
- abreg = (byte2 & 0x7f);
-
- if (byte1 & 0x80)
- UNW_DEC_SPILL_SPREL_P(X3, qp, t, abreg, off, arg);
- else
- UNW_DEC_SPILL_PSPREL_P(X3, qp, t, abreg, off, arg);
- return dp;
-}
-
-static unsigned char *
-unw_decode_x4 (unsigned char *dp,
- unsigned char code __attribute__((unused)),
- void *arg)
-{
- unsigned char byte1, byte2, byte3, qp, abreg, x, ytreg;
- unw_word t;
-
- byte1 = *dp++; byte2 = *dp++; byte3 = *dp++;
- t = unw_decode_uleb128 (&dp);
-
- qp = (byte1 & 0x3f);
- abreg = (byte2 & 0x7f);
- x = (byte2 >> 7) & 1;
- ytreg = byte3;
-
- if ((byte2 & 0x80) == 0 && byte3 == 0)
- UNW_DEC_RESTORE_P(X4, qp, t, abreg, arg);
- else
- UNW_DEC_SPILL_REG_P(X4, qp, t, abreg, x, ytreg, arg);
- return dp;
-}
-
-static unsigned char *
-unw_decode_r1 (unsigned char *dp, unsigned char code, void *arg)
-{
- int body = (code & 0x20) != 0;
- unw_word rlen;
-
- rlen = (code & 0x1f);
- UNW_DEC_PROLOGUE(R1, body, rlen, arg);
- return dp;
-}
-
-static unsigned char *
-unw_decode_r2 (unsigned char *dp, unsigned char code, void *arg)
-{
- unsigned char byte1, mask, grsave;
- unw_word rlen;
-
- byte1 = *dp++;
-
- mask = ((code & 0x7) << 1) | ((byte1 >> 7) & 1);
- grsave = (byte1 & 0x7f);
- rlen = unw_decode_uleb128 (&dp);
- UNW_DEC_PROLOGUE_GR(R2, rlen, mask, grsave, arg);
- return dp;
-}
-
-static unsigned char *
-unw_decode_r3 (unsigned char *dp, unsigned char code, void *arg)
-{
- unw_word rlen;
-
- rlen = unw_decode_uleb128 (&dp);
- UNW_DEC_PROLOGUE(R3, ((code & 0x3) == 1), rlen, arg);
- return dp;
-}
-
-static unsigned char *
-unw_decode_p1 (unsigned char *dp, unsigned char code, void *arg)
-{
- unsigned char brmask = (code & 0x1f);
-
- UNW_DEC_BR_MEM(P1, brmask, arg);
- return dp;
-}
-
-static unsigned char *
-unw_decode_p2_p5 (unsigned char *dp, unsigned char code, void *arg)
-{
- if ((code & 0x10) == 0)
- {
- unsigned char byte1 = *dp++;
-
- UNW_DEC_BR_GR(P2, ((code & 0xf) << 1) | ((byte1 >> 7) & 1),
- (byte1 & 0x7f), arg);
- }
- else if ((code & 0x08) == 0)
- {
- unsigned char byte1 = *dp++, r, dst;
-
- r = ((code & 0x7) << 1) | ((byte1 >> 7) & 1);
- dst = (byte1 & 0x7f);
- switch (r)
- {
- case 0: UNW_DEC_REG_GR(P3, UNW_REG_PSP, dst, arg); break;
- case 1: UNW_DEC_REG_GR(P3, UNW_REG_RP, dst, arg); break;
- case 2: UNW_DEC_REG_GR(P3, UNW_REG_PFS, dst, arg); break;
- case 3: UNW_DEC_REG_GR(P3, UNW_REG_PR, dst, arg); break;
- case 4: UNW_DEC_REG_GR(P3, UNW_REG_UNAT, dst, arg); break;
- case 5: UNW_DEC_REG_GR(P3, UNW_REG_LC, dst, arg); break;
- case 6: UNW_DEC_RP_BR(P3, dst, arg); break;
- case 7: UNW_DEC_REG_GR(P3, UNW_REG_RNAT, dst, arg); break;
- case 8: UNW_DEC_REG_GR(P3, UNW_REG_BSP, dst, arg); break;
- case 9: UNW_DEC_REG_GR(P3, UNW_REG_BSPSTORE, dst, arg); break;
- case 10: UNW_DEC_REG_GR(P3, UNW_REG_FPSR, dst, arg); break;
- case 11: UNW_DEC_PRIUNAT_GR(P3, dst, arg); break;
- default: UNW_DEC_BAD_CODE(r); break;
- }
- }
- else if ((code & 0x7) == 0)
- UNW_DEC_SPILL_MASK(P4, dp, arg);
- else if ((code & 0x7) == 1)
- {
- unw_word grmask, frmask, byte1, byte2, byte3;
-
- byte1 = *dp++; byte2 = *dp++; byte3 = *dp++;
- grmask = ((byte1 >> 4) & 0xf);
- frmask = ((byte1 & 0xf) << 16) | (byte2 << 8) | byte3;
- UNW_DEC_FRGR_MEM(P5, grmask, frmask, arg);
- }
- else
- UNW_DEC_BAD_CODE(code);
- return dp;
-}
-
-static unsigned char *
-unw_decode_p6 (unsigned char *dp, unsigned char code, void *arg)
-{
- int gregs = (code & 0x10) != 0;
- unsigned char mask = (code & 0x0f);
-
- if (gregs)
- UNW_DEC_GR_MEM(P6, mask, arg);
- else
- UNW_DEC_FR_MEM(P6, mask, arg);
- return dp;
-}
-
-static unsigned char *
-unw_decode_p7_p10 (unsigned char *dp, unsigned char code, void *arg)
-{
- unsigned char r, byte1, byte2;
- unw_word t, size;
-
- if ((code & 0x10) == 0)
- {
- r = (code & 0xf);
- t = unw_decode_uleb128 (&dp);
- switch (r)
- {
- case 0:
- size = unw_decode_uleb128 (&dp);
- UNW_DEC_MEM_STACK_F(P7, t, size, arg);
- break;
-
- case 1: UNW_DEC_MEM_STACK_V(P7, t, arg); break;
- case 2: UNW_DEC_SPILL_BASE(P7, t, arg); break;
- case 3: UNW_DEC_REG_SPREL(P7, UNW_REG_PSP, t, arg); break;
- case 4: UNW_DEC_REG_WHEN(P7, UNW_REG_RP, t, arg); break;
- case 5: UNW_DEC_REG_PSPREL(P7, UNW_REG_RP, t, arg); break;
- case 6: UNW_DEC_REG_WHEN(P7, UNW_REG_PFS, t, arg); break;
- case 7: UNW_DEC_REG_PSPREL(P7, UNW_REG_PFS, t, arg); break;
- case 8: UNW_DEC_REG_WHEN(P7, UNW_REG_PR, t, arg); break;
- case 9: UNW_DEC_REG_PSPREL(P7, UNW_REG_PR, t, arg); break;
- case 10: UNW_DEC_REG_WHEN(P7, UNW_REG_LC, t, arg); break;
- case 11: UNW_DEC_REG_PSPREL(P7, UNW_REG_LC, t, arg); break;
- case 12: UNW_DEC_REG_WHEN(P7, UNW_REG_UNAT, t, arg); break;
- case 13: UNW_DEC_REG_PSPREL(P7, UNW_REG_UNAT, t, arg); break;
- case 14: UNW_DEC_REG_WHEN(P7, UNW_REG_FPSR, t, arg); break;
- case 15: UNW_DEC_REG_PSPREL(P7, UNW_REG_FPSR, t, arg); break;
- default: UNW_DEC_BAD_CODE(r); break;
- }
- }
- else
- {
- switch (code & 0xf)
- {
- case 0x0: /* p8 */
- {
- r = *dp++;
- t = unw_decode_uleb128 (&dp);
- switch (r)
- {
- case 1: UNW_DEC_REG_SPREL(P8, UNW_REG_RP, t, arg); break;
- case 2: UNW_DEC_REG_SPREL(P8, UNW_REG_PFS, t, arg); break;
- case 3: UNW_DEC_REG_SPREL(P8, UNW_REG_PR, t, arg); break;
- case 4: UNW_DEC_REG_SPREL(P8, UNW_REG_LC, t, arg); break;
- case 5: UNW_DEC_REG_SPREL(P8, UNW_REG_UNAT, t, arg); break;
- case 6: UNW_DEC_REG_SPREL(P8, UNW_REG_FPSR, t, arg); break;
- case 7: UNW_DEC_REG_WHEN(P8, UNW_REG_BSP, t, arg); break;
- case 8: UNW_DEC_REG_PSPREL(P8, UNW_REG_BSP, t, arg); break;
- case 9: UNW_DEC_REG_SPREL(P8, UNW_REG_BSP, t, arg); break;
- case 10: UNW_DEC_REG_WHEN(P8, UNW_REG_BSPSTORE, t, arg); break;
- case 11: UNW_DEC_REG_PSPREL(P8, UNW_REG_BSPSTORE, t, arg); break;
- case 12: UNW_DEC_REG_SPREL(P8, UNW_REG_BSPSTORE, t, arg); break;
- case 13: UNW_DEC_REG_WHEN(P8, UNW_REG_RNAT, t, arg); break;
- case 14: UNW_DEC_REG_PSPREL(P8, UNW_REG_RNAT, t, arg); break;
- case 15: UNW_DEC_REG_SPREL(P8, UNW_REG_RNAT, t, arg); break;
- case 16: UNW_DEC_PRIUNAT_WHEN_GR(P8, t, arg); break;
- case 17: UNW_DEC_PRIUNAT_PSPREL(P8, t, arg); break;
- case 18: UNW_DEC_PRIUNAT_SPREL(P8, t, arg); break;
- case 19: UNW_DEC_PRIUNAT_WHEN_MEM(P8, t, arg); break;
- default: UNW_DEC_BAD_CODE(r); break;
- }
- }
- break;
-
- case 0x1:
- byte1 = *dp++; byte2 = *dp++;
- UNW_DEC_GR_GR(P9, (byte1 & 0xf), (byte2 & 0x7f), arg);
- break;
-
- case 0xf: /* p10 */
- byte1 = *dp++; byte2 = *dp++;
- UNW_DEC_ABI(P10, byte1, byte2, arg);
- break;
-
- case 0x9:
- return unw_decode_x1 (dp, code, arg);
-
- case 0xa:
- return unw_decode_x2 (dp, code, arg);
-
- case 0xb:
- return unw_decode_x3 (dp, code, arg);
-
- case 0xc:
- return unw_decode_x4 (dp, code, arg);
-
- default:
- UNW_DEC_BAD_CODE(code);
- break;
- }
- }
- return dp;
-}
-
-static unsigned char *
-unw_decode_b1 (unsigned char *dp, unsigned char code, void *arg)
-{
- unw_word label = (code & 0x1f);
-
- if ((code & 0x20) != 0)
- UNW_DEC_COPY_STATE(B1, label, arg);
- else
- UNW_DEC_LABEL_STATE(B1, label, arg);
- return dp;
-}
-
-static unsigned char *
-unw_decode_b2 (unsigned char *dp, unsigned char code, void *arg)
-{
- unw_word t;
-
- t = unw_decode_uleb128 (&dp);
- UNW_DEC_EPILOGUE(B2, t, (code & 0x1f), arg);
- return dp;
-}
-
-static unsigned char *
-unw_decode_b3_x4 (unsigned char *dp, unsigned char code, void *arg)
-{
- unw_word t, ecount, label;
-
- if ((code & 0x10) == 0)
- {
- t = unw_decode_uleb128 (&dp);
- ecount = unw_decode_uleb128 (&dp);
- UNW_DEC_EPILOGUE(B3, t, ecount, arg);
- }
- else if ((code & 0x07) == 0)
- {
- label = unw_decode_uleb128 (&dp);
- if ((code & 0x08) != 0)
- UNW_DEC_COPY_STATE(B4, label, arg);
- else
- UNW_DEC_LABEL_STATE(B4, label, arg);
- }
- else
- switch (code & 0x7)
- {
- case 1: return unw_decode_x1 (dp, code, arg);
- case 2: return unw_decode_x2 (dp, code, arg);
- case 3: return unw_decode_x3 (dp, code, arg);
- case 4: return unw_decode_x4 (dp, code, arg);
- default: UNW_DEC_BAD_CODE(code); break;
- }
- return dp;
-}
-
-typedef unsigned char *(*unw_decoder) (unsigned char *, unsigned char, void *);
-
-static const unw_decoder unw_decode_table[2][8] =
-{
- /* prologue table: */
- {
- unw_decode_r1, /* 0 */
- unw_decode_r1,
- unw_decode_r2,
- unw_decode_r3,
- unw_decode_p1, /* 4 */
- unw_decode_p2_p5,
- unw_decode_p6,
- unw_decode_p7_p10
- },
- {
- unw_decode_r1, /* 0 */
- unw_decode_r1,
- unw_decode_r2,
- unw_decode_r3,
- unw_decode_b1, /* 4 */
- unw_decode_b1,
- unw_decode_b2,
- unw_decode_b3_x4
- }
-};
-
-/*
- * Decode one descriptor and return address of next descriptor.
- */
-static inline unsigned char *
-unw_decode (unsigned char *dp, int inside_body, void *arg)
-{
- unw_decoder decoder;
- unsigned char code;
-
- code = *dp++;
- decoder = unw_decode_table[inside_body][code >> 5];
- dp = (*decoder) (dp, code, arg);
- return dp;
-}
-
-
-/* RSE helper functions. */
-
-static inline unsigned long
-ia64_rse_slot_num (unsigned long *addr)
-{
- return (((unsigned long) addr) >> 3) & 0x3f;
-}
-
-/* Return TRUE if ADDR is the address of an RNAT slot. */
-static inline unsigned long
-ia64_rse_is_rnat_slot (unsigned long *addr)
-{
- return ia64_rse_slot_num (addr) == 0x3f;
-}
-
-/* Returns the address of the RNAT slot that covers the slot at
- address SLOT_ADDR. */
-static inline unsigned long *
-ia64_rse_rnat_addr (unsigned long *slot_addr)
-{
- return (unsigned long *) ((unsigned long) slot_addr | (0x3f << 3));
-}
-
-/* Calculate the number of registers in the dirty partition starting at
- BSPSTORE with a size of DIRTY bytes. This isn't simply DIRTY
- divided by eight because the 64th slot is used to store ar.rnat. */
-static inline unsigned long
-ia64_rse_num_regs (unsigned long *bspstore, unsigned long *bsp)
-{
- unsigned long slots = (bsp - bspstore);
-
- return slots - (ia64_rse_slot_num (bspstore) + slots)/0x40;
-}
-
-/* The inverse of the above: given bspstore and the number of
- registers, calculate ar.bsp. */
-static inline unsigned long *
-ia64_rse_skip_regs (unsigned long *addr, long num_regs)
-{
- long delta = ia64_rse_slot_num (addr) + num_regs;
-
- if (num_regs < 0)
- delta -= 0x3e;
- return addr + num_regs + delta/0x3f;
-}
-
-
-/* Copy register backing store from SRC to DST, LEN words
- (which include both saved registers and nat collections).
- DST_RNAT is a partial nat collection for DST. SRC and DST
- don't have to be equal modulo 64 slots, so it cannot be
- done with a simple memcpy as the nat collections will be
- at different relative offsets and need to be combined together. */
-static void
-ia64_copy_rbs (struct _Unwind_Context *info, unsigned long dst,
- unsigned long src, long len, unsigned long dst_rnat)
-{
- long count;
- unsigned long src_rnat;
- unsigned long shift1, shift2;
-
- len <<= 3;
- dst_rnat &= (1UL << ((dst >> 3) & 0x3f)) - 1;
- src_rnat = src >= info->regstk_top
- ? info->rnat : *(unsigned long *) (src | 0x1f8);
- src_rnat &= ~((1UL << ((src >> 3) & 0x3f)) - 1);
- /* Just to make sure. */
- src_rnat &= ~(1UL << 63);
- shift1 = ((dst - src) >> 3) & 0x3f;
- if ((dst & 0x1f8) < (src & 0x1f8))
- shift1--;
- shift2 = 0x3f - shift1;
- if ((dst & 0x1f8) >= (src & 0x1f8))
- {
- count = ~dst & 0x1f8;
- goto first;
- }
- count = ~src & 0x1f8;
- goto second;
- while (len > 0)
- {
- src_rnat = src >= info->regstk_top
- ? info->rnat : *(unsigned long *) (src | 0x1f8);
- /* Just to make sure. */
- src_rnat &= ~(1UL << 63);
- count = shift2 << 3;
-first:
- if (count > len)
- count = len;
- memcpy ((char *) dst, (char *) src, count);
- dst += count;
- src += count;
- len -= count;
- dst_rnat |= (src_rnat << shift1) & ~(1UL << 63);
- if (len <= 0)
- break;
- *(long *) dst = dst_rnat;
- dst += 8;
- dst_rnat = 0;
- count = shift1 << 3;
-second:
- if (count > len)
- count = len;
- memcpy ((char *) dst, (char *) src, count);
- dst += count;
- src += count + 8;
- len -= count + 8;
- dst_rnat |= (src_rnat >> shift2);
- }
- if ((dst & 0x1f8) == 0x1f8)
- {
- *(long *) dst = dst_rnat;
- dst += 8;
- dst_rnat = 0;
- }
- /* Set info->regstk_top to lowest rbs address which will use
- info->rnat collection. */
- info->regstk_top = dst & ~0x1ffUL;
- info->rnat = dst_rnat;
-}
-
-/* Unwind accessors. */
-
-static void
-unw_access_gr (struct _Unwind_Context *info, int regnum,
- unsigned long *val, char *nat, int write)
-{
- unsigned long *addr, *nat_addr = 0, nat_mask = 0, dummy_nat;
- struct unw_ireg *ireg;
-
- if ((unsigned) regnum - 1 >= 127)
- abort ();
-
- if (regnum < 1)
- {
- nat_addr = addr = &dummy_nat;
- dummy_nat = 0;
- }
- else if (regnum < 32)
- {
- /* Access a non-stacked register. */
- ireg = &info->ireg[regnum - 2];
- addr = ireg->loc;
- if (addr)
- {
- nat_addr = addr + ireg->nat.off;
- switch (ireg->nat.type)
- {
- case UNW_NAT_VAL:
- /* Simulate getf.sig/setf.sig. */
- if (write)
- {
- if (*nat)
- {
- /* Write NaTVal and be done with it. */
- addr[0] = 0;
- addr[1] = 0x1fffe;
- return;
- }
- addr[1] = 0x1003e;
- }
- else if (addr[0] == 0 && addr[1] == 0x1ffe)
- {
- /* Return NaT and be done with it. */
- *val = 0;
- *nat = 1;
- return;
- }
- /* FALLTHRU */
-
- case UNW_NAT_NONE:
- dummy_nat = 0;
- nat_addr = &dummy_nat;
- break;
-
- case UNW_NAT_MEMSTK:
- nat_mask = 1UL << ((long) addr & 0x1f8)/8;
- break;
-
- case UNW_NAT_REGSTK:
- if ((unsigned long) addr >= info->regstk_top)
- nat_addr = &info->rnat;
- else
- nat_addr = ia64_rse_rnat_addr (addr);
- nat_mask = 1UL << ia64_rse_slot_num (addr);
- break;
- }
- }
- }
- else
- {
- /* Access a stacked register. */
- addr = ia64_rse_skip_regs ((unsigned long *) info->bsp, regnum - 32);
- if ((unsigned long) addr >= info->regstk_top)
- nat_addr = &info->rnat;
- else
- nat_addr = ia64_rse_rnat_addr (addr);
- nat_mask = 1UL << ia64_rse_slot_num (addr);
- }
-
- if (write)
- {
- *addr = *val;
- if (*nat)
- *nat_addr |= nat_mask;
- else
- *nat_addr &= ~nat_mask;
- }
- else
- {
- *val = *addr;
- *nat = (*nat_addr & nat_mask) != 0;
- }
-}
-
-/* Get the value of register REG as saved in CONTEXT. */
-
-_Unwind_Word
-_Unwind_GetGR (struct _Unwind_Context *context, int index)
-{
- _Unwind_Word ret;
- char nat;
-
- if (index == 1)
- return context->gp;
- else if (index >= 15 && index <= 18)
- return context->eh_data[index - 15];
- else
- unw_access_gr (context, index, &ret, &nat, 0);
-
- return ret;
-}
-
-/* Overwrite the saved value for register REG in CONTEXT with VAL. */
-
-void
-_Unwind_SetGR (struct _Unwind_Context *context, int index, _Unwind_Word val)
-{
- char nat = 0;
-
- if (index == 1)
- context->gp = val;
- else if (index >= 15 && index <= 18)
- context->eh_data[index - 15] = val;
- else
- unw_access_gr (context, index, &val, &nat, 1);
-}
-
-/* Retrieve the return address for CONTEXT. */
-
-inline _Unwind_Ptr
-_Unwind_GetIP (struct _Unwind_Context *context)
-{
- return context->rp;
-}
-
-inline _Unwind_Ptr
-_Unwind_GetIPInfo (struct _Unwind_Context *context, int *ip_before_insn)
-{
- *ip_before_insn = 0;
- return context->rp;
-}
-
-/* Overwrite the return address for CONTEXT with VAL. */
-
-inline void
-_Unwind_SetIP (struct _Unwind_Context *context, _Unwind_Ptr val)
-{
- context->rp = val;
-}
-
-void *
-_Unwind_GetLanguageSpecificData (struct _Unwind_Context *context)
-{
- return context->lsda;
-}
-
-_Unwind_Ptr
-_Unwind_GetRegionStart (struct _Unwind_Context *context)
-{
- return context->region_start;
-}
-
-void *
-_Unwind_FindEnclosingFunction (void *pc)
-{
- struct unw_table_entry *entp, ent;
- unsigned long segment_base, gp;
-
- entp = _Unwind_FindTableEntry (pc, &segment_base, &gp, &ent);
- if (entp == NULL)
- return NULL;
- else
- return (void *)(segment_base + entp->start_offset);
-}
-
-/* Get the value of the CFA as saved in CONTEXT. In GCC/Dwarf2 parlance,
- the CFA is the value of the stack pointer on entry; In IA-64 unwind
- parlance, this is the PSP. */
-
-_Unwind_Word
-_Unwind_GetCFA (struct _Unwind_Context *context)
-{
- return (_Unwind_Ptr) context->psp;
-}
-
-/* Get the value of the Backing Store Pointer as saved in CONTEXT. */
-
-_Unwind_Word
-_Unwind_GetBSP (struct _Unwind_Context *context)
-{
- return (_Unwind_Ptr) context->bsp;
-}
-
-#include "md-unwind-support.h"
-
-static _Unwind_Reason_Code
-uw_frame_state_for (struct _Unwind_Context *context, _Unwind_FrameState *fs)
-{
- struct unw_table_entry *entp, ent;
- unsigned long *unw, header, length;
- unsigned char *insn, *insn_end;
- unsigned long segment_base;
- struct unw_reg_info *r;
-
- memset (fs, 0, sizeof (*fs));
- for (r = fs->curr.reg; r < fs->curr.reg + UNW_NUM_REGS; ++r)
- r->when = UNW_WHEN_NEVER;
- context->lsda = 0;
-
- entp = _Unwind_FindTableEntry ((void *) context->rp,
- &segment_base, &context->gp, &ent);
- if (entp == NULL)
- {
- /* Couldn't find unwind info for this function. Try an
- os-specific fallback mechanism. This will necessarily
- not provide a personality routine or LSDA. */
-#ifdef MD_FALLBACK_FRAME_STATE_FOR
- if (MD_FALLBACK_FRAME_STATE_FOR (context, fs) == _URC_NO_REASON)
- return _URC_NO_REASON;
-#endif
-
- /* [SCRA 11.4.1] A leaf function with no memory stack, no exception
- handlers, and which keeps the return value in B0 does not need
- an unwind table entry.
-
- This can only happen in the frame after unwinding through a signal
- handler. Avoid infinite looping by requiring that B0 != RP.
- RP == 0 terminates the chain. */
- if (context->br_loc[0]
- && *context->br_loc[0] != context->rp
- && context->rp != 0)
- goto skip_unwind_info;
-
- return _URC_END_OF_STACK;
- }
-
- context->region_start = entp->start_offset + segment_base;
- fs->when_target = ((context->rp & -16) - context->region_start) / 16 * 3
- + (context->rp & 15);
-
- unw = (unsigned long *) (entp->info_offset + segment_base);
- header = *unw;
- length = UNW_LENGTH (header);
-
- /* Some operating systems use the personality routine slot in way not
- compatible with what we expect. For instance, OpenVMS uses this slot to
- designate "condition handlers" with very different arguments than what we
- would be providing. Such cases are typically identified from OS specific
- bits in the unwind information block header, and checked by the target
- MD_UNW_COMPATIBLE_PERSONALITY_P macro.
-
- We just pretend there is no personality from our standpoint in such
- situations, and expect GCC not to set the identifying bits itself so that
- compatible personalities for GCC compiled code are called.
-
- Of course, this raises the question of what combinations of native/GCC
- calls can be expected to behave properly exception handling-wise. We are
- not to provide a magic answer here, merely to prevent crashes assuming
- users know what they are doing.
-
- ??? Perhaps check UNW_VER / UNW_FLAG_OSMASK as well. */
-
- if (MD_UNW_COMPATIBLE_PERSONALITY_P (header)
- && (UNW_FLAG_EHANDLER (header) | UNW_FLAG_UHANDLER (header)))
- {
- fs->personality =
- *(_Unwind_Personality_Fn *) (unw[length + 1] + context->gp);
- context->lsda = unw + length + 2;
- }
-
- insn = (unsigned char *) (unw + 1);
- insn_end = (unsigned char *) (unw + 1 + length);
- while (!fs->done && insn < insn_end)
- insn = unw_decode (insn, fs->in_body, fs);
-
- free_label_states (fs->labeled_states);
- free_state_stack (&fs->curr);
-
-#ifdef ENABLE_MALLOC_CHECKING
- if (reg_state_alloced || labeled_state_alloced)
- abort ();
-#endif
-
- /* If we're in the epilogue, sp has been restored and all values
- on the memory stack below psp also have been restored. */
- if (fs->when_target > fs->epilogue_start)
- {
- struct unw_reg_info *r;
-
- fs->curr.reg[UNW_REG_PSP].where = UNW_WHERE_NONE;
- fs->curr.reg[UNW_REG_PSP].val = 0;
- for (r = fs->curr.reg; r < fs->curr.reg + UNW_NUM_REGS; ++r)
- if ((r->where == UNW_WHERE_PSPREL && r->val <= 0x10)
- || r->where == UNW_WHERE_SPREL)
- r->where = UNW_WHERE_NONE;
- }
-
-skip_unwind_info:
- /* If RP didn't get saved, generate entry for the return link register. */
- if (fs->curr.reg[UNW_REG_RP].when >= fs->when_target)
- {
- fs->curr.reg[UNW_REG_RP].where = UNW_WHERE_BR;
- fs->curr.reg[UNW_REG_RP].when = -1;
- fs->curr.reg[UNW_REG_RP].val = fs->return_link_reg;
- }
-
- /* There is a subtlety for the frame after unwinding through a signal
- handler: should we restore the cfm as usual or the pfs? We can't
- restore both because we use br.ret to resume execution of user code.
- For other frames the procedure is by definition non-leaf so the pfs
- is saved and restored and thus effectively dead in the body; only
- the cfm need therefore be restored.
-
- Here we have 2 cases:
- - either the pfs is saved and restored and thus effectively dead
- like in regular frames; then we do nothing special and restore
- the cfm.
- - or the pfs is not saved and thus live; but in that case the
- procedure is necessarily leaf so the cfm is effectively dead
- and we restore the pfs. */
- if (context->signal_pfs_loc)
- {
- if (fs->curr.reg[UNW_REG_PFS].when >= fs->when_target)
- context->pfs_loc = context->signal_pfs_loc;
- context->signal_pfs_loc = NULL;
- }
-
- return _URC_NO_REASON;
-}
-
-static void
-uw_update_reg_address (struct _Unwind_Context *context,
- _Unwind_FrameState *fs,
- enum unw_register_index regno)
-{
- struct unw_reg_info *r = fs->curr.reg + regno;
- void *addr;
- unsigned long rval;
-
- if (r->where == UNW_WHERE_NONE || r->when >= fs->when_target)
- return;
-
- rval = r->val;
- switch (r->where)
- {
- case UNW_WHERE_GR:
- if (rval >= 32)
- addr = ia64_rse_skip_regs ((unsigned long *) context->bsp, rval - 32);
- else if (rval >= 2)
- addr = context->ireg[rval - 2].loc;
- else if (rval == 0)
- {
- static const unsigned long dummy;
- addr = (void *) &dummy;
- }
- else
- abort ();
- break;
-
- case UNW_WHERE_FR:
- if (rval >= 2 && rval < 32)
- addr = context->fr_loc[rval - 2];
- else
- abort ();
- break;
-
- case UNW_WHERE_BR:
- /* Note that while RVAL can only be 1-5 from normal descriptors,
- we can want to look at B0, B6 and B7 due to having manually unwound a
- signal frame. */
- if (rval < 8)
- addr = context->br_loc[rval];
- else
- abort ();
- break;
-
- case UNW_WHERE_SPREL:
- addr = (void *)(context->sp + rval);
- break;
-
- case UNW_WHERE_PSPREL:
- addr = (void *)(context->psp + rval);
- break;
-
- default:
- abort ();
- }
-
- switch (regno)
- {
- case UNW_REG_R2 ... UNW_REG_R31:
- context->ireg[regno - UNW_REG_R2].loc = addr;
- switch (r->where)
- {
- case UNW_WHERE_GR:
- if (rval >= 32)
- {
- context->ireg[regno - UNW_REG_R2].nat.type = UNW_NAT_MEMSTK;
- context->ireg[regno - UNW_REG_R2].nat.off
- = context->pri_unat_loc - (unsigned long *) addr;
- }
- else if (rval >= 2)
- {
- context->ireg[regno - UNW_REG_R2].nat
- = context->ireg[rval - 2].nat;
- }
- else if (rval == 0)
- {
- context->ireg[regno - UNW_REG_R2].nat.type = UNW_NAT_NONE;
- context->ireg[regno - UNW_REG_R2].nat.off = 0;
- }
- else
- abort ();
- break;
-
- case UNW_WHERE_FR:
- context->ireg[regno - UNW_REG_R2].nat.type = UNW_NAT_VAL;
- context->ireg[regno - UNW_REG_R2].nat.off = 0;
- break;
-
- case UNW_WHERE_BR:
- context->ireg[regno - UNW_REG_R2].nat.type = UNW_NAT_NONE;
- context->ireg[regno - UNW_REG_R2].nat.off = 0;
- break;
-
- case UNW_WHERE_PSPREL:
- case UNW_WHERE_SPREL:
- context->ireg[regno - UNW_REG_R2].nat.type = UNW_NAT_MEMSTK;
- context->ireg[regno - UNW_REG_R2].nat.off
- = context->pri_unat_loc - (unsigned long *) addr;
- break;
-
- default:
- abort ();
- }
- break;
-
- case UNW_REG_F2 ... UNW_REG_F31:
- context->fr_loc[regno - UNW_REG_F2] = addr;
- break;
-
- case UNW_REG_B1 ... UNW_REG_B5:
- context->br_loc[regno - UNW_REG_B0] = addr;
- break;
-
- case UNW_REG_BSP:
- context->bsp_loc = addr;
- break;
- case UNW_REG_BSPSTORE:
- context->bspstore_loc = addr;
- break;
- case UNW_REG_PFS:
- context->pfs_loc = addr;
- break;
- case UNW_REG_RP:
- context->rp = *(unsigned long *)addr;
- break;
- case UNW_REG_UNAT:
- context->unat_loc = addr;
- break;
- case UNW_REG_PR:
- context->pr = *(unsigned long *) addr;
- break;
- case UNW_REG_LC:
- context->lc_loc = addr;
- break;
- case UNW_REG_FPSR:
- context->fpsr_loc = addr;
- break;
-
- case UNW_REG_PSP:
- context->psp = *(unsigned long *)addr;
- break;
-
- default:
- abort ();
- }
-}
-
-static void
-uw_update_context (struct _Unwind_Context *context, _Unwind_FrameState *fs)
-{
- long i;
-
-#ifdef MD_HANDLE_UNWABI
- MD_HANDLE_UNWABI (context, fs);
-#endif
-
- context->sp = context->psp;
-
- /* First, set PSP. Subsequent instructions may depend on this value. */
- if (fs->when_target > fs->curr.reg[UNW_REG_PSP].when)
- {
- if (fs->curr.reg[UNW_REG_PSP].where == UNW_WHERE_NONE)
- context->psp = context->psp + fs->curr.reg[UNW_REG_PSP].val;
- else
- uw_update_reg_address (context, fs, UNW_REG_PSP);
- }
-
- /* Determine the location of the primary UNaT. */
- {
- int i;
- if (fs->when_target < fs->curr.reg[UNW_REG_PRI_UNAT_GR].when)
- i = UNW_REG_PRI_UNAT_MEM;
- else if (fs->when_target < fs->curr.reg[UNW_REG_PRI_UNAT_MEM].when)
- i = UNW_REG_PRI_UNAT_GR;
- else if (fs->curr.reg[UNW_REG_PRI_UNAT_MEM].when
- > fs->curr.reg[UNW_REG_PRI_UNAT_GR].when)
- i = UNW_REG_PRI_UNAT_MEM;
- else
- i = UNW_REG_PRI_UNAT_GR;
- uw_update_reg_address (context, fs, i);
- }
-
- /* Compute the addresses of all registers saved in this frame. */
- for (i = UNW_REG_BSP; i < UNW_NUM_REGS; ++i)
- uw_update_reg_address (context, fs, i);
-
- /* Unwind BSP for the local registers allocated this frame. */
- /* ??? What to do with stored BSP or BSPSTORE registers. */
- /* We assert that we are either at a call site, or we have
- just unwound through a signal frame. In either case
- pfs_loc is valid. */
- if (!(fs -> no_reg_stack_frame))
- {
- unsigned long pfs = *context->pfs_loc;
- unsigned long sol = (pfs >> 7) & 0x7f;
- context->bsp = (unsigned long)
- ia64_rse_skip_regs ((unsigned long *) context->bsp, -sol);
- }
-}
-
-static void
-uw_advance_context (struct _Unwind_Context *context, _Unwind_FrameState *fs)
-{
- uw_update_context (context, fs);
-}
-
-/* Fill in CONTEXT for top-of-stack. The only valid registers at this
- level will be the return address and the CFA. Note that CFA = SP+16. */
-
-#define uw_init_context(CONTEXT) \
- do { \
- /* ??? There is a whole lot o code in uw_install_context that \
- tries to avoid spilling the entire machine state here. We \
- should try to make that work again. */ \
- __builtin_unwind_init(); \
- uw_init_context_1 (CONTEXT, __builtin_ia64_bsp ()); \
- } while (0)
-
-static void __attribute__((noinline))
-uw_init_context_1 (struct _Unwind_Context *context, void *bsp)
-{
- void *rp = __builtin_extract_return_addr (__builtin_return_address (0));
- /* Set psp to the caller's stack pointer. */
- void *psp = __builtin_dwarf_cfa () - 16;
- _Unwind_FrameState fs;
- unsigned long rnat, tmp1, tmp2;
-
- /* Flush the register stack to memory so that we can access it.
- Get rse nat collection for the last incomplete rbs chunk of
- registers at the same time. For this RSE needs to be turned
- into the mandatory only mode. */
- asm ("mov.m %1 = ar.rsc;;\n\t"
- "and %2 = 0x1c, %1;;\n\t"
- "mov.m ar.rsc = %2;;\n\t"
- "flushrs;;\n\t"
- "mov.m %0 = ar.rnat;;\n\t"
- "mov.m ar.rsc = %1\n\t"
- : "=r" (rnat), "=r" (tmp1), "=r" (tmp2));
-
- memset (context, 0, sizeof (struct _Unwind_Context));
- context->bsp = (unsigned long) bsp;
- /* Set context->regstk_top to lowest rbs address which will use
- context->rnat collection. */
- context->regstk_top = context->bsp & ~0x1ffULL;
- context->rnat = rnat;
- context->psp = (unsigned long) psp;
- context->rp = (unsigned long) rp;
- asm ("mov %0 = sp" : "=r" (context->sp));
- asm ("mov %0 = pr" : "=r" (context->pr));
- context->pri_unat_loc = &context->initial_unat; /* ??? */
-
- if (uw_frame_state_for (context, &fs) != _URC_NO_REASON)
- abort ();
-
- uw_update_context (context, &fs);
-}
-
-/* Install (i.e. longjmp to) the contents of TARGET. */
-
-static void __attribute__((noreturn))
-uw_install_context (struct _Unwind_Context *current __attribute__((unused)),
- struct _Unwind_Context *target)
-{
- unsigned long ireg_buf[4], ireg_nat = 0, ireg_pr = 0;
- long i;
-
- /* Copy integer register data from the target context to a
- temporary buffer. Do this so that we can frob AR.UNAT
- to get the NaT bits for these registers set properly. */
- for (i = 4; i <= 7; ++i)
- {
- char nat;
- void *t = target->ireg[i - 2].loc;
- if (t)
- {
- unw_access_gr (target, i, &ireg_buf[i - 4], &nat, 0);
- ireg_nat |= (long)nat << (((size_t)&ireg_buf[i - 4] >> 3) & 0x3f);
- /* Set p6 - p9. */
- ireg_pr |= 4L << i;
- }
- }
-
- /* The value in uc_bsp that we've computed is that for the
- target function. The value that we install below will be
- adjusted by the BR.RET instruction based on the contents
- of AR.PFS. So we must unadjust that here. */
- target->bsp = (unsigned long)
- ia64_rse_skip_regs ((unsigned long *)target->bsp,
- (*target->pfs_loc >> 7) & 0x7f);
-
- if (target->bsp < target->regstk_top)
- target->rnat = *ia64_rse_rnat_addr ((unsigned long *) target->bsp);
-
- /* Provide assembly with the offsets into the _Unwind_Context. */
- asm volatile ("uc_rnat = %0"
- : : "i"(offsetof (struct _Unwind_Context, rnat)));
- asm volatile ("uc_bsp = %0"
- : : "i"(offsetof (struct _Unwind_Context, bsp)));
- asm volatile ("uc_psp = %0"
- : : "i"(offsetof (struct _Unwind_Context, psp)));
- asm volatile ("uc_rp = %0"
- : : "i"(offsetof (struct _Unwind_Context, rp)));
- asm volatile ("uc_pr = %0"
- : : "i"(offsetof (struct _Unwind_Context, pr)));
- asm volatile ("uc_gp = %0"
- : : "i"(offsetof (struct _Unwind_Context, gp)));
- asm volatile ("uc_pfs_loc = %0"
- : : "i"(offsetof (struct _Unwind_Context, pfs_loc)));
- asm volatile ("uc_unat_loc = %0"
- : : "i"(offsetof (struct _Unwind_Context, unat_loc)));
- asm volatile ("uc_lc_loc = %0"
- : : "i"(offsetof (struct _Unwind_Context, lc_loc)));
- asm volatile ("uc_fpsr_loc = %0"
- : : "i"(offsetof (struct _Unwind_Context, fpsr_loc)));
- asm volatile ("uc_eh_data = %0"
- : : "i"(offsetof (struct _Unwind_Context, eh_data)));
- asm volatile ("uc_br_loc = %0"
- : : "i"(offsetof (struct _Unwind_Context, br_loc)));
- asm volatile ("uc_fr_loc = %0"
- : : "i"(offsetof (struct _Unwind_Context, fr_loc)));
-
- asm volatile (
- /* Load up call-saved non-window integer registers from ireg_buf. */
- "add r20 = 8, %1 \n\t"
- "mov ar.unat = %2 \n\t"
- "mov pr = %3, 0x3c0 \n\t"
- ";; \n\t"
- "(p6) ld8.fill r4 = [%1] \n\t"
- "(p7) ld8.fill r5 = [r20] \n\t"
- "add r21 = uc_br_loc + 16, %0 \n\t"
- "adds %1 = 16, %1 \n\t"
- "adds r20 = 16, r20 \n\t"
- ";; \n\t"
- "(p8) ld8.fill r6 = [%1] \n\t"
- "(p9) ld8.fill r7 = [r20] \n\t"
- "add r20 = uc_br_loc + 8, %0 \n\t"
- ";; \n\t"
- /* Load up call-saved branch registers. */
- "ld8 r22 = [r20], 16 \n\t"
- "ld8 r23 = [r21], 16 \n\t"
- ";; \n\t"
- "ld8 r24 = [r20], 16 \n\t"
- "ld8 r25 = [r21], uc_fr_loc - (uc_br_loc + 32)\n\t"
- ";; \n\t"
- "ld8 r26 = [r20], uc_fr_loc + 8 - (uc_br_loc + 40)\n\t"
- "ld8 r27 = [r21], 24 \n\t"
- "cmp.ne p6, p0 = r0, r22 \n\t"
- ";; \n\t"
- "ld8 r28 = [r20], 8 \n\t"
- "(p6) ld8 r22 = [r22] \n\t"
- "cmp.ne p7, p0 = r0, r23 \n\t"
- ";; \n\t"
- "(p7) ld8 r23 = [r23] \n\t"
- "cmp.ne p8, p0 = r0, r24 \n\t"
- ";; \n\t"
- "(p8) ld8 r24 = [r24] \n\t"
- "(p6) mov b1 = r22 \n\t"
- "cmp.ne p9, p0 = r0, r25 \n\t"
- ";; \n\t"
- "(p9) ld8 r25 = [r25] \n\t"
- "(p7) mov b2 = r23 \n\t"
- "cmp.ne p6, p0 = r0, r26 \n\t"
- ";; \n\t"
- "(p6) ld8 r26 = [r26] \n\t"
- "(p8) mov b3 = r24 \n\t"
- "cmp.ne p7, p0 = r0, r27 \n\t"
- ";; \n\t"
- /* Load up call-saved fp registers. */
- "(p7) ldf.fill f2 = [r27] \n\t"
- "(p9) mov b4 = r25 \n\t"
- "cmp.ne p8, p0 = r0, r28 \n\t"
- ";; \n\t"
- "(p8) ldf.fill f3 = [r28] \n\t"
- "(p6) mov b5 = r26 \n\t"
- ";; \n\t"
- "ld8 r29 = [r20], 16*8 - 4*8 \n\t"
- "ld8 r30 = [r21], 17*8 - 5*8 \n\t"
- ";; \n\t"
- "ld8 r22 = [r20], 16 \n\t"
- "ld8 r23 = [r21], 16 \n\t"
- ";; \n\t"
- "ld8 r24 = [r20], 16 \n\t"
- "ld8 r25 = [r21] \n\t"
- "cmp.ne p6, p0 = r0, r29 \n\t"
- ";; \n\t"
- "ld8 r26 = [r20], 8 \n\t"
- "(p6) ldf.fill f4 = [r29] \n\t"
- "cmp.ne p7, p0 = r0, r30 \n\t"
- ";; \n\t"
- "ld8 r27 = [r20], 8 \n\t"
- "(p7) ldf.fill f5 = [r30] \n\t"
- "cmp.ne p6, p0 = r0, r22 \n\t"
- ";; \n\t"
- "ld8 r28 = [r20], 8 \n\t"
- "(p6) ldf.fill f16 = [r22] \n\t"
- "cmp.ne p7, p0 = r0, r23 \n\t"
- ";; \n\t"
- "ld8 r29 = [r20], 8 \n\t"
- "(p7) ldf.fill f17 = [r23] \n\t"
- "cmp.ne p6, p0 = r0, r24 \n\t"
- ";; \n\t"
- "ld8 r22 = [r20], 8 \n\t"
- "(p6) ldf.fill f18 = [r24] \n\t"
- "cmp.ne p7, p0 = r0, r25 \n\t"
- ";; \n\t"
- "ld8 r23 = [r20], 8 \n\t"
- "(p7) ldf.fill f19 = [r25] \n\t"
- "cmp.ne p6, p0 = r0, r26 \n\t"
- ";; \n\t"
- "ld8 r24 = [r20], 8 \n\t"
- "(p6) ldf.fill f20 = [r26] \n\t"
- "cmp.ne p7, p0 = r0, r27 \n\t"
- ";; \n\t"
- "ld8 r25 = [r20], 8 \n\t"
- "(p7) ldf.fill f21 = [r27] \n\t"
- "cmp.ne p6, p0 = r0, r28 \n\t"
- ";; \n\t"
- "ld8 r26 = [r20], 8 \n\t"
- "(p6) ldf.fill f22 = [r28] \n\t"
- "cmp.ne p7, p0 = r0, r29 \n\t"
- ";; \n\t"
- "ld8 r27 = [r20], 8 \n\t"
- ";; \n\t"
- "ld8 r28 = [r20], 8 \n\t"
- "(p7) ldf.fill f23 = [r29] \n\t"
- "cmp.ne p6, p0 = r0, r22 \n\t"
- ";; \n\t"
- "ld8 r29 = [r20], 8 \n\t"
- "(p6) ldf.fill f24 = [r22] \n\t"
- "cmp.ne p7, p0 = r0, r23 \n\t"
- ";; \n\t"
- "(p7) ldf.fill f25 = [r23] \n\t"
- "cmp.ne p6, p0 = r0, r24 \n\t"
- "cmp.ne p7, p0 = r0, r25 \n\t"
- ";; \n\t"
- "(p6) ldf.fill f26 = [r24] \n\t"
- "(p7) ldf.fill f27 = [r25] \n\t"
- "cmp.ne p6, p0 = r0, r26 \n\t"
- ";; \n\t"
- "(p6) ldf.fill f28 = [r26] \n\t"
- "cmp.ne p7, p0 = r0, r27 \n\t"
- "cmp.ne p6, p0 = r0, r28 \n\t"
- ";; \n\t"
- "(p7) ldf.fill f29 = [r27] \n\t"
- "(p6) ldf.fill f30 = [r28] \n\t"
- "cmp.ne p7, p0 = r0, r29 \n\t"
- ";; \n\t"
- "(p7) ldf.fill f31 = [r29] \n\t"
- "add r20 = uc_rnat, %0 \n\t"
- "add r21 = uc_bsp, %0 \n\t"
- ";; \n\t"
- /* Load the balance of the thread state from the context. */
- "ld8 r22 = [r20], uc_psp - uc_rnat \n\t"
- "ld8 r23 = [r21], uc_gp - uc_bsp \n\t"
- ";; \n\t"
- "ld8 r24 = [r20], uc_pfs_loc - uc_psp \n\t"
- "ld8 r1 = [r21], uc_rp - uc_gp \n\t"
- ";; \n\t"
- "ld8 r25 = [r20], uc_unat_loc - uc_pfs_loc\n\t"
- "ld8 r26 = [r21], uc_pr - uc_rp \n\t"
- ";; \n\t"
- "ld8 r27 = [r20], uc_lc_loc - uc_unat_loc\n\t"
- "ld8 r28 = [r21], uc_fpsr_loc - uc_pr \n\t"
- ";; \n\t"
- "ld8 r29 = [r20], uc_eh_data - uc_lc_loc\n\t"
- "ld8 r30 = [r21], uc_eh_data + 8 - uc_fpsr_loc\n\t"
- ";; \n\t"
- /* Load data for the exception handler. */
- "ld8 r15 = [r20], 16 \n\t"
- "ld8 r16 = [r21], 16 \n\t"
- ";; \n\t"
- "ld8 r17 = [r20] \n\t"
- "ld8 r18 = [r21] \n\t"
- ";; \n\t"
- /* Install the balance of the thread state loaded above. */
- "cmp.ne p6, p0 = r0, r25 \n\t"
- "cmp.ne p7, p0 = r0, r27 \n\t"
- ";; \n\t"
- "(p6) ld8 r25 = [r25] \n\t"
- "(p7) ld8 r27 = [r27] \n\t"
- ";; \n\t"
- "(p7) mov.m ar.unat = r27 \n\t"
- "(p6) mov.i ar.pfs = r25 \n\t"
- "cmp.ne p9, p0 = r0, r29 \n\t"
- ";; \n\t"
- "(p9) ld8 r29 = [r29] \n\t"
- "cmp.ne p6, p0 = r0, r30 \n\t"
- ";; \n\t"
- "(p6) ld8 r30 = [r30] \n\t"
- /* Don't clobber p6-p9, which are in use at present. */
- "mov pr = r28, ~0x3c0 \n\t"
- "(p9) mov.i ar.lc = r29 \n\t"
- ";; \n\t"
- "mov.m r25 = ar.rsc \n\t"
- "(p6) mov.m ar.fpsr = r30 \n\t"
- ";; \n\t"
- "and r29 = 0x1c, r25 \n\t"
- "mov b0 = r26 \n\t"
- ";; \n\t"
- "mov.m ar.rsc = r29 \n\t"
- ";; \n\t"
- /* This must be done before setting AR.BSPSTORE, otherwise
- AR.BSP will be initialized with a random displacement
- below the value we want, based on the current number of
- dirty stacked registers. */
- "loadrs \n\t"
- "invala \n\t"
- ";; \n\t"
- "mov.m ar.bspstore = r23 \n\t"
- ";; \n\t"
- "mov.m ar.rnat = r22 \n\t"
- ";; \n\t"
- "mov.m ar.rsc = r25 \n\t"
- "mov sp = r24 \n\t"
- "br.ret.sptk.few b0"
- : : "r"(target), "r"(ireg_buf), "r"(ireg_nat), "r"(ireg_pr)
- : "r15", "r16", "r17", "r18", "r20", "r21", "r22",
- "r23", "r24", "r25", "r26", "r27", "r28", "r29",
- "r30", "r31");
- /* NOTREACHED */
- while (1);
-}
-
-static inline _Unwind_Ptr
-uw_identify_context (struct _Unwind_Context *context)
-{
- return _Unwind_GetIP (context);
-}
-
-#include "unwind.inc"
-
-#if defined (USE_GAS_SYMVER) && defined (SHARED) && defined (USE_LIBUNWIND_EXCEPTIONS)
-alias (_Unwind_Backtrace);
-alias (_Unwind_DeleteException);
-alias (_Unwind_FindEnclosingFunction);
-alias (_Unwind_ForcedUnwind);
-alias (_Unwind_GetBSP);
-alias (_Unwind_GetCFA);
-alias (_Unwind_GetGR);
-alias (_Unwind_GetIP);
-alias (_Unwind_GetLanguageSpecificData);
-alias (_Unwind_GetRegionStart);
-alias (_Unwind_RaiseException);
-alias (_Unwind_Resume);
-alias (_Unwind_Resume_or_Rethrow);
-alias (_Unwind_SetGR);
-alias (_Unwind_SetIP);
-#endif
-
-#endif
diff --git a/gcc/config/ia64/unwind-ia64.h b/gcc/config/ia64/unwind-ia64.h
deleted file mode 100644
index b98f048..0000000
--- a/gcc/config/ia64/unwind-ia64.h
+++ /dev/null
@@ -1,43 +0,0 @@
-/* Copyright (C) 1999, 2000, 2001, 2007, 2009 Free Software Foundation, Inc.
- Contributed by Andrew MacLeod <amacleod@cygnus.com>
- Andrew Haley <aph@cygnus.com>
-
- This file is part of GCC.
-
- GCC is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 3, or (at your option)
- any later version.
-
- GCC 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 General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with GCC; see the file COPYING3. If not see
- <http://www.gnu.org/licenses/>. */
-
-struct unw_table_entry
-{
- unsigned long start_offset;
- unsigned long end_offset;
- unsigned long info_offset;
-};
-
-/* Accessors to fields of an unwind info block header. In this common file to
- be visible from all the units involved in a target implementation. */
-
-#ifndef __USING_SJLJ_EXCEPTIONS__
-#define UNW_VER(x) ((x) >> 48)
-#define UNW_FLAG_MASK 0x0000ffff00000000
-#define UNW_FLAG_OSMASK 0x0000f00000000000
-#define UNW_FLAG_EHANDLER(x) ((x) & 0x0000000100000000L)
-#define UNW_FLAG_UHANDLER(x) ((x) & 0x0000000200000000L)
-#define UNW_LENGTH(x) ((x) & 0x00000000ffffffffL)
-#endif
-
-extern struct unw_table_entry *
-_Unwind_FindTableEntry (void *pc, unsigned long *segment_base,
- unsigned long *gp, struct unw_table_entry *ent)
- __attribute__ ((__visibility__ ("hidden")));
diff --git a/gcc/config/ia64/vms.h b/gcc/config/ia64/vms.h
index 847d79a..853e023 100644
--- a/gcc/config/ia64/vms.h
+++ b/gcc/config/ia64/vms.h
@@ -139,9 +139,6 @@ STATIC func_ptr __CTOR_LIST__[1] \
/* Define this to be nonzero if static stack checking is supported. */
#define STACK_CHECK_STATIC_BUILTIN 1
-#define UNW_IVMS_MODE(HEADER) (((HEADER) >> 44) & 0x3L)
-#define MD_UNW_COMPATIBLE_PERSONALITY_P(HEADER) (!UNW_IVMS_MODE (HEADER))
-
/* Minimum amount of stack required to recover from an anticipated stack
overflow detection. The default value conveys an estimate of the amount
of stack required to propagate an exception. */
diff --git a/gcc/config/picochip/t-picochip b/gcc/config/picochip/t-picochip
index ba4394e..4df74a0 100644
--- a/gcc/config/picochip/t-picochip
+++ b/gcc/config/picochip/t-picochip
@@ -43,9 +43,6 @@ LIB2FUNCS_EXTRA = \
LIB1ASMFUNCS = _mulsc3 _divsc3
LIB1ASMSRC = picochip/libgccExtras/fake_libgcc.asm
-# Turn off the building of exception handling libraries.
-LIB2ADDEH =
-
# Turn off ranlib on target libraries.
RANLIB_FOR_TARGET = cat
diff --git a/gcc/config/rs6000/aix.h b/gcc/config/rs6000/aix.h
index 13d317f..2c678a3 100644
--- a/gcc/config/rs6000/aix.h
+++ b/gcc/config/rs6000/aix.h
@@ -209,40 +209,6 @@
/* And similarly for general purpose registers. */
#define GP_SAVE_INLINE(FIRST_REG) ((FIRST_REG) < 32)
-/* If the current unwind info (FS) does not contain explicit info
- saving R2, then we have to do a minor amount of code reading to
- figure out if it was saved. The big problem here is that the
- code that does the save/restore is generated by the linker, so
- we have no good way to determine at compile time what to do. */
-
-#define R_LR 65
-
-#ifdef __64BIT__
-#define MD_FROB_UPDATE_CONTEXT(CTX, FS) \
- do { \
- if ((FS)->regs.reg[2].how == REG_UNSAVED) \
- { \
- unsigned int *insn \
- = (unsigned int *) \
- _Unwind_GetGR ((CTX), R_LR); \
- if (*insn == 0xE8410028) \
- _Unwind_SetGRPtr ((CTX), 2, (CTX)->cfa + 40); \
- } \
- } while (0)
-#else
-#define MD_FROB_UPDATE_CONTEXT(CTX, FS) \
- do { \
- if ((FS)->regs.reg[2].how == REG_UNSAVED) \
- { \
- unsigned int *insn \
- = (unsigned int *) \
- _Unwind_GetGR ((CTX), R_LR); \
- if (*insn == 0x80410014) \
- _Unwind_SetGRPtr ((CTX), 2, (CTX)->cfa + 20); \
- } \
- } while (0)
-#endif
-
#define PROFILE_HOOK(LABEL) output_profile_hook (LABEL)
/* No version of AIX fully supports AltiVec or 64-bit instructions in
diff --git a/gcc/config/rs6000/darwin-fallback.c b/gcc/config/rs6000/darwin-fallback.c
deleted file mode 100644
index 4591071..0000000
--- a/gcc/config/rs6000/darwin-fallback.c
+++ /dev/null
@@ -1,487 +0,0 @@
-/* Fallback frame-state unwinder for Darwin.
- Copyright (C) 2004, 2005, 2007, 2009 Free Software Foundation, Inc.
-
- This file is part of GCC.
-
- GCC is free software; you can redistribute it and/or modify it
- under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 3, or (at your option)
- any later version.
-
- GCC 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 General Public
- License for more details.
-
- Under Section 7 of GPL version 3, you are granted additional
- permissions described in the GCC Runtime Library Exception, version
- 3.1, as published by the Free Software Foundation.
-
- You should have received a copy of the GNU General Public License and
- a copy of the GCC Runtime Library Exception along with this program;
- see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
- <http://www.gnu.org/licenses/>. */
-
-#ifdef __ppc__
-
-#include "tconfig.h"
-#include "tsystem.h"
-#include "coretypes.h"
-#include "tm.h"
-#include "dwarf2.h"
-#include "unwind.h"
-#include "unwind-dw2.h"
-#include <stdint.h>
-#include <stdbool.h>
-#include <sys/types.h>
-#include <signal.h>
-
-#define R_LR 65
-#define R_CTR 66
-#define R_CR2 70
-#define R_XER 76
-#define R_VR0 77
-#define R_VRSAVE 109
-#define R_VSCR 110
-#define R_SPEFSCR 112
-
-typedef unsigned long reg_unit;
-
-/* Place in GPRS the parameters to the first 'sc' instruction that would
- have been executed if we were returning from this CONTEXT, or
- return false if an unexpected instruction is encountered. */
-
-static bool
-interpret_libc (reg_unit gprs[32], struct _Unwind_Context *context)
-{
- uint32_t *pc = (uint32_t *)_Unwind_GetIP (context);
- uint32_t cr;
- reg_unit lr = (reg_unit) pc;
- reg_unit ctr = 0;
- uint32_t *invalid_address = NULL;
-
- int i;
-
- for (i = 0; i < 13; i++)
- gprs[i] = 1;
- gprs[1] = _Unwind_GetCFA (context);
- for (; i < 32; i++)
- gprs[i] = _Unwind_GetGR (context, i);
- cr = _Unwind_GetGR (context, R_CR2);
-
- /* For each supported Libc, we have to track the code flow
- all the way back into the kernel.
-
- This code is believed to support all released Libc/Libsystem builds since
- Jaguar 6C115, including all the security updates. To be precise,
-
- Libc Libsystem Build(s)
- 262~1 60~37 6C115
- 262~1 60.2~4 6D52
- 262~1 61~3 6F21-6F22
- 262~1 63~24 6G30-6G37
- 262~1 63~32 6I34-6I35
- 262~1 63~64 6L29-6L60
- 262.4.1~1 63~84 6L123-6R172
-
- 320~1 71~101 7B85-7D28
- 320~1 71~266 7F54-7F56
- 320~1 71~288 7F112
- 320~1 71~289 7F113
- 320.1.3~1 71.1.1~29 7H60-7H105
- 320.1.3~1 71.1.1~30 7H110-7H113
- 320.1.3~1 71.1.1~31 7H114
-
- That's a big table! It would be insane to try to keep track of
- every little detail, so we just read the code itself and do what
- it would do.
- */
-
- for (;;)
- {
- uint32_t ins = *pc++;
-
- if ((ins & 0xFC000003) == 0x48000000) /* b instruction */
- {
- pc += ((((int32_t) ins & 0x3FFFFFC) ^ 0x2000000) - 0x2000004) / 4;
- continue;
- }
- if ((ins & 0xFC600000) == 0x2C000000) /* cmpwi */
- {
- int32_t val1 = (int16_t) ins;
- int32_t val2 = gprs[ins >> 16 & 0x1F];
- /* Only beq and bne instructions are supported, so we only
- need to set the EQ bit. */
- uint32_t mask = 0xF << ((ins >> 21 & 0x1C) ^ 0x1C);
- if (val1 == val2)
- cr |= mask;
- else
- cr &= ~mask;
- continue;
- }
- if ((ins & 0xFEC38003) == 0x40820000) /* forwards beq/bne */
- {
- if ((cr >> ((ins >> 16 & 0x1F) ^ 0x1F) & 1) == (ins >> 24 & 1))
- pc += (ins & 0x7FFC) / 4 - 1;
- continue;
- }
- if ((ins & 0xFC0007FF) == 0x7C000378) /* or, including mr */
- {
- gprs [ins >> 16 & 0x1F] = (gprs [ins >> 11 & 0x1F]
- | gprs [ins >> 21 & 0x1F]);
- continue;
- }
- if (ins >> 26 == 0x0E) /* addi, including li */
- {
- reg_unit src = (ins >> 16 & 0x1F) == 0 ? 0 : gprs [ins >> 16 & 0x1F];
- gprs [ins >> 21 & 0x1F] = src + (int16_t) ins;
- continue;
- }
- if (ins >> 26 == 0x0F) /* addis, including lis */
- {
- reg_unit src = (ins >> 16 & 0x1F) == 0 ? 0 : gprs [ins >> 16 & 0x1F];
- gprs [ins >> 21 & 0x1F] = src + ((int16_t) ins << 16);
- continue;
- }
- if (ins >> 26 == 0x20) /* lwz */
- {
- reg_unit src = (ins >> 16 & 0x1F) == 0 ? 0 : gprs [ins >> 16 & 0x1F];
- uint32_t *p = (uint32_t *)(src + (int16_t) ins);
- if (p == invalid_address)
- return false;
- gprs [ins >> 21 & 0x1F] = *p;
- continue;
- }
- if (ins >> 26 == 0x21) /* lwzu */
- {
- uint32_t *p = (uint32_t *)(gprs [ins >> 16 & 0x1F] += (int16_t) ins);
- if (p == invalid_address)
- return false;
- gprs [ins >> 21 & 0x1F] = *p;
- continue;
- }
- if (ins >> 26 == 0x24) /* stw */
- /* What we hope this is doing is '--in_sigtramp'. We don't want
- to actually store to memory, so just make a note of the
- address and refuse to load from it. */
- {
- reg_unit src = (ins >> 16 & 0x1F) == 0 ? 0 : gprs [ins >> 16 & 0x1F];
- uint32_t *p = (uint32_t *)(src + (int16_t) ins);
- if (p == NULL || invalid_address != NULL)
- return false;
- invalid_address = p;
- continue;
- }
- if (ins >> 26 == 0x2E) /* lmw */
- {
- reg_unit src = (ins >> 16 & 0x1F) == 0 ? 0 : gprs [ins >> 16 & 0x1F];
- uint32_t *p = (uint32_t *)(src + (int16_t) ins);
- int i;
-
- for (i = (ins >> 21 & 0x1F); i < 32; i++)
- {
- if (p == invalid_address)
- return false;
- gprs[i] = *p++;
- }
- continue;
- }
- if ((ins & 0xFC1FFFFF) == 0x7c0803a6) /* mtlr */
- {
- lr = gprs [ins >> 21 & 0x1F];
- continue;
- }
- if ((ins & 0xFC1FFFFF) == 0x7c0802a6) /* mflr */
- {
- gprs [ins >> 21 & 0x1F] = lr;
- continue;
- }
- if ((ins & 0xFC1FFFFF) == 0x7c0903a6) /* mtctr */
- {
- ctr = gprs [ins >> 21 & 0x1F];
- continue;
- }
- /* The PowerPC User's Manual says that bit 11 of the mtcrf
- instruction is reserved and should be set to zero, but it
- looks like the Darwin assembler doesn't do that... */
- if ((ins & 0xFC000FFF) == 0x7c000120) /* mtcrf */
- {
- int i;
- uint32_t mask = 0;
- for (i = 0; i < 8; i++)
- mask |= ((-(ins >> (12 + i) & 1)) & 0xF) << 4 * i;
- cr = (cr & ~mask) | (gprs [ins >> 21 & 0x1F] & mask);
- continue;
- }
- if (ins == 0x429f0005) /* bcl- 20,4*cr7+so,.+4, loads pc into LR */
- {
- lr = (reg_unit) pc;
- continue;
- }
- if (ins == 0x4e800420) /* bctr */
- {
- pc = (uint32_t *) ctr;
- continue;
- }
- if (ins == 0x44000002) /* sc */
- return true;
-
- return false;
- }
-}
-
-/* We used to include <ucontext.h> and <mach/thread_status.h>,
- but they change so much between different Darwin system versions
- that it's much easier to just write the structures involved here
- directly. */
-
-/* These defines are from the kernel's bsd/dev/ppc/unix_signal.c. */
-#define UC_TRAD 1
-#define UC_TRAD_VEC 6
-#define UC_TRAD64 20
-#define UC_TRAD64_VEC 25
-#define UC_FLAVOR 30
-#define UC_FLAVOR_VEC 35
-#define UC_FLAVOR64 40
-#define UC_FLAVOR64_VEC 45
-#define UC_DUAL 50
-#define UC_DUAL_VEC 55
-
-struct gcc_ucontext
-{
- int onstack;
- sigset_t sigmask;
- void * stack_sp;
- size_t stack_sz;
- int stack_flags;
- struct gcc_ucontext *link;
- size_t mcsize;
- struct gcc_mcontext32 *mcontext;
-};
-
-struct gcc_float_vector_state
-{
- double fpregs[32];
- uint32_t fpscr_pad;
- uint32_t fpscr;
- uint32_t save_vr[32][4];
- uint32_t save_vscr[4];
-};
-
-struct gcc_mcontext32 {
- uint32_t dar;
- uint32_t dsisr;
- uint32_t exception;
- uint32_t padding1[5];
- uint32_t srr0;
- uint32_t srr1;
- uint32_t gpr[32];
- uint32_t cr;
- uint32_t xer;
- uint32_t lr;
- uint32_t ctr;
- uint32_t mq;
- uint32_t vrsave;
- struct gcc_float_vector_state fvs;
-};
-
-/* These are based on /usr/include/ppc/ucontext.h and
- /usr/include/mach/ppc/thread_status.h, but rewritten to be more
- convenient, to compile on Jaguar, and to work around Radar 3712064
- on Panther, which is that the 'es' field of 'struct mcontext64' has
- the wrong type (doh!). */
-
-struct gcc_mcontext64 {
- uint64_t dar;
- uint32_t dsisr;
- uint32_t exception;
- uint32_t padding1[4];
- uint64_t srr0;
- uint64_t srr1;
- uint32_t gpr[32][2];
- uint32_t cr;
- uint32_t xer[2]; /* These are arrays because the original structure has them misaligned. */
- uint32_t lr[2];
- uint32_t ctr[2];
- uint32_t vrsave;
- struct gcc_float_vector_state fvs;
-};
-
-#define UC_FLAVOR_SIZE \
- (sizeof (struct gcc_mcontext32) - 33*16)
-
-#define UC_FLAVOR_VEC_SIZE (sizeof (struct gcc_mcontext32))
-
-#define UC_FLAVOR64_SIZE \
- (sizeof (struct gcc_mcontext64) - 33*16)
-
-#define UC_FLAVOR64_VEC_SIZE (sizeof (struct gcc_mcontext64))
-
-/* Given GPRS as input to a 'sc' instruction, and OLD_CFA, update FS
- to represent the execution of a signal return; or, if not a signal
- return, return false. */
-
-static bool
-handle_syscall (_Unwind_FrameState *fs, const reg_unit gprs[32],
- _Unwind_Ptr old_cfa)
-{
- struct gcc_ucontext *uctx;
- bool is_64, is_vector;
- struct gcc_float_vector_state * float_vector_state;
- _Unwind_Ptr new_cfa;
- int i;
- static _Unwind_Ptr return_addr;
-
- /* Yay! We're in a Libc that we understand, and it's made a
- system call. In Jaguar, this is a direct system call with value 103;
- in Panther and Tiger it is a SYS_syscall call for system call number 184,
- and in Leopard it is a direct syscall with number 184. */
-
- if (gprs[0] == 0x67 /* SYS_SIGRETURN */)
- {
- uctx = (struct gcc_ucontext *) gprs[3];
- is_vector = (uctx->mcsize == UC_FLAVOR64_VEC_SIZE
- || uctx->mcsize == UC_FLAVOR_VEC_SIZE);
- is_64 = (uctx->mcsize == UC_FLAVOR64_VEC_SIZE
- || uctx->mcsize == UC_FLAVOR64_SIZE);
- }
- else if (gprs[0] == 0 /* SYS_syscall */ && gprs[3] == 184)
- {
- int ctxstyle = gprs[5];
- uctx = (struct gcc_ucontext *) gprs[4];
- is_vector = (ctxstyle == UC_FLAVOR_VEC || ctxstyle == UC_FLAVOR64_VEC
- || ctxstyle == UC_TRAD_VEC || ctxstyle == UC_TRAD64_VEC);
- is_64 = (ctxstyle == UC_FLAVOR64_VEC || ctxstyle == UC_TRAD64_VEC
- || ctxstyle == UC_FLAVOR64 || ctxstyle == UC_TRAD64);
- }
- else if (gprs[0] == 184 /* SYS_sigreturn */)
- {
- int ctxstyle = gprs[4];
- uctx = (struct gcc_ucontext *) gprs[3];
- is_vector = (ctxstyle == UC_FLAVOR_VEC || ctxstyle == UC_FLAVOR64_VEC
- || ctxstyle == UC_TRAD_VEC || ctxstyle == UC_TRAD64_VEC);
- is_64 = (ctxstyle == UC_FLAVOR64_VEC || ctxstyle == UC_TRAD64_VEC
- || ctxstyle == UC_FLAVOR64 || ctxstyle == UC_TRAD64);
- }
- else
- return false;
-
-#define set_offset(r, addr) \
- (fs->regs.reg[r].how = REG_SAVED_OFFSET, \
- fs->regs.reg[r].loc.offset = (_Unwind_Ptr)(addr) - new_cfa)
-
- /* Restore even the registers that are not call-saved, since they
- might be being used in the prologue to save other registers,
- for instance GPR0 is sometimes used to save LR. */
-
- /* Handle the GPRs, and produce the information needed to do the rest. */
- if (is_64)
- {
- /* The context is 64-bit, but it doesn't carry any extra information
- for us because only the low 32 bits of the registers are
- call-saved. */
- struct gcc_mcontext64 *m64 = (struct gcc_mcontext64 *)uctx->mcontext;
- int i;
-
- float_vector_state = &m64->fvs;
-
- new_cfa = m64->gpr[1][1];
-
- set_offset (R_CR2, &m64->cr);
- for (i = 0; i < 32; i++)
- set_offset (i, m64->gpr[i] + 1);
- set_offset (R_XER, m64->xer + 1);
- set_offset (R_LR, m64->lr + 1);
- set_offset (R_CTR, m64->ctr + 1);
- if (is_vector)
- set_offset (R_VRSAVE, &m64->vrsave);
-
- /* Sometimes, srr0 points to the instruction that caused the exception,
- and sometimes to the next instruction to be executed; we want
- the latter. */
- if (m64->exception == 3 || m64->exception == 4
- || m64->exception == 6
- || (m64->exception == 7 && !(m64->srr1 & 0x10000)))
- return_addr = m64->srr0 + 4;
- else
- return_addr = m64->srr0;
- }
- else
- {
- struct gcc_mcontext32 *m = uctx->mcontext;
- int i;
-
- float_vector_state = &m->fvs;
-
- new_cfa = m->gpr[1];
-
- set_offset (R_CR2, &m->cr);
- for (i = 0; i < 32; i++)
- set_offset (i, m->gpr + i);
- set_offset (R_XER, &m->xer);
- set_offset (R_LR, &m->lr);
- set_offset (R_CTR, &m->ctr);
-
- if (is_vector)
- set_offset (R_VRSAVE, &m->vrsave);
-
- /* Sometimes, srr0 points to the instruction that caused the exception,
- and sometimes to the next instruction to be executed; we want
- the latter. */
- if (m->exception == 3 || m->exception == 4
- || m->exception == 6
- || (m->exception == 7 && !(m->srr1 & 0x10000)))
- return_addr = m->srr0 + 4;
- else
- return_addr = m->srr0;
- }
-
- fs->regs.cfa_how = CFA_REG_OFFSET;
- fs->regs.cfa_reg = STACK_POINTER_REGNUM;
- fs->regs.cfa_offset = new_cfa - old_cfa;;
-
- /* The choice of column for the return address is somewhat tricky.
- Fortunately, the actual choice is private to this file, and
- the space it's reserved from is the GCC register space, not the
- DWARF2 numbering. So any free element of the right size is an OK
- choice. Thus: */
- fs->retaddr_column = ARG_POINTER_REGNUM;
- /* FIXME: this should really be done using a DWARF2 location expression,
- not using a static variable. In fact, this entire file should
- be implemented in DWARF2 expressions. */
- set_offset (ARG_POINTER_REGNUM, &return_addr);
-
- for (i = 0; i < 32; i++)
- set_offset (32 + i, float_vector_state->fpregs + i);
- set_offset (R_SPEFSCR, &float_vector_state->fpscr);
-
- if (is_vector)
- {
- for (i = 0; i < 32; i++)
- set_offset (R_VR0 + i, float_vector_state->save_vr + i);
- set_offset (R_VSCR, float_vector_state->save_vscr);
- }
-
- return true;
-}
-
-/* This is also prototyped in rs6000/darwin.h, inside the
- MD_FALLBACK_FRAME_STATE_FOR macro. */
-extern bool _Unwind_fallback_frame_state_for (struct _Unwind_Context *context,
- _Unwind_FrameState *fs);
-
-/* Implement the MD_FALLBACK_FRAME_STATE_FOR macro,
- returning true iff the frame was a sigreturn() frame that we
- can understand. */
-
-bool
-_Unwind_fallback_frame_state_for (struct _Unwind_Context *context,
- _Unwind_FrameState *fs)
-{
- reg_unit gprs[32];
-
- if (!interpret_libc (gprs, context))
- return false;
- return handle_syscall (fs, gprs, _Unwind_GetCFA (context));
-}
-#endif
diff --git a/gcc/config/rs6000/t-darwin b/gcc/config/rs6000/t-darwin
index 8113b9e..27fc07b 100644
--- a/gcc/config/rs6000/t-darwin
+++ b/gcc/config/rs6000/t-darwin
@@ -1,5 +1,5 @@
# Copyright (C) 2001, 2002, 2003, 2004, 2005, 2006,
-# 2007 Free Software Foundation, Inc.
+# 2007, 2011 Free Software Foundation, Inc.
#
# This file is part of GCC.
#
@@ -40,7 +40,5 @@ TARGET_LIBGCC2_CFLAGS = -Wa,-force_cpusubtype_ALL -pipe -mmacosx-version-min=10.
# Export the _xlq* symbols from darwin-ldouble.c.
SHLIB_MAPFILES += $(srcdir)/config/rs6000/libgcc-ppc64.ver
-LIB2ADDEH += $(srcdir)/config/rs6000/darwin-fallback.c
-
darwin-fpsave.o: $(srcdir)/config/rs6000/darwin-asm.h
darwin-tramp.o: $(srcdir)/config/rs6000/darwin-asm.h
diff --git a/gcc/config/sh/t-sh b/gcc/config/sh/t-sh
index a897bff..27cbd3d 100644
--- a/gcc/config/sh/t-sh
+++ b/gcc/config/sh/t-sh
@@ -1,5 +1,5 @@
# Copyright (C) 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
-# 2003, 2004, 2006, 2008, 2009 Free Software Foundation, Inc.
+# 2003, 2004, 2006, 2008, 2009, 2011 Free Software Foundation, Inc.
#
# This file is part of GCC.
#
@@ -149,7 +149,7 @@ $(T)sdivsi3_i4i-Os-4-200.o: $(srcdir)/config/sh/lib1funcs-Os-4-200.asm $(GCC_PAS
$(GCC_FOR_TARGET) $(MULTILIB_CFLAGS) -c -o $@ -DL_sdivsi3_i4i -x assembler-with-cpp $<
$(T)udivsi3_i4i-Os-4-200.o: $(srcdir)/config/sh/lib1funcs-Os-4-200.asm $(GCC_PASSES)
$(GCC_FOR_TARGET) $(MULTILIB_CFLAGS) -c -o $@ -DL_udivsi3_i4i -x assembler-with-cpp $<
-$(T)unwind-dw2-Os-4-200.o: $(srcdir)/unwind-dw2.c $(srcdir)/unwind-generic.h unwind-pe.h unwind.inc unwind-dw2-fde.h unwind-dw2.h $(CONFIG_H) coretypes.h $(TM_H) $(MACHMODE_H) longlong.h config.status stmp-int-hdrs tsystem.h $(GCC_PASSES)
+$(T)unwind-dw2-Os-4-200.o: $(srcdir)/../libgcc/unwind-dw2.c $(srcdir)/../libgcc/unwind-generic.h $(srcdir)/../libgcc/unwind-pe.h $(srcdir)/../libgcc/unwind.inc $(srcdir)/../libgcc/unwind-dw2-fde.h $(srcdir)/../libgcc/unwind-dw2.h $(CONFIG_H) coretypes.h $(TM_H) $(MACHMODE_H) longlong.h config.status stmp-int-hdrs tsystem.h $(GCC_PASSES)
$(GCC_FOR_TARGET) $(MULTILIB_CFLAGS) $(LIBGCC2_CFLAGS) $(INCLUDES) $(vis_hide) -fexceptions -Os -c -o $@ $<
OBJS_Os_4_200=$(T)sdivsi3_i4i-Os-4-200.o $(T)udivsi3_i4i-Os-4-200.o $(T)unwind-dw2-Os-4-200.o
$(T)libgcc-Os-4-200.a: $(OBJS_Os_4_200) $(GCC_PASSES)
diff --git a/gcc/config/spu/t-spu-elf b/gcc/config/spu/t-spu-elf
index 5189f28..ab680f5 100644
--- a/gcc/config/spu/t-spu-elf
+++ b/gcc/config/spu/t-spu-elf
@@ -47,9 +47,6 @@ LIB2FUNCS_STATIC_EXTRA = $(srcdir)/config/spu/float_unssidf.c \
$(srcdir)/config/spu/divmodti4.c \
$(srcdir)/config/spu/divv2df3.c
-LIB2ADDEH = $(srcdir)/unwind-dw2.c $(srcdir)/unwind-dw2-fde.c \
- $(srcdir)/unwind-sjlj.c $(srcdir)/unwind-c.c
-
# We want fine grained libraries, so use the new code to build the
# floating point emulation libraries.
FPBIT = fp-bit.c
diff --git a/gcc/config/t-darwin b/gcc/config/t-darwin
index 9e77395..d952bd3 100644
--- a/gcc/config/t-darwin
+++ b/gcc/config/t-darwin
@@ -42,10 +42,6 @@ darwin-driver.o: $(srcdir)/config/darwin-driver.c \
$(COMPILER) -c $(ALL_COMPILERFLAGS) $(ALL_CPPFLAGS) $(INCLUDES) \
$(srcdir)/config/darwin-driver.c
-# Use unwind-dw2-fde-darwin
-LIB2ADDEH = $(srcdir)/unwind-dw2.c $(srcdir)/unwind-dw2-fde-darwin.c \
- $(srcdir)/unwind-sjlj.c $(srcdir)/unwind-c.c
-
# -pipe because there's an assembler bug, 4077127, which causes
# it to not properly process the first # directive, causing temporary
# file names to appear in stabs, causing the bootstrap to fail. Using -pipe
diff --git a/gcc/config/t-freebsd b/gcc/config/t-freebsd
index af2df24..0680618 100644
--- a/gcc/config/t-freebsd
+++ b/gcc/config/t-freebsd
@@ -3,7 +3,3 @@ CRTSTUFF_T_CFLAGS_S = $(CRTSTUFF_T_CFLAGS) -fPIC
# Compile libgcc.a with pic.
TARGET_LIBGCC2_CFLAGS += -fPIC
-
-# Use unwind-dw2-fde-glibc
-LIB2ADDEH = $(srcdir)/unwind-dw2.c $(srcdir)/unwind-dw2-fde-glibc.c \
- $(srcdir)/unwind-sjlj.c $(srcdir)/unwind-c.c
diff --git a/gcc/config/t-libunwind b/gcc/config/t-libunwind
index 6fdaf67..6b8d2dd 100644
--- a/gcc/config/t-libunwind
+++ b/gcc/config/t-libunwind
@@ -1,4 +1,4 @@
-# Copyright (C) 2002, 2003, 2004 Free Software Foundation, Inc.
+# Copyright (C) 2002, 2003, 2004, 2011 Free Software Foundation, Inc.
#
# This file is part of GCC.
#
@@ -22,9 +22,6 @@
# so that the resulting libgcc_s.so has the necessary DT_NEEDED entry for
# libunwind.
SHLIB_LC = -lunwind -lc
-LIB2ADDEH = $(srcdir)/unwind-sjlj.c $(srcdir)/unwind-c.c \
- $(srcdir)/unwind-compat.c $(srcdir)/unwind-dw2-fde-compat.c
-LIB2ADDEHSTATIC = $(srcdir)/unwind-sjlj.c $(srcdir)/unwind-c.c
T_CFLAGS += -DUSE_LIBUNWIND_EXCEPTIONS
TARGET_LIBGCC2_CFLAGS += -DUSE_GAS_SYMVER
diff --git a/gcc/config/t-libunwind-elf b/gcc/config/t-libunwind-elf
deleted file mode 100644
index 5ae0d62..0000000
--- a/gcc/config/t-libunwind-elf
+++ /dev/null
@@ -1,49 +0,0 @@
-# Copyright (C) 2004, 2005 Free Software Foundation, Inc.
-#
-# This file is part of GCC.
-#
-# GCC is free software; you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation; either version 3, or (at your option)
-# any later version.
-#
-# GCC 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 General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with GCC; see the file COPYING3. If not see
-# <http://www.gnu.org/licenses/>.
-
-# Build libunwind for ELF with the GNU linker.
-
-# Use unwind-dw2-fde-glibc
-LIBUNWIND = $(srcdir)/unwind-dw2.c $(srcdir)/unwind-dw2-fde-glibc.c
-LIBUNWINDDEP = unwind.inc unwind-dw2-fde.h unwind-dw2-fde.c
-
-SHLIBUNWIND_SOVERSION = 7
-SHLIBUNWIND_SONAME = @shlib_base_name@.so.$(SHLIBUNWIND_SOVERSION)
-
-SHLIBUNWIND_LINK = $(GCC_FOR_TARGET) $(LIBGCC2_CFLAGS) -shared \
- -nodefaultlibs -Wl,-h,$(SHLIBUNWIND_SONAME) \
- -Wl,-z,text -Wl,-z,defs -o $(SHLIB_DIR)/$(SHLIBUNWIND_SONAME).tmp \
- @multilib_flags@ $(SHLIB_OBJS) -lc && \
- rm -f $(SHLIB_DIR)/$(SHLIB_SOLINK) && \
- if [ -f $(SHLIB_DIR)/$(SHLIBUNWIND_SONAME) ]; then \
- mv -f $(SHLIB_DIR)/$(SHLIBUNWIND_SONAME) \
- $(SHLIB_DIR)/$(SHLIBUNWIND_SONAME).backup; \
- else true; fi && \
- mv $(SHLIB_DIR)/$(SHLIBUNWIND_SONAME).tmp \
- $(SHLIB_DIR)/$(SHLIBUNWIND_SONAME) && \
- $(LN_S) $(SHLIBUNWIND_SONAME) $(SHLIB_DIR)/$(SHLIB_SOLINK)
-
-# $(slibdir) double quoted to protect it from expansion while building
-# libgcc.mk. We want this delayed until actual install time.
-SHLIBUNWIND_INSTALL = \
- $$(SHELL) $$(srcdir)/mkinstalldirs $$(DESTDIR)$$(slibdir)$(SHLIB_SLIBDIR_QUAL); \
- $(INSTALL_DATA) $(SHLIB_DIR)/$(SHLIBUNWIND_SONAME) \
- $$(DESTDIR)$$(slibdir)$(SHLIB_SLIBDIR_QUAL)/$(SHLIBUNWIND_SONAME); \
- rm -f $$(DESTDIR)$$(slibdir)$(SHLIB_SLIBDIR_QUAL)/$(SHLIB_SOLINK); \
- $(LN_S) $(SHLIBUNWIND_SONAME) \
- $$(DESTDIR)$$(slibdir)$(SHLIB_SLIBDIR_QUAL)/$(SHLIB_SOLINK)
diff --git a/gcc/config/t-linux b/gcc/config/t-linux
index 039fa27..64d19ca 100644
--- a/gcc/config/t-linux
+++ b/gcc/config/t-linux
@@ -25,7 +25,3 @@ TARGET_LIBGCC2_CFLAGS = -fPIC
# Override t-slibgcc-elf-ver to export some libgcc symbols with
# the symbol versions that glibc used.
SHLIB_MAPFILES += $(srcdir)/config/libgcc-glibc.ver
-
-# Use unwind-dw2-fde-glibc
-LIB2ADDEH = $(srcdir)/unwind-dw2.c $(srcdir)/unwind-dw2-fde-glibc.c \
- $(srcdir)/unwind-sjlj.c $(srcdir)/unwind-c.c
diff --git a/gcc/config/t-sol2 b/gcc/config/t-sol2
index 73fd8eb..f53da4d 100644
--- a/gcc/config/t-sol2
+++ b/gcc/config/t-sol2
@@ -31,8 +31,3 @@ sol2.o: $(srcdir)/config/sol2.c $(CONFIG_H) $(SYSTEM_H) coretypes.h \
# This is required by gcc/ada/gcc-interface/Makefile.in.
TARGET_LIBGCC2_CFLAGS = -fPIC
-
-# Use unwind-dw2-fde-glibc.c. Unless linker support and dl_iterate_phdr
-# are present, automatically falls back to unwind-dw2-fde.c.
-LIB2ADDEH = $(srcdir)/unwind-dw2.c $(srcdir)/unwind-dw2-fde-glibc.c \
- $(srcdir)/unwind-sjlj.c $(srcdir)/unwind-c.c
diff --git a/gcc/config/xtensa/t-xtensa b/gcc/config/xtensa/t-xtensa
index c3d98ae..641e6fe 100644
--- a/gcc/config/xtensa/t-xtensa
+++ b/gcc/config/xtensa/t-xtensa
@@ -1,4 +1,5 @@
-# Copyright (C) 2002, 2003, 2006, 2007, 2008 Free Software Foundation, Inc.
+# Copyright (C) 2002, 2003, 2006, 2007, 2008, 2011
+# Free Software Foundation, Inc.
#
# This file is part of GCC.
#
@@ -29,8 +30,6 @@ LIB1ASMFUNCS = _mulsi3 _divsi3 _modsi3 _udivsi3 _umodsi3 \
_truncdfsf2 _extendsfdf2
LIB2FUNCS_EXTRA = $(srcdir)/config/xtensa/lib2funcs.S
-LIB2ADDEH = $(srcdir)/config/xtensa/unwind-dw2-xtensa.c \
- $(srcdir)/unwind-dw2-fde.c $(srcdir)/unwind-sjlj.c $(srcdir)/unwind-c.c
$(T)crti.o: $(srcdir)/config/xtensa/crti.asm $(GCC_PASSES)
$(GCC_FOR_TARGET) $(GCC_CFLAGS) $(MULTILIB_CFLAGS) $(INCLUDES) \
diff --git a/gcc/config/xtensa/unwind-dw2-xtensa.c b/gcc/config/xtensa/unwind-dw2-xtensa.c
deleted file mode 100644
index 54daf76..0000000
--- a/gcc/config/xtensa/unwind-dw2-xtensa.c
+++ /dev/null
@@ -1,544 +0,0 @@
-/* DWARF2 exception handling and frame unwinding for Xtensa.
- Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006,
- 2007, 2008, 2009, 2011
- Free Software Foundation, Inc.
-
- This file is part of GCC.
-
- GCC is free software; you can redistribute it and/or modify it
- under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 3, or (at your option)
- any later version.
-
- GCC 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 General Public
- License for more details.
-
- Under Section 7 of GPL version 3, you are granted additional
- permissions described in the GCC Runtime Library Exception, version
- 3.1, as published by the Free Software Foundation.
-
- You should have received a copy of the GNU General Public License and
- a copy of the GCC Runtime Library Exception along with this program;
- see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
- <http://www.gnu.org/licenses/>. */
-
-#include "tconfig.h"
-#include "tsystem.h"
-#include "coretypes.h"
-#include "tm.h"
-#include "dwarf2.h"
-#include "unwind.h"
-#ifdef __USING_SJLJ_EXCEPTIONS__
-# define NO_SIZE_OF_ENCODED_VALUE
-#endif
-#include "unwind-pe.h"
-#include "unwind-dw2-fde.h"
-#include "unwind-dw2-xtensa.h"
-
-#ifndef __USING_SJLJ_EXCEPTIONS__
-
-/* The standard CIE and FDE structures work fine for Xtensa but the
- variable-size register window save areas are not a good fit for the rest
- of the standard DWARF unwinding mechanism. Nor is that mechanism
- necessary, since the register save areas are always in fixed locations
- in each stack frame. This file is a stripped down and customized version
- of the standard DWARF unwinding code. It needs to be customized to have
- builtin logic for finding the save areas and also to track the stack
- pointer value (besides the CFA) while unwinding since the primary save
- area is located below the stack pointer. It is stripped down to reduce
- code size and ease the maintenance burden of tracking changes in the
- standard version of the code. */
-
-#ifndef DWARF_REG_TO_UNWIND_COLUMN
-#define DWARF_REG_TO_UNWIND_COLUMN(REGNO) (REGNO)
-#endif
-
-#define XTENSA_RA_FIELD_MASK 0x3FFFFFFF
-
-/* This is the register and unwind state for a particular frame. This
- provides the information necessary to unwind up past a frame and return
- to its caller. */
-struct _Unwind_Context
-{
- /* Track register window save areas of 4 registers each, instead of
- keeping separate addresses for the individual registers. */
- _Unwind_Word *reg[4];
-
- void *cfa;
- void *sp;
- void *ra;
-
- /* Cache the 2 high bits to replace the window size in return addresses. */
- _Unwind_Word ra_high_bits;
-
- void *lsda;
- struct dwarf_eh_bases bases;
- /* Signal frame context. */
-#define SIGNAL_FRAME_BIT ((~(_Unwind_Word) 0 >> 1) + 1)
- _Unwind_Word flags;
- /* 0 for now, can be increased when further fields are added to
- struct _Unwind_Context. */
- _Unwind_Word version;
-};
-
-
-/* Read unaligned data from the instruction buffer. */
-
-union unaligned
-{
- void *p;
-} __attribute__ ((packed));
-
-static void uw_update_context (struct _Unwind_Context *, _Unwind_FrameState *);
-static _Unwind_Reason_Code uw_frame_state_for (struct _Unwind_Context *,
- _Unwind_FrameState *);
-
-static inline void *
-read_pointer (const void *p) { const union unaligned *up = p; return up->p; }
-
-static inline _Unwind_Word
-_Unwind_IsSignalFrame (struct _Unwind_Context *context)
-{
- return (context->flags & SIGNAL_FRAME_BIT) ? 1 : 0;
-}
-
-static inline void
-_Unwind_SetSignalFrame (struct _Unwind_Context *context, int val)
-{
- if (val)
- context->flags |= SIGNAL_FRAME_BIT;
- else
- context->flags &= ~SIGNAL_FRAME_BIT;
-}
-
-/* Get the value of register INDEX as saved in CONTEXT. */
-
-inline _Unwind_Word
-_Unwind_GetGR (struct _Unwind_Context *context, int index)
-{
- _Unwind_Word *ptr;
-
- index = DWARF_REG_TO_UNWIND_COLUMN (index);
- ptr = context->reg[index >> 2] + (index & 3);
-
- return *ptr;
-}
-
-/* Get the value of the CFA as saved in CONTEXT. */
-
-_Unwind_Word
-_Unwind_GetCFA (struct _Unwind_Context *context)
-{
- return (_Unwind_Ptr) context->cfa;
-}
-
-/* Overwrite the saved value for register INDEX in CONTEXT with VAL. */
-
-inline void
-_Unwind_SetGR (struct _Unwind_Context *context, int index, _Unwind_Word val)
-{
- _Unwind_Word *ptr;
-
- index = DWARF_REG_TO_UNWIND_COLUMN (index);
- ptr = context->reg[index >> 2] + (index & 3);
-
- *ptr = val;
-}
-
-/* Retrieve the return address for CONTEXT. */
-
-inline _Unwind_Ptr
-_Unwind_GetIP (struct _Unwind_Context *context)
-{
- return (_Unwind_Ptr) context->ra;
-}
-
-/* Retrieve the return address and flag whether that IP is before
- or after first not yet fully executed instruction. */
-
-inline _Unwind_Ptr
-_Unwind_GetIPInfo (struct _Unwind_Context *context, int *ip_before_insn)
-{
- *ip_before_insn = _Unwind_IsSignalFrame (context);
- return (_Unwind_Ptr) context->ra;
-}
-
-/* Overwrite the return address for CONTEXT with VAL. */
-
-inline void
-_Unwind_SetIP (struct _Unwind_Context *context, _Unwind_Ptr val)
-{
- context->ra = (void *) val;
-}
-
-void *
-_Unwind_GetLanguageSpecificData (struct _Unwind_Context *context)
-{
- return context->lsda;
-}
-
-_Unwind_Ptr
-_Unwind_GetRegionStart (struct _Unwind_Context *context)
-{
- return (_Unwind_Ptr) context->bases.func;
-}
-
-void *
-_Unwind_FindEnclosingFunction (void *pc)
-{
- struct dwarf_eh_bases bases;
- const struct dwarf_fde *fde = _Unwind_Find_FDE (pc-1, &bases);
- if (fde)
- return bases.func;
- else
- return NULL;
-}
-
-_Unwind_Ptr
-_Unwind_GetDataRelBase (struct _Unwind_Context *context)
-{
- return (_Unwind_Ptr) context->bases.dbase;
-}
-
-_Unwind_Ptr
-_Unwind_GetTextRelBase (struct _Unwind_Context *context)
-{
- return (_Unwind_Ptr) context->bases.tbase;
-}
-
-#include "md-unwind-support.h"
-
-/* Extract any interesting information from the CIE for the translation
- unit F belongs to. Return a pointer to the byte after the augmentation,
- or NULL if we encountered an undecipherable augmentation. */
-
-static const unsigned char *
-extract_cie_info (const struct dwarf_cie *cie, struct _Unwind_Context *context,
- _Unwind_FrameState *fs)
-{
- const unsigned char *aug = cie->augmentation;
- const unsigned char *p = aug + strlen ((const char *)aug) + 1;
- const unsigned char *ret = NULL;
- _uleb128_t utmp;
- _sleb128_t stmp;
-
- /* g++ v2 "eh" has pointer immediately following augmentation string,
- so it must be handled first. */
- if (aug[0] == 'e' && aug[1] == 'h')
- {
- fs->eh_ptr = read_pointer (p);
- p += sizeof (void *);
- aug += 2;
- }
-
- /* Immediately following the augmentation are the code and
- data alignment and return address column. */
- p = read_uleb128 (p, &utmp);
- p = read_sleb128 (p, &stmp);
- if (cie->version == 1)
- fs->retaddr_column = *p++;
- else
- {
- p = read_uleb128 (p, &utmp);
- fs->retaddr_column = (_Unwind_Word)utmp;
- }
- fs->lsda_encoding = DW_EH_PE_omit;
-
- /* If the augmentation starts with 'z', then a uleb128 immediately
- follows containing the length of the augmentation field following
- the size. */
- if (*aug == 'z')
- {
- p = read_uleb128 (p, &utmp);
- ret = p + utmp;
-
- fs->saw_z = 1;
- ++aug;
- }
-
- /* Iterate over recognized augmentation subsequences. */
- while (*aug != '\0')
- {
- /* "L" indicates a byte showing how the LSDA pointer is encoded. */
- if (aug[0] == 'L')
- {
- fs->lsda_encoding = *p++;
- aug += 1;
- }
-
- /* "R" indicates a byte indicating how FDE addresses are encoded. */
- else if (aug[0] == 'R')
- {
- fs->fde_encoding = *p++;
- aug += 1;
- }
-
- /* "P" indicates a personality routine in the CIE augmentation. */
- else if (aug[0] == 'P')
- {
- _Unwind_Ptr personality;
-
- p = read_encoded_value (context, *p, p + 1, &personality);
- fs->personality = (_Unwind_Personality_Fn) personality;
- aug += 1;
- }
-
- /* "S" indicates a signal frame. */
- else if (aug[0] == 'S')
- {
- fs->signal_frame = 1;
- aug += 1;
- }
-
- /* Otherwise we have an unknown augmentation string.
- Bail unless we saw a 'z' prefix. */
- else
- return ret;
- }
-
- return ret ? ret : p;
-}
-
-/* Given the _Unwind_Context CONTEXT for a stack frame, look up the FDE for
- its caller and decode it into FS. This function also sets the
- lsda member of CONTEXT, as it is really information
- about the caller's frame. */
-
-static _Unwind_Reason_Code
-uw_frame_state_for (struct _Unwind_Context *context, _Unwind_FrameState *fs)
-{
- const struct dwarf_fde *fde;
- const struct dwarf_cie *cie;
- const unsigned char *aug;
- int window_size;
- _Unwind_Word *ra_ptr;
-
- memset (fs, 0, sizeof (*fs));
- context->lsda = 0;
-
- fde = _Unwind_Find_FDE (context->ra + _Unwind_IsSignalFrame (context) - 1,
- &context->bases);
- if (fde == NULL)
- {
-#ifdef MD_FALLBACK_FRAME_STATE_FOR
- _Unwind_Reason_Code reason;
- /* Couldn't find frame unwind info for this function. Try a
- target-specific fallback mechanism. This will necessarily
- not provide a personality routine or LSDA. */
- reason = MD_FALLBACK_FRAME_STATE_FOR (context, fs);
- if (reason != _URC_END_OF_STACK)
- return reason;
-#endif
- /* The frame was not recognized and handled by the fallback function,
- but it is not really the end of the stack. Fall through here and
- unwind it anyway. */
- }
- else
- {
- cie = get_cie (fde);
- if (extract_cie_info (cie, context, fs) == NULL)
- /* CIE contained unknown augmentation. */
- return _URC_FATAL_PHASE1_ERROR;
-
- /* Locate augmentation for the fde. */
- aug = (const unsigned char *) fde + sizeof (*fde);
- aug += 2 * size_of_encoded_value (fs->fde_encoding);
- if (fs->saw_z)
- {
- _uleb128_t i;
- aug = read_uleb128 (aug, &i);
- }
- if (fs->lsda_encoding != DW_EH_PE_omit)
- {
- _Unwind_Ptr lsda;
-
- aug = read_encoded_value (context, fs->lsda_encoding, aug, &lsda);
- context->lsda = (void *) lsda;
- }
- }
-
- /* Check for the end of the stack. This needs to be checked after
- the MD_FALLBACK_FRAME_STATE_FOR check for signal frames because
- the contents of context->reg[0] are undefined at a signal frame,
- and register a0 may appear to be zero. (The return address in
- context->ra comes from register a4 or a8). */
- ra_ptr = context->reg[0];
- if (ra_ptr && *ra_ptr == 0)
- return _URC_END_OF_STACK;
-
- /* Find the window size from the high bits of the return address. */
- if (ra_ptr)
- window_size = (*ra_ptr >> 30) * 4;
- else
- window_size = 8;
-
- fs->retaddr_column = window_size;
-
- return _URC_NO_REASON;
-}
-
-static void
-uw_update_context_1 (struct _Unwind_Context *context, _Unwind_FrameState *fs)
-{
- struct _Unwind_Context orig_context = *context;
- _Unwind_Word *sp, *cfa, *next_cfa;
- int i;
-
- if (fs->signal_regs)
- {
- cfa = (_Unwind_Word *) fs->signal_regs[1];
- next_cfa = (_Unwind_Word *) cfa[-3];
-
- for (i = 0; i < 4; i++)
- context->reg[i] = fs->signal_regs + (i << 2);
- }
- else
- {
- int window_size = fs->retaddr_column >> 2;
-
- sp = (_Unwind_Word *) orig_context.sp;
- cfa = (_Unwind_Word *) orig_context.cfa;
- next_cfa = (_Unwind_Word *) cfa[-3];
-
- /* Registers a0-a3 are in the save area below sp. */
- context->reg[0] = sp - 4;
-
- /* Find the extra save area below next_cfa. */
- for (i = 1; i < window_size; i++)
- context->reg[i] = next_cfa - 4 * (1 + window_size - i);
-
- /* Remaining registers rotate from previous save areas. */
- for (i = window_size; i < 4; i++)
- context->reg[i] = orig_context.reg[i - window_size];
- }
-
- context->sp = cfa;
- context->cfa = next_cfa;
-
- _Unwind_SetSignalFrame (context, fs->signal_frame);
-}
-
-/* CONTEXT describes the unwind state for a frame, and FS describes the FDE
- of its caller. Update CONTEXT to refer to the caller as well. Note
- that the lsda member is not updated here, but later in
- uw_frame_state_for. */
-
-static void
-uw_update_context (struct _Unwind_Context *context, _Unwind_FrameState *fs)
-{
- uw_update_context_1 (context, fs);
-
- /* Compute the return address now, since the return address column
- can change from frame to frame. */
- if (fs->signal_ra != 0)
- context->ra = (void *) fs->signal_ra;
- else
- context->ra = (void *) ((_Unwind_GetGR (context, fs->retaddr_column)
- & XTENSA_RA_FIELD_MASK) | context->ra_high_bits);
-}
-
-static void
-uw_advance_context (struct _Unwind_Context *context, _Unwind_FrameState *fs)
-{
- uw_update_context (context, fs);
-}
-
-/* Fill in CONTEXT for top-of-stack. The only valid registers at this
- level will be the return address and the CFA. */
-
-#define uw_init_context(CONTEXT) \
- do \
- { \
- __builtin_unwind_init (); \
- uw_init_context_1 (CONTEXT, __builtin_dwarf_cfa (), \
- __builtin_return_address (0)); \
- } \
- while (0)
-
-static void __attribute__((noinline))
-uw_init_context_1 (struct _Unwind_Context *context, void *outer_cfa,
- void *outer_ra)
-{
- void *ra = __builtin_return_address (0);
- void *cfa = __builtin_dwarf_cfa ();
- _Unwind_FrameState fs;
-
- memset (context, 0, sizeof (struct _Unwind_Context));
- context->ra = ra;
-
- memset (&fs, 0, sizeof (fs));
- fs.retaddr_column = 8;
- context->sp = cfa;
- context->cfa = outer_cfa;
- context->ra_high_bits =
- ((_Unwind_Word) uw_init_context_1) & ~XTENSA_RA_FIELD_MASK;
- uw_update_context_1 (context, &fs);
-
- context->ra = outer_ra;
-}
-
-
-/* Install TARGET into CURRENT so that we can return to it. This is a
- macro because __builtin_eh_return must be invoked in the context of
- our caller. */
-
-#define uw_install_context(CURRENT, TARGET) \
- do \
- { \
- long offset = uw_install_context_1 ((CURRENT), (TARGET)); \
- void *handler = __builtin_frob_return_addr ((TARGET)->ra); \
- __builtin_eh_return (offset, handler); \
- } \
- while (0)
-
-static long
-uw_install_context_1 (struct _Unwind_Context *current,
- struct _Unwind_Context *target)
-{
- long i;
-
- /* The eh_return insn assumes a window size of 8, so don't bother copying
- the save areas for registers a8-a15 since they won't be reloaded. */
- for (i = 0; i < 2; ++i)
- {
- void *c = current->reg[i];
- void *t = target->reg[i];
-
- if (t && c && t != c)
- memcpy (c, t, 4 * sizeof (_Unwind_Word));
- }
-
- return 0;
-}
-
-static inline _Unwind_Ptr
-uw_identify_context (struct _Unwind_Context *context)
-{
- return _Unwind_GetCFA (context);
-}
-
-
-#include "unwind.inc"
-
-#if defined (USE_GAS_SYMVER) && defined (SHARED) && defined (USE_LIBUNWIND_EXCEPTIONS)
-alias (_Unwind_Backtrace);
-alias (_Unwind_DeleteException);
-alias (_Unwind_FindEnclosingFunction);
-alias (_Unwind_ForcedUnwind);
-alias (_Unwind_GetDataRelBase);
-alias (_Unwind_GetTextRelBase);
-alias (_Unwind_GetCFA);
-alias (_Unwind_GetGR);
-alias (_Unwind_GetIP);
-alias (_Unwind_GetLanguageSpecificData);
-alias (_Unwind_GetRegionStart);
-alias (_Unwind_RaiseException);
-alias (_Unwind_Resume);
-alias (_Unwind_Resume_or_Rethrow);
-alias (_Unwind_SetGR);
-alias (_Unwind_SetIP);
-#endif
-
-#endif /* !USING_SJLJ_EXCEPTIONS */
diff --git a/gcc/config/xtensa/unwind-dw2-xtensa.h b/gcc/config/xtensa/unwind-dw2-xtensa.h
deleted file mode 100644
index d13b326..0000000
--- a/gcc/config/xtensa/unwind-dw2-xtensa.h
+++ /dev/null
@@ -1,50 +0,0 @@
-/* DWARF2 frame unwind data structure for Xtensa.
- Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2007, 2008,
- 2009 Free Software Foundation, Inc.
-
- This file is part of GCC.
-
- GCC is free software; you can redistribute it and/or modify it
- under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 3, or (at your option)
- any later version.
-
- GCC 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 General Public
- License for more details.
-
- Under Section 7 of GPL version 3, you are granted additional
- permissions described in the GCC Runtime Library Exception, version
- 3.1, as published by the Free Software Foundation.
-
- You should have received a copy of the GNU General Public License and
- a copy of the GCC Runtime Library Exception along with this program;
- see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
- <http://www.gnu.org/licenses/>. */
-
-/* A target can override (perhaps for backward compatibility) how
- many dwarf2 columns are unwound. */
-#ifndef DWARF_FRAME_REGISTERS
-#define DWARF_FRAME_REGISTERS FIRST_PSEUDO_REGISTER
-#endif
-
-/* Xtensa's variable-size register window save areas can be unwound without
- any unwind info. This is a stripped down version of the standard DWARF
- _Unwind_FrameState. */
-typedef struct
-{
- /* The information we care about from the CIE/FDE. */
- _Unwind_Personality_Fn personality;
- _Unwind_Word retaddr_column;
- unsigned char fde_encoding;
- unsigned char lsda_encoding;
- unsigned char saw_z;
- unsigned char signal_frame;
- void *eh_ptr;
-
- /* Saved registers for a signal frame. */
- _Unwind_Word *signal_regs;
- _Unwind_Word signal_ra;
-} _Unwind_FrameState;
-