aboutsummaryrefslogtreecommitdiff
path: root/compiler-rt/lib
diff options
context:
space:
mode:
Diffstat (limited to 'compiler-rt/lib')
-rw-r--r--compiler-rt/lib/builtins/gcc_personality_v0.c81
-rw-r--r--compiler-rt/lib/profile/CMakeLists.txt6
-rw-r--r--compiler-rt/lib/profile/GCDAProfiling.c5
-rw-r--r--compiler-rt/lib/profile/InstrProfilingFile.c5
-rw-r--r--compiler-rt/lib/profile/InstrProfilingUtil.c5
5 files changed, 92 insertions, 10 deletions
diff --git a/compiler-rt/lib/builtins/gcc_personality_v0.c b/compiler-rt/lib/builtins/gcc_personality_v0.c
index ef63a5f..3ed17fa 100644
--- a/compiler-rt/lib/builtins/gcc_personality_v0.c
+++ b/compiler-rt/lib/builtins/gcc_personality_v0.c
@@ -30,6 +30,54 @@ EXCEPTION_DISPOSITION _GCC_specific_handler(PEXCEPTION_RECORD, void *, PCONTEXT,
_Unwind_Personality_Fn);
#endif
+#if __has_feature(ptrauth_calls)
+#include <ptrauth.h>
+
+// `__ptrauth_restricted_intptr` is a feature of apple clang that predates
+// support for direct application of `__ptrauth` to integer types. This
+// guard is necessary to support compilation with those compiler.
+#if __has_feature(ptrauth_restricted_intptr_qualifier)
+#define __ptrauth_gcc_personality_intptr(key, addressDiscriminated, \
+ discriminator) \
+ __ptrauth_restricted_intptr(key, addressDiscriminated, discriminator)
+#else
+#define __ptrauth_gcc_personality_intptr(key, addressDiscriminated, \
+ discriminator) \
+ __ptrauth(key, addressDiscriminated, discriminator)
+#endif
+#else
+#define __ptrauth_gcc_personality_intptr(...)
+#endif
+
+#define __ptrauth_gcc_personality_func_key ptrauth_key_function_pointer
+
+// ptrauth_string_discriminator("__gcc_personality_v0'funcStart") == 0xDFEB
+#define __ptrauth_gcc_personality_func_start \
+ __ptrauth_gcc_personality_intptr(__ptrauth_gcc_personality_func_key, 1, \
+ 0xDFEB)
+
+// ptrauth_string_discriminator("__gcc_personality_v0'start") == 0x52DC
+#define __ptrauth_gcc_personality_start \
+ __ptrauth_gcc_personality_intptr(__ptrauth_gcc_personality_func_key, 1, \
+ 0x52DC)
+
+// ptrauth_string_discriminator("__gcc_personality_v0'length") == 0xFFF7
+#define __ptrauth_gcc_personality_length \
+ __ptrauth_gcc_personality_intptr(__ptrauth_gcc_personality_func_key, 1, \
+ 0xFFF7)
+
+// ptrauth_string_discriminator("__gcc_personality_v0'landingPadOffset") ==
+// 0x6498
+#define __ptrauth_gcc_personality_lpoffset \
+ __ptrauth_gcc_personality_intptr(__ptrauth_gcc_personality_func_key, 1, \
+ 0x6498)
+
+// ptrauth_string_discriminator("__gcc_personality_v0'landingPad") == 0xA134
+#define __ptrauth_gcc_personality_lpad_disc 0xA134
+#define __ptrauth_gcc_personality_lpad \
+ __ptrauth_gcc_personality_intptr(__ptrauth_gcc_personality_func_key, 1, \
+ __ptrauth_gcc_personality_lpad_disc)
+
// Pointer encodings documented at:
// http://refspecs.freestandards.org/LSB_1.3.0/gLSB/gLSB/ehframehdr.html
@@ -205,7 +253,8 @@ COMPILER_RT_ABI _Unwind_Reason_Code __gcc_personality_v0(
return continueUnwind(exceptionObject, context);
uintptr_t pc = (uintptr_t)_Unwind_GetIP(context) - 1;
- uintptr_t funcStart = (uintptr_t)_Unwind_GetRegionStart(context);
+ uintptr_t __ptrauth_gcc_personality_func_start funcStart =
+ (uintptr_t)_Unwind_GetRegionStart(context);
uintptr_t pcOffset = pc - funcStart;
// Parse LSDA header.
@@ -224,11 +273,14 @@ COMPILER_RT_ABI _Unwind_Reason_Code __gcc_personality_v0(
const uint8_t *callSiteTableEnd = callSiteTableStart + callSiteTableLength;
const uint8_t *p = callSiteTableStart;
while (p < callSiteTableEnd) {
- uintptr_t start = readEncodedPointer(&p, callSiteEncoding);
- size_t length = readEncodedPointer(&p, callSiteEncoding);
- size_t landingPad = readEncodedPointer(&p, callSiteEncoding);
+ uintptr_t __ptrauth_gcc_personality_start start =
+ readEncodedPointer(&p, callSiteEncoding);
+ size_t __ptrauth_gcc_personality_length length =
+ readEncodedPointer(&p, callSiteEncoding);
+ size_t __ptrauth_gcc_personality_lpoffset landingPadOffset =
+ readEncodedPointer(&p, callSiteEncoding);
readULEB128(&p); // action value not used for C code
- if (landingPad == 0)
+ if (landingPadOffset == 0)
continue; // no landing pad for this entry
if ((start <= pcOffset) && (pcOffset < (start + length))) {
// Found landing pad for the PC.
@@ -238,7 +290,24 @@ COMPILER_RT_ABI _Unwind_Reason_Code __gcc_personality_v0(
_Unwind_SetGR(context, __builtin_eh_return_data_regno(0),
(uintptr_t)exceptionObject);
_Unwind_SetGR(context, __builtin_eh_return_data_regno(1), 0);
- _Unwind_SetIP(context, (funcStart + landingPad));
+ size_t __ptrauth_gcc_personality_lpad landingPad =
+ funcStart + landingPadOffset;
+#if __has_feature(ptrauth_calls)
+ uintptr_t stackPointer = _Unwind_GetGR(context, -2);
+ const uintptr_t existingDiscriminator = ptrauth_blend_discriminator(
+ &landingPad, __ptrauth_gcc_personality_lpad_disc);
+ // newIP is authenticated as if it were qualified with a pseudo qualifier
+ // along the lines of:
+ // __ptrauth(ptrauth_key_return_address, <stackPointer>, 0)
+ // where the stack pointer is used in place of the strict storage
+ // address.
+ uintptr_t newIP = (uintptr_t)ptrauth_auth_and_resign(
+ *(void **)&landingPad, __ptrauth_gcc_personality_func_key,
+ existingDiscriminator, ptrauth_key_return_address, stackPointer);
+ _Unwind_SetIP(context, newIP);
+#else
+ _Unwind_SetIP(context, landingPad);
+#endif
return _URC_INSTALL_CONTEXT;
}
}
diff --git a/compiler-rt/lib/profile/CMakeLists.txt b/compiler-rt/lib/profile/CMakeLists.txt
index ac1451c..a6402f8 100644
--- a/compiler-rt/lib/profile/CMakeLists.txt
+++ b/compiler-rt/lib/profile/CMakeLists.txt
@@ -162,8 +162,7 @@ if(APPLE)
CFLAGS ${EXTRA_FLAGS}
SOURCES ${PROFILE_SOURCES}
ADDITIONAL_HEADERS ${PROFILE_HEADERS}
- PARENT_TARGET profile
- EXTENSIONS ON)
+ PARENT_TARGET profile)
else()
add_compiler_rt_runtime(clang_rt.profile
STATIC
@@ -171,6 +170,5 @@ else()
CFLAGS ${EXTRA_FLAGS}
SOURCES ${PROFILE_SOURCES}
ADDITIONAL_HEADERS ${PROFILE_HEADERS}
- PARENT_TARGET profile
- EXTENSIONS ON)
+ PARENT_TARGET profile)
endif()
diff --git a/compiler-rt/lib/profile/GCDAProfiling.c b/compiler-rt/lib/profile/GCDAProfiling.c
index ac01805..523ade5 100644
--- a/compiler-rt/lib/profile/GCDAProfiling.c
+++ b/compiler-rt/lib/profile/GCDAProfiling.c
@@ -21,6 +21,11 @@
#if !defined(__Fuchsia__)
+#if defined(__linux__)
+// For fdopen()
+#define _DEFAULT_SOURCE
+#endif
+
#include <errno.h>
#include <fcntl.h>
#include <stdint.h>
diff --git a/compiler-rt/lib/profile/InstrProfilingFile.c b/compiler-rt/lib/profile/InstrProfilingFile.c
index 354f21b..71127b0 100644
--- a/compiler-rt/lib/profile/InstrProfilingFile.c
+++ b/compiler-rt/lib/profile/InstrProfilingFile.c
@@ -8,6 +8,11 @@
#if !defined(__Fuchsia__)
+#if defined(__linux__)
+// For fileno(), ftruncate(), getpagesize(), setenv()
+#define _DEFAULT_SOURCE
+#endif
+
#include <assert.h>
#include <errno.h>
#include <stdio.h>
diff --git a/compiler-rt/lib/profile/InstrProfilingUtil.c b/compiler-rt/lib/profile/InstrProfilingUtil.c
index 0fae91c..a9d9df8 100644
--- a/compiler-rt/lib/profile/InstrProfilingUtil.c
+++ b/compiler-rt/lib/profile/InstrProfilingUtil.c
@@ -12,6 +12,11 @@
#include <windows.h>
#include "WindowsMMap.h"
#else
+#if defined(__linux__)
+// For fdopen(), fileno(), getpagesize(), madvise()
+#define _DEFAULT_SOURCE
+#endif
+
#include <errno.h>
#include <fcntl.h>
#include <sys/file.h>