1 // A shadow call stack runtime is not yet included with compiler-rt, provide a 2 // minimal runtime to allocate a shadow call stack and assign an 3 // architecture-specific register to point at it. 4 5 #pragma once 6 7 #ifdef __x86_64__ 8 #include <asm/prctl.h> 9 int arch_prctl(int code, void *addr); 10 #endif 11 #include <stdlib.h> 12 #include <sys/mman.h> 13 #include <sys/prctl.h> 14 15 #include "libc_support.h" 16 17 __attribute__((no_sanitize("shadow-call-stack"))) 18 static void __shadowcallstack_init() { 19 void *stack = mmap(NULL, 8192, PROT_READ | PROT_WRITE, 20 MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); 21 if (stack == MAP_FAILED) 22 abort(); 23 24 #if defined(__x86_64__) 25 if (arch_prctl(ARCH_SET_GS, stack)) 26 abort(); 27 #elif defined(__aarch64__) 28 __asm__ __volatile__("mov x18, %0" ::"r"(stack)); 29 #else 30 #error Unsupported platform 31 #endif 32 } 33 34 int scs_main(void); 35 36 __attribute__((no_sanitize("shadow-call-stack"))) int main(void) { 37 __shadowcallstack_init(); 38 39 // We can't simply return scs_main() because scs_main might have corrupted our 40 // return address for testing purposes (see overflow.c), so we need to exit 41 // ourselves. 42 exit(scs_main()); 43 } 44