152 lines · plain
1#include "asan_mapping.h"2#include "sanitizer_common/sanitizer_asm.h"3 4#if defined(__x86_64__)5#include "sanitizer_common/sanitizer_platform.h"6 7.file "asan_rtl_x86_64.S"8.att_syntax9 10#define NAME(n, reg, op, s, i) n##_##op##_##i##_##s##_##reg11 12#define FNAME(reg, op, s, i) NAME(__asan_check, reg, op, s, i)13#define RLABEL(reg, op, s, i) NAME(.return, reg, op, s, i)14#define CLABEL(reg, op, s, i) NAME(.check, reg, op, s, i)15#define FLABEL(reg, op, s, i) NAME(.fail, reg, op, s, i)16 17#define BEGINF(reg, op, s, i) \18.section .text.FNAME(reg, op, s, i),"ax",@progbits ;\19.globl FNAME(reg, op, s, i) ;\20.hidden FNAME(reg, op, s, i) ;\21ASM_TYPE_FUNCTION(FNAME(reg, op, s, i)) ;\22.cfi_startproc ;\23FNAME(reg, op, s, i): ;\24 25#define ENDF .cfi_endproc ;\26 27// Access check functions for 1,2 and 4 byte types, which require extra checks.28#define ASAN_MEMORY_ACCESS_INITIAL_CHECK_ADD(reg, op, s) \29 mov %##reg,%r10 ;\30 shr $0x3,%r10 ;\31 .if ASAN_SHADOW_OFFSET_CONST < 0x80000000 ;\32 movsbl ASAN_SHADOW_OFFSET_CONST(%r10),%r10d ;\33 .else ;\34 movabsq $ASAN_SHADOW_OFFSET_CONST,%r11 ;\35 movsbl (%r10,%r11),%r10d ;\36 .endif ;\37 test %r10d,%r10d ;\38 jne CLABEL(reg, op, s, add) ;\39RLABEL(reg, op, s, add): ;\40 retq ;\41 42#define ASAN_MEMORY_ACCESS_EXTRA_CHECK_1(reg, op, i) \43CLABEL(reg, op, 1, i): ;\44 mov %##reg,%r11 ;\45 and $0x7,%r11d ;\46 cmp %r10d,%r11d ;\47 jl RLABEL(reg, op, 1, i);\48 mov %##reg,%rdi ;\49 jmp __asan_report_##op##1_asm ;\50 51#define ASAN_MEMORY_ACCESS_EXTRA_CHECK_2(reg, op, i) \52CLABEL(reg, op, 2, i): ;\53 mov %##reg,%r11 ;\54 and $0x7,%r11d ;\55 add $0x1,%r11d ;\56 cmp %r10d,%r11d ;\57 jl RLABEL(reg, op, 2, i);\58 mov %##reg,%rdi ;\59 jmp __asan_report_##op##2_asm ;\60 61#define ASAN_MEMORY_ACCESS_EXTRA_CHECK_4(reg, op, i) \62CLABEL(reg, op, 4, i): ;\63 mov %##reg,%r11 ;\64 and $0x7,%r11d ;\65 add $0x3,%r11d ;\66 cmp %r10d,%r11d ;\67 jl RLABEL(reg, op, 4, i);\68 mov %##reg,%rdi ;\69 jmp __asan_report_##op##4_asm ;\70 71#define ASAN_MEMORY_ACCESS_CALLBACK_ADD_1(reg, op) \72BEGINF(reg, op, 1, add) ;\73 ASAN_MEMORY_ACCESS_INITIAL_CHECK_ADD(reg, op, 1) ;\74 ASAN_MEMORY_ACCESS_EXTRA_CHECK_1(reg, op, add) ;\75ENDF76 77#define ASAN_MEMORY_ACCESS_CALLBACK_ADD_2(reg, op) \78BEGINF(reg, op, 2, add) ;\79 ASAN_MEMORY_ACCESS_INITIAL_CHECK_ADD(reg, op, 2) ;\80 ASAN_MEMORY_ACCESS_EXTRA_CHECK_2(reg, op, add) ;\81ENDF82 83#define ASAN_MEMORY_ACCESS_CALLBACK_ADD_4(reg, op) \84BEGINF(reg, op, 4, add) ;\85 ASAN_MEMORY_ACCESS_INITIAL_CHECK_ADD(reg, op, 4) ;\86 ASAN_MEMORY_ACCESS_EXTRA_CHECK_4(reg, op, add) ;\87ENDF88 89// Access check functions for 8 and 16 byte types: no extra checks required.90#define ASAN_MEMORY_ACCESS_CHECK_ADD(reg, op, s, c) \91 mov %##reg,%r10 ;\92 shr $0x3,%r10 ;\93 .if ASAN_SHADOW_OFFSET_CONST < 0x80000000 ;\94 ##c $0x0,ASAN_SHADOW_OFFSET_CONST(%r10) ;\95 .else ;\96 movabsq $ASAN_SHADOW_OFFSET_CONST,%r11 ;\97 ##c $0x0,(%r10,%r11) ;\98 .endif ;\99 jne FLABEL(reg, op, s, add) ;\100 retq ;\101 102#define ASAN_MEMORY_ACCESS_FAIL(reg, op, s, i) \103FLABEL(reg, op, s, i): ;\104 mov %##reg,%rdi ;\105 jmp __asan_report_##op##s##_asm;\106 107#define ASAN_MEMORY_ACCESS_CALLBACK_ADD_8(reg, op) \108BEGINF(reg, op, 8, add) ;\109 ASAN_MEMORY_ACCESS_CHECK_ADD(reg, op, 8, cmpb) ;\110 ASAN_MEMORY_ACCESS_FAIL(reg, op, 8, add) ;\111ENDF112 113#define ASAN_MEMORY_ACCESS_CALLBACK_ADD_16(reg, op) \114BEGINF(reg, op, 16, add) ;\115 ASAN_MEMORY_ACCESS_CHECK_ADD(reg, op, 16, cmpw) ;\116 ASAN_MEMORY_ACCESS_FAIL(reg, op, 16, add) ;\117ENDF118 119#define ASAN_MEMORY_ACCESS_CALLBACKS_ADD(reg) \120ASAN_MEMORY_ACCESS_CALLBACK_ADD_1(reg, load) \121ASAN_MEMORY_ACCESS_CALLBACK_ADD_1(reg, store) \122ASAN_MEMORY_ACCESS_CALLBACK_ADD_2(reg, load) \123ASAN_MEMORY_ACCESS_CALLBACK_ADD_2(reg, store) \124ASAN_MEMORY_ACCESS_CALLBACK_ADD_4(reg, load) \125ASAN_MEMORY_ACCESS_CALLBACK_ADD_4(reg, store) \126ASAN_MEMORY_ACCESS_CALLBACK_ADD_8(reg, load) \127ASAN_MEMORY_ACCESS_CALLBACK_ADD_8(reg, store) \128ASAN_MEMORY_ACCESS_CALLBACK_ADD_16(reg, load) \129ASAN_MEMORY_ACCESS_CALLBACK_ADD_16(reg, store) \130 131 132// Instantiate all but R10 and R11 callbacks. We are using PLTSafe class with133// the intrinsic, which guarantees that the code generation will never emit134// R10 or R11 callback.135ASAN_MEMORY_ACCESS_CALLBACKS_ADD(RAX)136ASAN_MEMORY_ACCESS_CALLBACKS_ADD(RBX)137ASAN_MEMORY_ACCESS_CALLBACKS_ADD(RCX)138ASAN_MEMORY_ACCESS_CALLBACKS_ADD(RDX)139ASAN_MEMORY_ACCESS_CALLBACKS_ADD(RSI)140ASAN_MEMORY_ACCESS_CALLBACKS_ADD(RDI)141ASAN_MEMORY_ACCESS_CALLBACKS_ADD(RBP)142ASAN_MEMORY_ACCESS_CALLBACKS_ADD(R8)143ASAN_MEMORY_ACCESS_CALLBACKS_ADD(R9)144ASAN_MEMORY_ACCESS_CALLBACKS_ADD(R12)145ASAN_MEMORY_ACCESS_CALLBACKS_ADD(R13)146ASAN_MEMORY_ACCESS_CALLBACKS_ADD(R14)147ASAN_MEMORY_ACCESS_CALLBACKS_ADD(R15)148 149#endif150 151NO_EXEC_STACK_DIRECTIVE152