Hi,
this fixes exception handling when using eg++ on sparc64. Since stack
frames are non-standard on OpenBSD/sparc64 because of stackghost, we
need adapted code to unwind the stack.
Regress tests in regress/misc/exceptions pass. Also, pdns_server is
much happier (though still suffering from a Bus Error unrelated to
exceptions).
Thanks to kettenis@ pointing me in the right direction. The code is
equivalent to the code in the base C++ compiler.
OK?
-Otto
Index: Makefile
===================================================================
RCS file: /cvs/ports/lang/gcc/4.9/Makefile,v
retrieving revision 1.64
diff -u -p -r1.64 Makefile
--- Makefile 17 Dec 2018 14:05:21 -0000 1.64
+++ Makefile 2 Feb 2019 13:18:11 -0000
@@ -4,7 +4,7 @@ ONLY_FOR_ARCHS = ${GCC49_ARCHS}
DPB_PROPERTIES = parallel
V = 4.9.4
-REVISION = 15
+REVISION = 16
FULL_VERSION = $V
FULL_PKGVERSION = $V
Index: patches/patch-libgcc_unwind-dw2_c
===================================================================
RCS file: patches/patch-libgcc_unwind-dw2_c
diff -N patches/patch-libgcc_unwind-dw2_c
--- /dev/null 1 Jan 1970 00:00:00 -0000
+++ patches/patch-libgcc_unwind-dw2_c 2 Feb 2019 13:18:11 -0000
@@ -0,0 +1,53 @@
+$OpenBSD$
+
+Index: libgcc/unwind-dw2.c
+--- libgcc/unwind-dw2.c.orig
++++ libgcc/unwind-dw2.c
+@@ -217,6 +217,25 @@ _Unwind_IsExtendedContext (struct _Unwind_Context *con
+ return (ASSUME_EXTENDED_UNWIND_CONTEXT
+ || (context->flags & EXTENDED_CONTEXT_BIT));
+ }
++
++#ifdef __sparc64__
++
++/* Figure out StackGhost cookie. */
++_Unwind_Word uw_get_wcookie(void);
++
++asm(".text\n"
++ "uw_get_wcookie:\n"
++ " add %o7, %g0, %g4\n"
++ " save %sp, -176, %sp\n"
++ " save %sp, -176, %sp\n"
++ " flushw\n"
++ " restore\n"
++ " ldx [%sp + 2047 + 120], %g5\n"
++ " xor %g4, %g5, %i0\n"
++ " ret\n"
++ " restore\n");
++#endif
++
+
+ /* Get the value of register INDEX as saved in CONTEXT. */
+
+@@ -239,6 +258,13 @@ _Unwind_GetGR (struct _Unwind_Context *context, int in
+ if (_Unwind_IsExtendedContext (context) && context->by_value[index])
+ return _Unwind_Get_Unwind_Word (val);
+
++#ifdef __sparc64__
++ /* _Unwind_Word and _Unwind_Ptr are the same size on sparc64 */
++ _Unwind_Word reg = * (_Unwind_Word *) val;
++ if (index == 15 || index == 31)
++ reg ^= uw_get_wcookie ();
++ return reg;
++#else
+ /* This will segfault if the register hasn't been saved. */
+ if (size == sizeof(_Unwind_Ptr))
+ return * (_Unwind_Ptr *) (_Unwind_Internal_Ptr) val;
+@@ -247,6 +273,7 @@ _Unwind_GetGR (struct _Unwind_Context *context, int in
+ gcc_assert (size == sizeof(_Unwind_Word));
+ return * (_Unwind_Word *) (_Unwind_Internal_Ptr) val;
+ }
++#endif
+ }
+
+ static inline void *