diff options
author | Jakub Jelinek <jakub@redhat.com> | 2003-12-19 15:00:53 +0100 |
---|---|---|
committer | Jakub Jelinek <jakub@gcc.gnu.org> | 2003-12-19 15:00:53 +0100 |
commit | e8c89d29703051af683fe65dc055089b61acde2f (patch) | |
tree | 7faf100b24bd243e8eba0de3b6bf9f538ba40ee2 /gcc/testsuite | |
parent | effed6551681c1411cfaebeb005979cb6996e528 (diff) | |
download | gcc-e8c89d29703051af683fe65dc055089b61acde2f.zip gcc-e8c89d29703051af683fe65dc055089b61acde2f.tar.gz gcc-e8c89d29703051af683fe65dc055089b61acde2f.tar.bz2 |
unwind-ia64.c (ia64_copy_rbs): New function.
* config/ia64/unwind-ia64.c (ia64_copy_rbs): New function.
(unw_access_gr): Only call ia64_rse_rnat_addr if addr is above
regstk_top.
(uw_frame_state_for): Handle locations inside bundles.
(uw_init_context_1): Initialize context->rnat.
Set context->regstk_top to lowest rbs address which has nat collection
in context->rnat.
(uw_install_context): Fix rnat restoring.
Restore ar.rsc to previous state.
* config/ia64/linux.h (MD_FALLBACK_FRAME_STATE_FOR,
MD_HANDLE_UNWABI): Handle unwinding through SA_ONSTACK frames.
* gcc.dg/cleanup-10.c: New test.
* gcc.dg/cleanup-11.c: New test.
From-SVN: r74835
Diffstat (limited to 'gcc/testsuite')
-rw-r--r-- | gcc/testsuite/ChangeLog | 5 | ||||
-rw-r--r-- | gcc/testsuite/gcc.dg/cleanup-10.c | 114 | ||||
-rw-r--r-- | gcc/testsuite/gcc.dg/cleanup-11.c | 114 |
3 files changed, 233 insertions, 0 deletions
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 3010412f..33e006e 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,5 +1,10 @@ 2003-12-19 Jakub Jelinek <jakub@redhat.com> + * gcc.dg/cleanup-10.c: New test. + * gcc.dg/cleanup-11.c: New test. + +2003-12-19 Jakub Jelinek <jakub@redhat.com> + PR c++/13239 * g++.dg/opt/expect1.C: New test. diff --git a/gcc/testsuite/gcc.dg/cleanup-10.c b/gcc/testsuite/gcc.dg/cleanup-10.c new file mode 100644 index 0000000..39923fd --- /dev/null +++ b/gcc/testsuite/gcc.dg/cleanup-10.c @@ -0,0 +1,114 @@ +/* { dg-do run { target i?86-*-linux* x86_64-*-linux* ia64-*-linux* alpha*-*-linux* powerpc*-*-linux* s390*-*-linux* sparc*-*-linux* mips*-*-linux* } } */ +/* { dg-options "-fasynchronous-unwind-tables -fexceptions -O2" } */ +/* Verify that cleanups work with exception handling through signal frames + on alternate stack. */ + +#include <unwind.h> +#include <stdlib.h> +#include <signal.h> +#include <unistd.h> + +static _Unwind_Reason_Code +force_unwind_stop (int version, _Unwind_Action actions, + _Unwind_Exception_Class exc_class, + struct _Unwind_Exception *exc_obj, + struct _Unwind_Context *context, + void *stop_parameter) +{ + if (actions & _UA_END_OF_STACK) + abort (); + return _URC_NO_REASON; +} + +static void force_unwind () +{ + struct _Unwind_Exception *exc = malloc (sizeof (*exc)); + exc->exception_class = 0; + exc->exception_cleanup = 0; + +#ifndef __USING_SJLJ_EXCEPTIONS__ + _Unwind_ForcedUnwind (exc, force_unwind_stop, 0); +#else + _Unwind_SjLj_ForcedUnwind (exc, force_unwind_stop, 0); +#endif + + abort (); +} + +int count; +char *null; + +static void counter (void *p __attribute__((unused))) +{ + ++count; +} + +static void handler (void *p __attribute__((unused))) +{ + if (count != 2) + abort (); + exit (0); +} + +static int __attribute__((noinline)) fn5 () +{ + char dummy __attribute__((cleanup (counter))); + force_unwind (); + return 0; +} + +static void fn4 (int sig, siginfo_t *info, void *ctx) +{ + char dummy __attribute__((cleanup (counter))); + fn5 (); + null = NULL; +} + +static void fn3 () +{ + abort (); +} + +static int __attribute__((noinline)) fn2 () +{ + *null = 0; + fn3 (); + return 0; +} + +static int __attribute__((noinline)) fn1 () +{ + stack_t ss; + struct sigaction s; + + ss.ss_size = 4 * sysconf (_SC_PAGESIZE); + if (ss.ss_size < SIGSTKSZ) + ss.ss_size = SIGSTKSZ; + ss.ss_sp = malloc (ss.ss_size); + if (ss.ss_sp == NULL) + exit (1); + ss.ss_flags = 0; + if (sigaltstack (&ss, NULL) < 0) + exit (1); + + sigemptyset (&s.sa_mask); + s.sa_sigaction = fn4; + s.sa_flags = SA_ONESHOT | SA_ONSTACK; + sigaction (SIGSEGV, &s, NULL); + fn2 (); + return 0; +} + +static int __attribute__((noinline)) fn0 () +{ + char dummy __attribute__((cleanup (handler))); + fn1 (); + null = 0; + return 0; +} + +int main() +{ + fn0 (); + abort (); +} diff --git a/gcc/testsuite/gcc.dg/cleanup-11.c b/gcc/testsuite/gcc.dg/cleanup-11.c new file mode 100644 index 0000000..9c47f6c --- /dev/null +++ b/gcc/testsuite/gcc.dg/cleanup-11.c @@ -0,0 +1,114 @@ +/* { dg-do run { target i?86-*-linux* x86_64-*-linux* ia64-*-linux* alpha*-*-linux* powerpc*-*-linux* s390*-*-linux* sparc*-*-linux* mips*-*-linux* } } */ +/* { dg-options "-fasynchronous-unwind-tables -fexceptions -O2" } */ +/* Verify that cleanups work with exception handling through realtime signal + frames on alternate stack. */ + +#include <unwind.h> +#include <stdlib.h> +#include <signal.h> +#include <unistd.h> + +static _Unwind_Reason_Code +force_unwind_stop (int version, _Unwind_Action actions, + _Unwind_Exception_Class exc_class, + struct _Unwind_Exception *exc_obj, + struct _Unwind_Context *context, + void *stop_parameter) +{ + if (actions & _UA_END_OF_STACK) + abort (); + return _URC_NO_REASON; +} + +static void force_unwind () +{ + struct _Unwind_Exception *exc = malloc (sizeof (*exc)); + exc->exception_class = 0; + exc->exception_cleanup = 0; + +#ifndef __USING_SJLJ_EXCEPTIONS__ + _Unwind_ForcedUnwind (exc, force_unwind_stop, 0); +#else + _Unwind_SjLj_ForcedUnwind (exc, force_unwind_stop, 0); +#endif + + abort (); +} + +int count; +char *null; + +static void counter (void *p __attribute__((unused))) +{ + ++count; +} + +static void handler (void *p __attribute__((unused))) +{ + if (count != 2) + abort (); + exit (0); +} + +static int __attribute__((noinline)) fn5 () +{ + char dummy __attribute__((cleanup (counter))); + force_unwind (); + return 0; +} + +static void fn4 (int sig, siginfo_t *info, void *ctx) +{ + char dummy __attribute__((cleanup (counter))); + fn5 (); + null = NULL; +} + +static void fn3 () +{ + abort (); +} + +static int __attribute__((noinline)) fn2 () +{ + *null = 0; + fn3 (); + return 0; +} + +static int __attribute__((noinline)) fn1 () +{ + stack_t ss; + struct sigaction s; + + ss.ss_size = 4 * sysconf (_SC_PAGESIZE); + if (ss.ss_size < SIGSTKSZ) + ss.ss_size = SIGSTKSZ; + ss.ss_sp = malloc (ss.ss_size); + if (ss.ss_sp == NULL) + exit (1); + ss.ss_flags = 0; + if (sigaltstack (&ss, NULL) < 0) + exit (1); + + sigemptyset (&s.sa_mask); + s.sa_sigaction = fn4; + s.sa_flags = SA_ONESHOT | SA_ONSTACK | SA_SIGINFO; + sigaction (SIGSEGV, &s, NULL); + fn2 (); + return 0; +} + +static int __attribute__((noinline)) fn0 () +{ + char dummy __attribute__((cleanup (handler))); + fn1 (); + null = 0; + return 0; +} + +int main() +{ + fn0 (); + abort (); +} |