X-Git-Url: http://git.sourceforge.jp/view?a=blobdiff_plain;f=libjava%2Finclude%2Fdwarf2-signal.h;h=949bcc0ae390c28d9441de87ae406918b807bff5;hb=bdf1b6f7bcb34f5e9e472572439ebad187a57469;hp=08287056705a16e2b233805af75d3e490250ff9d;hpb=d1c27e26f94b13dbda12e171e62228f532cf484c;p=pf3gnuchains%2Fgcc-fork.git diff --git a/libjava/include/dwarf2-signal.h b/libjava/include/dwarf2-signal.h index 08287056705..949bcc0ae39 100644 --- a/libjava/include/dwarf2-signal.h +++ b/libjava/include/dwarf2-signal.h @@ -1,6 +1,6 @@ // dwarf2-signal.h - Catch runtime signals and turn them into exceptions. -/* Copyright (C) 2000, 2001 Free Software Foundation +/* Copyright (C) 2000, 2001, 2009 Free Software Foundation This file is part of libgcj. @@ -58,53 +58,7 @@ do \ _sc->sc_ip++; \ } \ while (0) -#elif defined(__sparc__) -/* We could do the unwind of the signal frame quickly by hand here like - sparc-signal.h does under Solaris, but that makes debugging unwind - failures almost impossible. */ -#if !defined(__arch64__) -#define MAKE_THROW_FRAME(_exception) \ -do \ -{ \ - /* Sparc-32 leaves PC pointing at a faulting instruction \ - always. So we adjust the saved PC to point to the following \ - instruction; this is what the handler in libgcc expects. */ \ - /* Note that we are lying to the unwinder here, which expects the \ - faulting pc, not pc+1. But we claim the unwind information can't \ - be changed by such a ld or st instruction, so it doesn't matter. */ \ - struct sig_regs { \ - unsigned int psr, pc, npc, y, u_regs[16]; \ - } *regp; \ - unsigned int insn; \ - __asm__ __volatile__("ld [%%i7 + 8], %0" : "=r" (insn)); \ - if (insn == 0x821020d8) \ - regp = (struct sig_regs *) _sip; \ - else \ - regp = (struct sig_regs *) (_sip + 1); \ - regp->pc = regp->npc; \ - regp->npc += 4; \ -} \ -while (0) -#else -#define MAKE_THROW_FRAME(_exception) \ -do \ -{ \ - /* Sparc-64 leaves PC pointing at a faulting instruction \ - always. So we adjust the saved PC to point to the following \ - instruction; this is what the handler in libgcc expects. */ \ - /* Note that we are lying to the unwinder here, which expects the \ - faulting pc, not pc+1. But we claim the unwind information can't \ - be changed by such a ld or st instruction, so it doesn't matter. */ \ - struct pt_regs { \ - unsigned long u_regs[16]; \ - unsigned long tstate, tpc, tnpc; \ - unsigned int y, fprs; \ - } *regp = (struct pt_regs *) (_sip + 1); \ - regp->tpc = regp->tnpc; \ - regp->tnpc += 4; \ -} \ -while (0) -#endif + #else #define MAKE_THROW_FRAME(_exception) \ do \ @@ -114,11 +68,90 @@ do \ while (0) #endif -#if !(defined(__ia64__) || defined(__sparc__)) +#if defined(__sparc__) +#if defined(__arch64__) +extern "C" { + static void __rt_sigreturn_stub(void) + { + __asm__("mov %0, %%g1\n\t" + "ta 0x6d\n\t" + : /* no outputs */ + : "i" (__NR_rt_sigreturn)); + } + struct kernel_sigaction + { + void (*k_sa_sigaction)(int,siginfo_t *,void *); + unsigned long k_sa_flags; + void (*k_sa_restorer)(void); + sigset_t k_sa_mask; + }; +} +#define INIT_SEGV \ +do \ + { \ + struct kernel_sigaction act; \ + unsigned long stub = ((unsigned long)&__rt_sigreturn_stub); \ + act.k_sa_sigaction = _Jv_catch_segv; \ + sigemptyset (&act.k_sa_mask); \ + act.k_sa_flags = SA_SIGINFO; \ + act.k_sa_restorer = NULL; \ + syscall (SYS_rt_sigaction, SIGSEGV, &act, NULL, \ + stub - 8, _NSIG / 8); \ + } \ +while (0) + +#define INIT_FPE \ +do \ + { \ + struct kernel_sigaction act; \ + unsigned long stub = ((unsigned long)&__rt_sigreturn_stub); \ + act.k_sa_sigaction = _Jv_catch_fpe; \ + sigemptyset (&act.k_sa_mask); \ + act.k_sa_flags = SA_SIGINFO; \ + act.k_sa_restorer = NULL; \ + syscall (SYS_rt_sigaction, SIGFPE, &act, NULL, \ + stub - 8, _NSIG / 8); \ + } \ +while (0) +#else /* __arch64__ */ + +extern "C" { + struct kernel_sigaction + { + void (*k_sa_sigaction)(int,siginfo_t *,void *); + unsigned long k_sa_mask, k_sa_flags; + void (*k_sa_restorer)(void); + }; +} + +#define INIT_SEGV \ +do \ + { \ + struct kernel_sigaction act; \ + act.k_sa_sigaction = _Jv_catch_segv; \ + act.k_sa_mask = 0; \ + act.k_sa_flags = SA_SIGINFO; \ + act.k_sa_restorer = NULL; \ + syscall (SYS_sigaction, -SIGSEGV, &act, NULL); \ + } \ +while (0) + +#define INIT_FPE \ +do \ + { \ + struct kernel_sigaction act; \ + act.k_sa_sigaction = _Jv_catch_fpe; \ + act.k_sa_mask = 0; \ + act.k_sa_flags = SA_SIGINFO; \ + act.k_sa_restorer = NULL; \ + syscall (SYS_sigaction, -SIGFPE, &act, NULL); \ + } \ +while (0) +#endif +#elif !defined(__ia64__) #define INIT_SEGV \ do \ { \ - nullp = new java::lang::NullPointerException (); \ struct sigaction act; \ act.sa_sigaction = _Jv_catch_segv; \ sigemptyset (&act.sa_mask); \ @@ -130,8 +163,6 @@ while (0) #define INIT_FPE \ do \ { \ - arithexception = new java::lang::ArithmeticException \ - (JvNewStringLatin1 ("/ by zero")); \ struct sigaction act; \ act.sa_sigaction = _Jv_catch_fpe; \ sigemptyset (&act.sa_mask); \ @@ -147,40 +178,31 @@ while (0) * go away once all systems have pthreads libraries that are * compiled with full unwind info. */ -#else /* __ia64__ || __sparc__ */ +#else /* __ia64__ */ -// FIXME: We shouldn't be using libc_sigaction here, since it should -// be glibc private. But using syscall here would mean translating to -// the kernel's struct sigaction and argument sequence, which we -// shouldn't either. The right solution is to call sigaction and to -// make sure that we can unwind correctly through the pthread signal -// wrapper. -extern "C" int __libc_sigaction (int __sig, - __const struct sigaction *__restrict __act, - struct sigaction *__restrict __oact) throw (); +// On IA64, unwind information is mandatory, so we can unwind +// correctly through glibc frames. Thus we call the ordinary +// sigaction. #define INIT_SEGV \ do \ { \ - nullp = new java::lang::NullPointerException (); \ struct sigaction act; \ act.sa_sigaction = _Jv_catch_segv; \ sigemptyset (&act.sa_mask); \ act.sa_flags = SA_SIGINFO; \ - __libc_sigaction (SIGSEGV, &act, NULL); \ + sigaction (SIGSEGV, &act, NULL); \ } \ while (0) #define INIT_FPE \ do \ { \ - arithexception = new java::lang::ArithmeticException \ - (JvNewStringLatin1 ("/ by zero")); \ struct sigaction act; \ act.sa_sigaction = _Jv_catch_fpe; \ sigemptyset (&act.sa_mask); \ act.sa_flags = SA_SIGINFO; \ - __libc_sigaction (SIGFPE, &act, NULL); \ + sigaction (SIGFPE, &act, NULL); \ } \ while (0) #endif /* __ia64__ || __sparc__ */