diff options
-rw-r--r-- | libjava/ChangeLog | 6 | ||||
-rwxr-xr-x | libjava/configure | 2 | ||||
-rw-r--r-- | libjava/configure.in | 2 | ||||
-rw-r--r-- | libjava/include/powerpc-signal.h | 87 |
4 files changed, 95 insertions, 2 deletions
diff --git a/libjava/ChangeLog b/libjava/ChangeLog index b4173cb..252e6da 100644 --- a/libjava/ChangeLog +++ b/libjava/ChangeLog @@ -1,3 +1,9 @@ +2003-06-17 Franz Sirl <Franz.Sirl-kernel@lauterbach.com> + + * include/powerpc-signal.h: New File. + * configure.in: Use it. + * configure: Regenerated. + 2003-06-17 Michael Koch <konqueror@gmx.de> * java/util/Locale.java diff --git a/libjava/configure b/libjava/configure index 2e5b34d..8eba4cb 100755 --- a/libjava/configure +++ b/libjava/configure @@ -8618,7 +8618,7 @@ case "${host}" in SIGNAL_HANDLER=include/dwarf2-signal.h ;; powerpc-*-linux*) - SIGNAL_HANDLER=include/dwarf2-signal.h + SIGNAL_HANDLER=include/powerpc-signal.h ;; alpha*-*-linux*) SIGNAL_HANDLER=include/dwarf2-signal.h diff --git a/libjava/configure.in b/libjava/configure.in index f1e0a39..dcdf4c1 100644 --- a/libjava/configure.in +++ b/libjava/configure.in @@ -1004,7 +1004,7 @@ case "${host}" in SIGNAL_HANDLER=include/dwarf2-signal.h ;; powerpc-*-linux*) - SIGNAL_HANDLER=include/dwarf2-signal.h + SIGNAL_HANDLER=include/powerpc-signal.h ;; alpha*-*-linux*) SIGNAL_HANDLER=include/dwarf2-signal.h diff --git a/libjava/include/powerpc-signal.h b/libjava/include/powerpc-signal.h new file mode 100644 index 0000000..00a5a6d --- /dev/null +++ b/libjava/include/powerpc-signal.h @@ -0,0 +1,87 @@ +// powerpc-signal.h - Catch runtime signals and turn them into exceptions +// on a powerpc based Linux system. + +/* Copyright (C) 2003 Free Software Foundation + + This file is part of libgcj. + +This software is copyrighted work licensed under the terms of the +Libgcj License. Please consult the file "LIBGCJ_LICENSE" for +details. */ + + +#ifndef JAVA_SIGNAL_H +# define JAVA_SIGNAL_H 1 + +# include <signal.h> +# include <sys/syscall.h> + +# define HANDLE_SEGV 1 +# undef HANDLE_FPE + +# define SIGNAL_HANDLER(_name) \ + static void _name (int /* _signal */, struct sigcontext *_sc) + +/* PPC either leaves PC pointing at a faulting instruction or the + following instruction, depending on the signal. SEGV always does + the former, so we adjust the saved PC to point to the following + instruction. This is what the handler in libgcc expects. */ + +# define MAKE_THROW_FRAME(_exception) \ +do \ + { \ + _sc->regs->nip += 4; \ + } \ +while (0) + +/* For an explanation why we cannot simply use sigaction to + install the handlers, see i386-signal.h. */ + +/* We use kernel_old_sigaction here because we're calling the kernel + directly rather than via glibc. The sigaction structure that the + syscall uses is a different shape from the one in userland and not + visible to us in a header file so we define it here. + Additionally we want a proper prototype for the handler function + with the struct sigcontext pointer passed by the kernel as the 2nd + argument, which isn't there in userland headers. + + Note that we explicitly avoid the SA_SIGINFO flag in INIT_SEGV and + INIT_FPE below. Using the ucontext pointer passed as 3rd argument + of a SA_SIGINFO type handler would need complicated backwards + compatibility hacks in MAKE_THROW_FRAME, as the ucontext layout + on PPC changed during the 2.5 kernel series. */ + +struct kernel_old_sigaction { + void (*k_sa_handler) (int, struct sigcontext *); + unsigned long k_sa_mask; + unsigned long k_sa_flags; + void (*k_sa_restorer) (void); +}; + +# define INIT_SEGV \ +do \ + { \ + nullp = new java::lang::NullPointerException (); \ + struct kernel_old_sigaction kact; \ + kact.k_sa_handler = catch_segv; \ + kact.k_sa_mask = 0; \ + kact.k_sa_flags = 0; \ + syscall (SYS_sigaction, SIGSEGV, &kact, NULL); \ + } \ +while (0) + +# define INIT_FPE \ +do \ + { \ + arithexception = new java::lang::ArithmeticException \ + (JvNewStringLatin1 ("/ by zero")); \ + struct kernel_old_sigaction kact; \ + kact.k_sa_handler = catch_fpe; \ + kact.k_sa_mask = 0; \ + kact.k_sa_flags = 0; \ + syscall (SYS_sigaction, SIGFPE, &kact, NULL); \ + } \ +while (0) + +#endif /* JAVA_SIGNAL_H */ + |