Files
clang-p2996/llvm/test/CodeGen/X86/base-pointer-and-cmpxchg.ll
Nick Desaulniers 3787ee4571 reland [IR] make -stack-alignment= into a module attr
Relands commit 433c8d950c with fixes for
MIPS.

Similar to D102742, specifying the stack alignment via CodegenOpts means
that this flag gets dropped during LTO, unless the command line is
re-specified as a plugin opt. Instead, encode this information as a
module level attribute so that we don't have to expose this llvm
internal flag when linking the Linux kernel with LTO.

Looks like external dependencies might need a fix:
* https://github.com/llvm-hs/llvm-hs/issues/345
* https://github.com/halide/Halide/issues/6079

Link: https://github.com/ClangBuiltLinux/linux/issues/1377

Reviewed By: tejohnson

Differential Revision: https://reviews.llvm.org/D103048
2021-06-08 10:59:46 -07:00

54 lines
2.7 KiB
LLVM

; RUN: llc -mtriple=x86_64-apple-macosx -mattr=+cx16 -x86-use-base-pointer=true -stackrealign %s -o - | FileCheck --check-prefix=CHECK --check-prefix=USE_BASE --check-prefix=USE_BASE_64 %s
; RUN: llc -mtriple=x86_64-apple-macosx -mattr=+cx16 -x86-use-base-pointer=false -stackrealign %s -o - | FileCheck --check-prefix=CHECK --check-prefix=DONT_USE_BASE %s
; RUN: llc -mtriple=x86_64-linux-gnux32 -mattr=+cx16 -x86-use-base-pointer=true -stackrealign %s -o - | FileCheck --check-prefix=CHECK --check-prefix=USE_BASE --check-prefix=USE_BASE_32 %s
; RUN: llc -mtriple=x86_64-linux-gnux32 -mattr=+cx16 -x86-use-base-pointer=false -stackrealign %s -o - | FileCheck --check-prefix=CHECK --check-prefix=DONT_USE_BASE %s
; This function uses dynamic allocated stack to force the use
; of a frame pointer.
; The inline asm clobbers a bunch of registers to make sure
; the frame pointer will need to be used (for spilling in that case).
;
; Then, we check that when we use rbx as the base pointer,
; we do not use cmpxchg, since using that instruction requires
; to clobbers rbx to set the arguments of the instruction and when
; rbx is used as the base pointer, RA cannot fix the code for us.
;
; CHECK-LABEL: cmp_and_swap16:
; Check that we actually use rbx.
; gnux32 use the 32bit variant of the registers.
; USE_BASE_64: movq %rsp, %rbx
; USE_BASE_32: movl %esp, %ebx
;
; Make sure the base pointer is saved before the rbx argument for
; cmpxchg16b is set.
;
; Because of how the test is written, we spill SAVE_rbx.
; However, it would have been perfectly fine to just keep it in register.
; USE_BASE: movq %rbx, [[SAVE_rbx_SLOT:[0-9]*\(%[er]bx\)]]
;
; SAVE_rbx must be in register before we clobber rbx.
; It is fine to use any register but rbx and the ones defined and use
; by cmpxchg. Since such regex would be complicated to write, just stick
; to the numbered registers. The bottom line is: if this test case fails
; because of that regex, this is likely just the regex being too conservative.
; USE_BASE: movq [[SAVE_rbx_SLOT]], [[SAVE_rbx:%r[0-9]+]]
;
; USE_BASE: movq {{[^ ]+}}, %rbx
; USE_BASE-NEXT: cmpxchg16b
; USE_BASE-NEXT: movq [[SAVE_rbx]], %rbx
;
; DONT_USE_BASE-NOT: movq %rsp, %rbx
; DONT_USE_BASE-NOT: movl %esp, %ebx
; DONT_USE_BASE: cmpxchg
define i1 @cmp_and_swap16(i128 %a, i128 %b, i128* %addr, i32 %n) {
%dummy = alloca i32, i32 %n
tail call void asm sideeffect "nop", "~{rax},~{rcx},~{rdx},~{rsi},~{rdi},~{rbp},~{r8},~{r9},~{r10},~{r11},~{r12},~{r13},~{r14},~{r15}"()
%cmp = cmpxchg i128* %addr, i128 %a, i128 %b seq_cst seq_cst
%res = extractvalue { i128, i1 } %cmp, 1
%idx = getelementptr i32, i32* %dummy, i32 5
store i32 %n, i32* %idx
ret i1 %res
}
!llvm.module.flags = !{!0}
!0 = !{i32 2, !"override-stack-alignment", i32 32}