Home | History | Annotate | Line # | Download | only in hwasan
hwasan_setjmp_x86_64.S revision 1.1.1.1
      1 //===-- hwasan_setjmp_x86_64.S --------------------------------------------===//
      2 //
      3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
      4 // See https://llvm.org/LICENSE.txt for license information.
      5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
      6 //
      7 //===----------------------------------------------------------------------===//
      8 //
      9 // setjmp interceptor for x86_64.
     10 //
     11 //===----------------------------------------------------------------------===//
     12 
     13 #include "sanitizer_common/sanitizer_asm.h"
     14 
     15 #if HWASAN_WITH_INTERCEPTORS && defined(__x86_64__)
     16 #include "sanitizer_common/sanitizer_platform.h"
     17 
     18 // We want to save the context of the calling function.
     19 // That requires
     20 // 1) No modification of the return address by this function.
     21 // 2) No modification of the stack pointer by this function.
     22 // 3) (no modification of any other saved register, but that's not really going
     23 // to occur, and hence isn't as much of a worry).
     24 //
     25 // There's essentially no way to ensure that the compiler will not modify the
     26 // stack pointer when compiling a C function.
     27 // Hence we have to write this function in assembly.
     28 //
     29 // TODO: Handle Intel CET.
     30 
     31 .section .text
     32 .file "hwasan_setjmp_x86_64.S"
     33 
     34 .global __interceptor_setjmp
     35 ASM_TYPE_FUNCTION(__interceptor_setjmp)
     36 __interceptor_setjmp:
     37   CFI_STARTPROC
     38   _CET_ENDBR
     39   xorl %esi, %esi
     40   jmp	__interceptor_sigsetjmp
     41   CFI_ENDPROC
     42 ASM_SIZE(__interceptor_setjmp)
     43 
     44 .global __interceptor_sigsetjmp
     45 ASM_TYPE_FUNCTION(__interceptor_sigsetjmp)
     46 __interceptor_sigsetjmp:
     47   CFI_STARTPROC
     48   _CET_ENDBR
     49 
     50   // Save callee save registers.
     51   mov %rbx, (0*8)(%rdi)
     52   mov %rbp, (1*8)(%rdi)
     53   mov %r12, (2*8)(%rdi)
     54   mov %r13, (3*8)(%rdi)
     55   mov %r14, (4*8)(%rdi)
     56   mov %r15, (5*8)(%rdi)
     57 
     58   // Save SP as it was in caller's frame.
     59   lea 8(%rsp), %rdx
     60   mov %rdx, (6*8)(%rdi)
     61 
     62   // Save return address.
     63   mov (%rsp), %rax
     64   mov %rax, (7*8)(%rdi)
     65 
     66   jmp __sigjmp_save
     67 
     68   CFI_ENDPROC
     69 ASM_SIZE(__interceptor_sigsetjmp)
     70 
     71 
     72 .macro WEAK_ALIAS first second
     73   .weak \second
     74   .equ \second\(), \first
     75 .endm
     76 
     77 WEAK_ALIAS __interceptor_sigsetjmp, __sigsetjmp
     78 WEAK_ALIAS __interceptor_setjmp, _setjmp
     79 #endif
     80 
     81 // We do not need executable stack.
     82 NO_EXEC_STACK_DIRECTIVE
     83