hwasan_setjmp_aarch64.S 2.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102
  1. //===-- hwasan_setjmp_aarch64.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. // This file is a part of HWAddressSanitizer.
  10. //
  11. // HWAddressSanitizer runtime.
  12. //===----------------------------------------------------------------------===//
  13. #include "sanitizer_common/sanitizer_asm.h"
  14. #include "builtins/assembly.h"
  15. #if HWASAN_WITH_INTERCEPTORS && defined(__aarch64__)
  16. #include "sanitizer_common/sanitizer_platform.h"
  17. // We want to save the context of the calling function.
  18. // That requires
  19. // 1) No modification of the link register by this function.
  20. // 2) No modification of the stack pointer by this function.
  21. // 3) (no modification of any other saved register, but that's not really going
  22. // to occur, and hence isn't as much of a worry).
  23. //
  24. // There's essentially no way to ensure that the compiler will not modify the
  25. // stack pointer when compiling a C function.
  26. // Hence we have to write this function in assembly.
  27. .section .text
  28. .file "hwasan_setjmp_aarch64.S"
  29. .global ASM_WRAPPER_NAME(setjmp)
  30. ASM_TYPE_FUNCTION(ASM_WRAPPER_NAME(setjmp))
  31. ASM_WRAPPER_NAME(setjmp):
  32. CFI_STARTPROC
  33. BTI_C
  34. mov x1, #0
  35. b ASM_WRAPPER_NAME(sigsetjmp)
  36. CFI_ENDPROC
  37. ASM_SIZE(ASM_WRAPPER_NAME(setjmp))
  38. ASM_INTERCEPTOR_TRAMPOLINE(setjmp)
  39. #if SANITIZER_ANDROID
  40. // Bionic also defines a function `setjmp` that calls `sigsetjmp` saving the
  41. // current signal.
  42. .global ASM_WRAPPER_NAME(setjmp_bionic)
  43. ASM_TYPE_FUNCTION(ASM_WRAPPER_NAME(setjmp_bionic))
  44. ASM_WRAPPER_NAME(setjmp_bionic):
  45. CFI_STARTPROC
  46. BTI_C
  47. mov x1, #1
  48. b ASM_WRAPPER_NAME(sigsetjmp)
  49. CFI_ENDPROC
  50. ASM_SIZE(ASM_WRAPPER_NAME(setjmp_bionic))
  51. ASM_INTERCEPTOR_TRAMPOLINE(setjmp_bionic)
  52. #endif
  53. .global ASM_WRAPPER_NAME(sigsetjmp)
  54. ASM_TYPE_FUNCTION(ASM_WRAPPER_NAME(sigsetjmp))
  55. ASM_WRAPPER_NAME(sigsetjmp):
  56. CFI_STARTPROC
  57. BTI_C
  58. stp x19, x20, [x0, #0<<3]
  59. stp x21, x22, [x0, #2<<3]
  60. stp x23, x24, [x0, #4<<3]
  61. stp x25, x26, [x0, #6<<3]
  62. stp x27, x28, [x0, #8<<3]
  63. stp x29, x30, [x0, #10<<3]
  64. stp d8, d9, [x0, #14<<3]
  65. stp d10, d11, [x0, #16<<3]
  66. stp d12, d13, [x0, #18<<3]
  67. stp d14, d15, [x0, #20<<3]
  68. mov x2, sp
  69. str x2, [x0, #13<<3]
  70. // We always have the second argument to __sigjmp_save (savemask) set, since
  71. // the _setjmp function above has set it for us as `false`.
  72. // This function is defined in hwasan_interceptors.cc
  73. b __sigjmp_save
  74. CFI_ENDPROC
  75. ASM_SIZE(ASM_WRAPPER_NAME(sigsetjmp))
  76. ASM_INTERCEPTOR_TRAMPOLINE(sigsetjmp)
  77. #if SANITIZER_ANDROID
  78. ASM_TRAMPOLINE_ALIAS(sigsetjmp, sigsetjmp)
  79. ASM_TRAMPOLINE_ALIAS(setjmp, setjmp_bionic)
  80. #else
  81. ASM_TRAMPOLINE_ALIAS(__sigsetjmp, sigsetjmp)
  82. #endif
  83. ASM_TRAMPOLINE_ALIAS(_setjmp, setjmp)
  84. #endif
  85. // We do not need executable stack.
  86. NO_EXEC_STACK_DIRECTIVE
  87. GNU_PROPERTY_BTI_PAC