Index: lib/Target/X86/AsmParser/X86AsmInstrumentation.cpp =================================================================== --- lib/Target/X86/AsmParser/X86AsmInstrumentation.cpp +++ lib/Target/X86/AsmParser/X86AsmInstrumentation.cpp @@ -177,13 +177,26 @@ MCStreamer &Out) override; }; -void X86AddressSanitizer64::InstrumentMemOperandImpl( - X86Operand *Op, unsigned AccessSize, bool IsWrite, MCContext &Ctx, - MCStreamer &Out) { +void X86AddressSanitizer64::InstrumentMemOperandImpl(X86Operand *Op, + unsigned AccessSize, + bool IsWrite, + MCContext &Ctx, + MCStreamer &Out) { // FIXME: emit .cfi directives for correct stack unwinding. - // Set %rsp below current red zone (128 bytes wide) - EmitInstruction(Out, MCInstBuilder(X86::SUB64ri32).addReg(X86::RSP) - .addReg(X86::RSP).addImm(128)); + + // Set %rsp below current red zone (128 bytes wide) LEA instruction + // should be used as it don't affect flags. + { + MCInst Inst; + Inst.setOpcode(X86::LEA64r); + Inst.addOperand(MCOperand::CreateReg(X86::RSP)); + + const MCExpr *Disp = MCConstantExpr::Create(-128, Ctx); + X86Operand *Op = + X86Operand::CreateMem(0, Disp, X86::RSP, 0, 1, SMLoc(), SMLoc()); + Op->addMemOperands(Inst, 5); + EmitInstruction(Out, Inst); + } EmitInstruction(Out, MCInstBuilder(X86::PUSH64r).addReg(X86::RDI)); { MCInst Inst; @@ -200,8 +213,19 @@ EmitInstruction(Out, MCInstBuilder(X86::CALL64pcrel32).addExpr(FuncExpr)); } EmitInstruction(Out, MCInstBuilder(X86::POP64r).addReg(X86::RDI)); - EmitInstruction(Out, MCInstBuilder(X86::ADD64ri32).addReg(X86::RSP) - .addReg(X86::RSP).addImm(128)); + + // Restore old %rsp value. + { + MCInst Inst; + Inst.setOpcode(X86::LEA64r); + Inst.addOperand(MCOperand::CreateReg(X86::RSP)); + + const MCExpr *Disp = MCConstantExpr::Create(128, Ctx); + X86Operand *Op = + X86Operand::CreateMem(0, Disp, X86::RSP, 0, 1, SMLoc(), SMLoc()); + Op->addMemOperands(Inst, 5); + EmitInstruction(Out, Inst); + } } } // End anonymous namespace Index: test/Instrumentation/AddressSanitizer/X86/asm_mov.ll =================================================================== --- test/Instrumentation/AddressSanitizer/X86/asm_mov.ll +++ test/Instrumentation/AddressSanitizer/X86/asm_mov.ll @@ -4,19 +4,19 @@ target triple = "x86_64-unknown-linux-gnu" ; CHECK-LABEL: mov1b -; CHECK: subq $128, %rsp +; CHECK: leaq -128(%rsp), %rsp ; CHECK-NEXT: pushq %rdi ; CHECK-NEXT: leaq {{.*}}, %rdi ; CHECK-NEXT: callq __sanitizer_sanitize_load1@PLT ; CHECK-NEXT: popq %rdi -; CHECK-NEXT: addq $128, %rsp +; CHECK-NEXT: leaq 128(%rsp), %rsp -; CHECK: subq $128, %rsp +; CHECK: leaq -128(%rsp), %rsp ; CHECK-NEXT: pushq %rdi ; CHECK-NEXT: leaq {{.*}}, %rdi ; CHECK-NEXT: callq __sanitizer_sanitize_store1@PLT ; CHECK-NEXT: popq %rdi -; CHECK-NEXT: addq $128, %rsp +; CHECK-NEXT: leaq 128(%rsp), %rsp ; CHECK: movb {{.*}}, {{.*}} define void @mov1b(i8* %dst, i8* %src) #0 { @@ -26,19 +26,19 @@ } ; CHECK-LABEL: mov2b -; CHECK: subq $128, %rsp +; CHECK: leaq -128(%rsp), %rsp ; CHECK-NEXT: pushq %rdi ; CHECK-NEXT: leaq {{.*}}, %rdi ; CHECK-NEXT: callq __sanitizer_sanitize_load2@PLT ; CHECK-NEXT: popq %rdi -; CHECK-NEXT: addq $128, %rsp +; CHECK-NEXT: leaq 128(%rsp), %rsp -; CHECK: subq $128, %rsp +; CHECK: leaq -128(%rsp), %rsp ; CHECK-NEXT: pushq %rdi ; CHECK-NEXT: leaq {{.*}}, %rdi ; CHECK-NEXT: callq __sanitizer_sanitize_store2@PLT ; CHECK-NEXT: popq %rdi -; CHECK-NEXT: addq $128, %rsp +; CHECK-NEXT: leaq 128(%rsp), %rsp ; CHECK: movw {{.*}}, {{.*}} define void @mov2b(i16* %dst, i16* %src) #0 { @@ -48,19 +48,19 @@ } ; CHECK-LABEL: mov4b -; CHECK: subq $128, %rsp +; CHECK: leaq -128(%rsp), %rsp ; CHECK-NEXT: pushq %rdi ; CHECK-NEXT: leaq {{.*}}, %rdi ; CHECK-NEXT: callq __sanitizer_sanitize_load4@PLT ; CHECK-NEXT: popq %rdi -; CHECK-NEXT: addq $128, %rsp +; CHECK-NEXT: leaq 128(%rsp), %rsp -; CHECK: subq $128, %rsp +; CHECK: leaq -128(%rsp), %rsp ; CHECK-NEXT: pushq %rdi ; CHECK-NEXT: leaq {{.*}}, %rdi ; CHECK-NEXT: callq __sanitizer_sanitize_store4@PLT ; CHECK-NEXT: popq %rdi -; CHECK-NEXT: addq $128, %rsp +; CHECK-NEXT: leaq 128(%rsp), %rsp ; CHECK: movl {{.*}}, {{.*}} define void @mov4b(i32* %dst, i32* %src) #0 { @@ -70,19 +70,19 @@ } ; CHECK-LABEL: mov8b -; CHECK: subq $128, %rsp +; CHECK: leaq -128(%rsp), %rsp ; CHECK-NEXT: pushq %rdi ; CHECK-NEXT: leaq {{.*}}, %rdi ; CHECK-NEXT: callq __sanitizer_sanitize_load8@PLT ; CHECK-NEXT: popq %rdi -; CHECK-NEXT: addq $128, %rsp +; CHECK-NEXT: leaq 128(%rsp), %rsp -; CHECK: subq $128, %rsp +; CHECK: leaq -128(%rsp), %rsp ; CHECK-NEXT: pushq %rdi ; CHECK-NEXT: leaq {{.*}}, %rdi ; CHECK-NEXT: callq __sanitizer_sanitize_store8@PLT ; CHECK-NEXT: popq %rdi -; CHECK-NEXT: addq $128, %rsp +; CHECK-NEXT: leaq 128(%rsp), %rsp ; CHECK: movq {{.*}}, {{.*}} define void @mov8b(i64* %dst, i64* %src) #0 { @@ -92,19 +92,19 @@ } ; CHECK-LABEL: mov16b -; CHECK: subq $128, %rsp +; CHECK: leaq -128(%rsp), %rsp ; CHECK-NEXT: pushq %rdi ; CHECK-NEXT: leaq {{.*}}, %rdi ; CHECK-NEXT: callq __sanitizer_sanitize_load16@PLT ; CHECK-NEXT: popq %rdi -; CHECK-NEXT: addq $128, %rsp +; CHECK-NEXT: leaq 128(%rsp), %rsp -; CHECK: subq $128, %rsp +; CHECK: leaq -128(%rsp), %rsp ; CHECK-NEXT: pushq %rdi ; CHECK-NEXT: leaq {{.*}}, %rdi ; CHECK-NEXT: callq __sanitizer_sanitize_store16@PLT ; CHECK-NEXT: popq %rdi -; CHECK-NEXT: addq $128, %rsp +; CHECK-NEXT: leaq 128(%rsp), %rsp ; CHECK: movaps {{.*}}, {{.*}} define void @mov16b(<2 x i64>* %dst, <2 x i64>* %src) #0 { Index: test/Instrumentation/AddressSanitizer/X86/asm_mov.s =================================================================== --- test/Instrumentation/AddressSanitizer/X86/asm_mov.s +++ test/Instrumentation/AddressSanitizer/X86/asm_mov.s @@ -6,21 +6,21 @@ .type mov1b,@function # CHECK-LABEL: mov1b: # -# CHECK: subq $128, %rsp +# CHECK: leaq -128(%rsp), %rsp # CHECK-NEXT: pushq %rdi # CHECK-NEXT: leaq (%rsi), %rdi # CHECK-NEXT: callq __sanitizer_sanitize_load1@PLT # CHECK-NEXT: popq %rdi -# CHECK-NEXT: addq $128, %rsp +# CHECK-NEXT: leaq 128(%rsp), %rsp # # CHECK-NEXT: movb (%rsi), %al # -# CHECK-NEXT: subq $128, %rsp +# CHECK-NEXT: leaq -128(%rsp), %rsp # CHECK-NEXT: pushq %rdi # CHECK-NEXT: leaq (%rdi), %rdi # CHECK-NEXT: callq __sanitizer_sanitize_store1@PLT # CHECK-NEXT: popq %rdi -# CHECK-NEXT: addq $128, %rsp +# CHECK-NEXT: leaq 128(%rsp), %rsp # # CHECK-NEXT: movb %al, (%rdi) mov1b: # @mov1b @@ -41,21 +41,21 @@ .type mov16b,@function # CHECK-LABEL: mov16b: # -# CHECK: subq $128, %rsp +# CHECK: leaq -128(%rsp), %rsp # CHECK-NEXT: pushq %rdi # CHECK-NEXT: leaq (%rsi), %rdi # CHECK-NEXT: callq __sanitizer_sanitize_load16@PLT # CHECK-NEXT: popq %rdi -# CHECK-NEXT: addq $128, %rsp +# CHECK-NEXT: leaq 128(%rsp), %rsp # # CHECK-NEXT: movaps (%rsi), %xmm0 # -# CHECK-NEXT: subq $128, %rsp +# CHECK-NEXT: leaq -128(%rsp), %rsp # CHECK-NEXT: pushq %rdi # CHECK-NEXT: leaq (%rdi), %rdi # CHECK-NEXT: callq __sanitizer_sanitize_store16@PLT # CHECK-NEXT: popq %rdi -# CHECK-NEXT: addq $128, %rsp +# CHECK-NEXT: leaq 128(%rsp), %rsp # # CHECK-NEXT: movaps %xmm0, (%rdi) mov16b: # @mov16b Index: test/Instrumentation/AddressSanitizer/X86/asm_swap_intel.s =================================================================== --- test/Instrumentation/AddressSanitizer/X86/asm_swap_intel.s +++ test/Instrumentation/AddressSanitizer/X86/asm_swap_intel.s @@ -6,39 +6,39 @@ .type swap,@function # CHECK-LABEL: swap: # -# CHECK: subq $128, %rsp +# CHECK: leaq -128(%rsp), %rsp # CHECK-NEXT: pushq %rdi # CHECK-NEXT: leaq (%rcx), %rdi # CHECK-NEXT: callq __sanitizer_sanitize_load8@PLT # CHECK-NEXT: popq %rdi -# CHECK-NEXT: addq $128, %rsp +# CHECK-NEXT: leaq 128(%rsp), %rsp # # CHECK-NEXT: movq (%rcx), %rax # -# CHECK-NEXT: subq $128, %rsp +# CHECK-NEXT: leaq -128(%rsp), %rsp # CHECK-NEXT: pushq %rdi # CHECK-NEXT: leaq (%rdx), %rdi # CHECK-NEXT: callq __sanitizer_sanitize_load8@PLT # CHECK-NEXT: popq %rdi -# CHECK-NEXT: addq $128, %rsp +# CHECK-NEXT: leaq 128(%rsp), %rsp # # CHECK-NEXT: movq (%rdx), %rbx # -# CHECK: subq $128, %rsp +# CHECK: leaq -128(%rsp), %rsp # CHECK-NEXT: pushq %rdi # CHECK-NEXT: leaq (%rcx), %rdi # CHECK-NEXT: callq __sanitizer_sanitize_store8@PLT # CHECK-NEXT: popq %rdi -# CHECK-NEXT: addq $128, %rsp +# CHECK-NEXT: leaq 128(%rsp), %rsp # # CHECK-NEXT: movq %rbx, (%rcx) # -# CHECK-NEXT: subq $128, %rsp +# CHECK-NEXT: leaq -128(%rsp), %rsp # CHECK-NEXT: pushq %rdi # CHECK-NEXT: leaq (%rdx), %rdi # CHECK-NEXT: callq __sanitizer_sanitize_store8@PLT # CHECK-NEXT: popq %rdi -# CHECK-NEXT: addq $128, %rsp +# CHECK-NEXT: leaq 128(%rsp), %rsp # # CHECK-NEXT: movq %rax, (%rdx) swap: # @swap