summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJason King <jason.king@joyent.com>2020-10-29 14:43:04 +0000
committerJason King <jason.king@joyent.com>2020-10-29 14:43:04 +0000
commit041ee33ad0c71565fb9907e8c2816437ea1ddc9d (patch)
tree293e312195c48f4845991e939a1a915c42f7bf67
parent25224c29e0bd70ec85db1db89171523a472a3ee2 (diff)
parent1ba82a13d050678604bdd3fae596131469ca10e6 (diff)
downloadillumos-joyent-041ee33ad0c71565fb9907e8c2816437ea1ddc9d.tar.gz
[illumos-gate merge]
commit 1ba82a13d050678604bdd3fae596131469ca10e6 13254 SEGV due to misaligned stack in Unwind_RaiseException
-rw-r--r--usr/src/lib/libc/amd64/Makefile5
-rw-r--r--usr/src/lib/libc/amd64/unwind/unwind.c28
-rw-r--r--usr/src/lib/libc/amd64/unwind/unwind_wrap.s31
3 files changed, 51 insertions, 13 deletions
diff --git a/usr/src/lib/libc/amd64/Makefile b/usr/src/lib/libc/amd64/Makefile
index b2aa4f3a58..d8919e9201 100644
--- a/usr/src/lib/libc/amd64/Makefile
+++ b/usr/src/lib/libc/amd64/Makefile
@@ -25,7 +25,7 @@
# Copyright 2013 Garrett D'Amore <garrett@damore.org>
# Copyright 2018 Nexenta Systems, Inc.
# Copyright 2019 Joyent, Inc.
-# Copyright 2019 OmniOS Community Edition (OmniOSce) Association.
+# Copyright 2020 OmniOS Community Edition (OmniOSce) Association.
#
LIBCBASE= .
@@ -884,7 +884,8 @@ UNWINDMACHOBJS= \
pics/unwind.o:= COPTFLAG64 =
UNWINDASMOBJS= \
- unwind_frame.o
+ unwind_frame.o \
+ unwind_wrap.o
# Preserved solely to ease maintenance of 32-bit and 64-bit library builds
# This macro should ALWAYS be empty; native APIs are already 'large file'.
diff --git a/usr/src/lib/libc/amd64/unwind/unwind.c b/usr/src/lib/libc/amd64/unwind/unwind.c
index 064e241df3..810a385031 100644
--- a/usr/src/lib/libc/amd64/unwind/unwind.c
+++ b/usr/src/lib/libc/amd64/unwind/unwind.c
@@ -23,6 +23,7 @@
* Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
* Copyright 2012 Milan Jurik. All rights reserved.
+ * Copyright 2020 OmniOS Community Edition (OmniOSce) Association.
*/
/*
@@ -124,7 +125,6 @@
#define _Unwind_GetIP _SUNW_Unwind_GetIP
#define _Unwind_GetLanguageSpecificData _SUNW_Unwind_GetLanguageSpecificData
#define _Unwind_GetRegionStart _SUNW_Unwind_GetRegionStart
-#define _Unwind_RaiseException _SUNW_Unwind_RaiseException
#define _Unwind_Resume _SUNW_Unwind_Resume
#define _Unwind_SetGR _SUNW_Unwind_SetGR
#define _Unwind_SetIP _SUNW_Unwind_SetIP
@@ -137,7 +137,6 @@
#pragma weak _SUNW_Unwind_GetLanguageSpecificData = \
_Unwind_GetLanguageSpecificData
#pragma weak _SUNW_Unwind_GetRegionStart = _Unwind_GetRegionStart
-#pragma weak _SUNW_Unwind_RaiseException = _Unwind_RaiseException
#pragma weak _SUNW_Unwind_Resume = _Unwind_Resume
#pragma weak _SUNW_Unwind_SetGR = _Unwind_SetGR
#pragma weak _SUNW_Unwind_SetIP = _Unwind_SetIP
@@ -174,8 +173,7 @@ ctx_who(struct _Unwind_Context *ctx)
/* ARGSUSED */
_Unwind_Reason_Code
_Unw_very_boring_personality(int version, int actions, uint64_t exclass,
- struct _Unwind_Exception *exception_object,
- struct _Unwind_Context *ctx)
+ struct _Unwind_Exception *exception_object, struct _Unwind_Context *ctx)
{
_Unwind_Reason_Code res = _URC_CONTINUE_UNWIND;
uint64_t fp;
@@ -287,7 +285,7 @@ jmp_ctx(struct _Unwind_Context *ctx)
*/
_Unwind_Reason_Code
_Unwind_RaiseException_Body(struct _Unwind_Exception *exception_object,
- struct _Unwind_Context *entry_ctx, int phase)
+ struct _Unwind_Context *entry_ctx, int phase)
{
struct _Unwind_Context context;
struct _Unwind_Context *ctx = &context;
@@ -347,8 +345,17 @@ _Unwind_RaiseException_Body(struct _Unwind_Exception *exception_object,
return (res);
}
+/*
+ * Unfortunately, the closed source libCrun.so library calls into the
+ * _Unwind_RaiseException function without ensuring that the stack pointer
+ * is properly aligned. Some of the downstream functions use SSE instructions
+ * and raise GP when the stack is not aligned.
+ * To work around this, the entry point for _Unwind_RaiseException is
+ * implemented in assembler (in unwind_wrap.s) and it properly aligns the stack
+ * before calling the real function here.
+ */
_Unwind_Reason_Code
-_Unwind_RaiseException(struct _Unwind_Exception *exception_object)
+__Unwind_RaiseException_Backend(struct _Unwind_Exception *exception_object)
{
struct _Unwind_Context entry_context;
struct _Unwind_Context *entry_ctx = &entry_context;
@@ -361,8 +368,8 @@ _Unwind_RaiseException(struct _Unwind_Exception *exception_object)
_Unwind_Reason_Code
_Unwind_ForcedUnwind_Body(struct _Unwind_Exception *exception_object,
- _Unwind_Stop_Fn stop, void *stop_parameter,
- struct _Unwind_Context *ctx, int resume)
+ _Unwind_Stop_Fn stop, void *stop_parameter,
+ struct _Unwind_Context *ctx, int resume)
{
_Unwind_Reason_Code res;
int phase = _UA_CLEANUP_PHASE | _UA_FORCE_UNWIND;
@@ -433,7 +440,7 @@ _Unwind_ForcedUnwind_Body(struct _Unwind_Exception *exception_object,
_Unwind_Reason_Code
_Unwind_ForcedUnwind(struct _Unwind_Exception *exception_object,
- _Unwind_Stop_Fn stop, void *stop_parameter)
+ _Unwind_Stop_Fn stop, void *stop_parameter)
{
struct _Unwind_Context context;
struct _Unwind_Context *ctx = &context;
@@ -492,8 +499,7 @@ _Unwind_GetGR(struct _Unwind_Context *context, int index)
void
-_Unwind_SetGR(struct _Unwind_Context *context, int index,
-uint64_t new_value)
+_Unwind_SetGR(struct _Unwind_Context *context, int index, uint64_t new_value)
{
if (index <= EIR_R15) {
context->current_regs[index] = new_value;
diff --git a/usr/src/lib/libc/amd64/unwind/unwind_wrap.s b/usr/src/lib/libc/amd64/unwind/unwind_wrap.s
new file mode 100644
index 0000000000..1e2b33fad7
--- /dev/null
+++ b/usr/src/lib/libc/amd64/unwind/unwind_wrap.s
@@ -0,0 +1,31 @@
+/*
+ * This file and its contents are supplied under the terms of the
+ * Common Development and Distribution License ("CDDL"), version 1.0.
+ * You may only use this file in accordance with the terms of version
+ * 1.0 of the CDDL.
+ *
+ * A full copy of the text of the CDDL should have accompanied this
+ * source. A copy of the CDDL is also available via the Internet at
+ * http://www.illumos.org/license/CDDL.
+ */
+
+/*
+ * Copyright 2020 OmniOS Community Edition (OmniOSce) Association.
+ */
+
+ .file "unwind_wrap.s"
+ .global __Unwind_RaiseException_Backend
+
+#include "SYS.h"
+
+ ANSI_PRAGMA_WEAK2(_SUNW_Unwind_RaiseException,_Unwind_RaiseException,
+ function)
+
+ ENTRY(_Unwind_RaiseException)
+ pushq %rbp
+ movq %rsp,%rbp
+ andq $-STACK_ALIGN, %rsp /* adjust stack alignment */
+ call __Unwind_RaiseException_Backend
+ leave
+ ret
+ SET_SIZE(_Unwind_RaiseException)