diff --git a/llvm/lib/Target/X86/X86Subtarget.cpp b/llvm/lib/Target/X86/X86Subtarget.cpp --- a/llvm/lib/Target/X86/X86Subtarget.cpp +++ b/llvm/lib/Target/X86/X86Subtarget.cpp @@ -95,12 +95,17 @@ case CodeModel::Large: return X86II::MO_GOTOFF; - // Medium is a hybrid: RIP-rel for code, GOTOFF for DSO local data. + // Medium is a hybrid: RIP-rel for code and non-large data, GOTOFF for + // remaining DSO local data. case CodeModel::Medium: // Constant pool and jump table handling pass a nullptr to this // function so we need to use isa_and_nonnull. if (isa_and_nonnull(GV)) return X86II::MO_NO_FLAG; // All code is RIP-relative + if (auto *GVar = dyn_cast_or_null(GV)) { + if (!TM.isLargeData(GVar)) + return X86II::MO_NO_FLAG; + } return X86II::MO_GOTOFF; // Local symbols use GOTOFF. } llvm_unreachable("invalid code model"); diff --git a/llvm/test/CodeGen/X86/code-model-elf.ll b/llvm/test/CodeGen/X86/code-model-elf.ll --- a/llvm/test/CodeGen/X86/code-model-elf.ll +++ b/llvm/test/CodeGen/X86/code-model-elf.ll @@ -1,4 +1,4 @@ -; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py +; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --no_x86_scrub_sp ; Run with --no_x86_scrub_rip because we care a lot about how globals are ; accessed in the code model. @@ -6,9 +6,12 @@ ; RUN: llc -verify-machineinstrs < %s -relocation-model=static -code-model=medium | FileCheck %s --check-prefix=CHECK --check-prefix=MEDIUM-STATIC ; RUN: llc -verify-machineinstrs < %s -relocation-model=static -code-model=large | FileCheck %s --check-prefix=CHECK --check-prefix=LARGE-STATIC ; RUN: llc -verify-machineinstrs < %s -relocation-model=pic -code-model=small | FileCheck %s --check-prefix=CHECK --check-prefix=SMALL-PIC +; RUN: llc -verify-machineinstrs < %s -relocation-model=pic -code-model=medium -large-data-threshold=1000 | FileCheck %s --check-prefix=CHECK --check-prefix=MEDIUM-SMALL-DATA-PIC ; RUN: llc -verify-machineinstrs < %s -relocation-model=pic -code-model=medium | FileCheck %s --check-prefix=CHECK --check-prefix=MEDIUM-PIC ; RUN: llc -verify-machineinstrs < %s -relocation-model=pic -code-model=large | FileCheck %s --check-prefix=CHECK --check-prefix=LARGE-PIC +; FIXME: small pic and medium pic w/ big enough large data threshold should be equivalent + ; Generated from this C source: ; ; static int static_data[10]; @@ -62,6 +65,11 @@ ; SMALL-PIC-NEXT: leaq static_data(%rip), %rax ; SMALL-PIC-NEXT: retq ; +; MEDIUM-SMALL-DATA-PIC-LABEL: lea_static_data: +; MEDIUM-SMALL-DATA-PIC: # %bb.0: +; MEDIUM-SMALL-DATA-PIC-NEXT: leaq static_data(%rip), %rax +; MEDIUM-SMALL-DATA-PIC-NEXT: retq +; ; MEDIUM-PIC-LABEL: lea_static_data: ; MEDIUM-PIC: # %bb.0: ; MEDIUM-PIC-NEXT: leaq _GLOBAL_OFFSET_TABLE_(%rip), %rcx @@ -102,6 +110,11 @@ ; SMALL-PIC-NEXT: leaq global_data(%rip), %rax ; SMALL-PIC-NEXT: retq ; +; MEDIUM-SMALL-DATA-PIC-LABEL: lea_global_data: +; MEDIUM-SMALL-DATA-PIC: # %bb.0: +; MEDIUM-SMALL-DATA-PIC-NEXT: leaq global_data(%rip), %rax +; MEDIUM-SMALL-DATA-PIC-NEXT: retq +; ; MEDIUM-PIC-LABEL: lea_global_data: ; MEDIUM-PIC: # %bb.0: ; MEDIUM-PIC-NEXT: leaq _GLOBAL_OFFSET_TABLE_(%rip), %rcx @@ -142,6 +155,11 @@ ; SMALL-PIC-NEXT: movq extern_data@GOTPCREL(%rip), %rax ; SMALL-PIC-NEXT: retq ; +; MEDIUM-SMALL-DATA-PIC-LABEL: lea_extern_data: +; MEDIUM-SMALL-DATA-PIC: # %bb.0: +; MEDIUM-SMALL-DATA-PIC-NEXT: movq extern_data@GOTPCREL(%rip), %rax +; MEDIUM-SMALL-DATA-PIC-NEXT: retq +; ; MEDIUM-PIC-LABEL: lea_extern_data: ; MEDIUM-PIC: # %bb.0: ; MEDIUM-PIC-NEXT: movq extern_data@GOTPCREL(%rip), %rax @@ -180,6 +198,13 @@ ; SMALL-PIC-NEXT: leaq unknown_size_data(%rip), %rax ; SMALL-PIC-NEXT: retq ; +; MEDIUM-SMALL-DATA-PIC-LABEL: lea_unknown_size_data: +; MEDIUM-SMALL-DATA-PIC: # %bb.0: +; MEDIUM-SMALL-DATA-PIC-NEXT: leaq _GLOBAL_OFFSET_TABLE_(%rip), %rcx +; MEDIUM-SMALL-DATA-PIC-NEXT: movabsq $unknown_size_data@GOTOFF, %rax +; MEDIUM-SMALL-DATA-PIC-NEXT: addq %rcx, %rax +; MEDIUM-SMALL-DATA-PIC-NEXT: retq +; ; MEDIUM-PIC-LABEL: lea_unknown_size_data: ; MEDIUM-PIC: # %bb.0: ; MEDIUM-PIC-NEXT: leaq _GLOBAL_OFFSET_TABLE_(%rip), %rcx @@ -222,6 +247,12 @@ ; SMALL-PIC-NEXT: movl global_data+8(%rip), %eax ; SMALL-PIC-NEXT: retq ; +; MEDIUM-SMALL-DATA-PIC-LABEL: load_global_data: +; MEDIUM-SMALL-DATA-PIC: # %bb.0: +; MEDIUM-SMALL-DATA-PIC-NEXT: leaq global_data(%rip), %rax +; MEDIUM-SMALL-DATA-PIC-NEXT: movl 8(%rax), %eax +; MEDIUM-SMALL-DATA-PIC-NEXT: retq +; ; MEDIUM-PIC-LABEL: load_global_data: ; MEDIUM-PIC: # %bb.0: ; MEDIUM-PIC-NEXT: leaq _GLOBAL_OFFSET_TABLE_(%rip), %rax @@ -267,6 +298,12 @@ ; SMALL-PIC-NEXT: movl 8(%rax), %eax ; SMALL-PIC-NEXT: retq ; +; MEDIUM-SMALL-DATA-PIC-LABEL: load_extern_data: +; MEDIUM-SMALL-DATA-PIC: # %bb.0: +; MEDIUM-SMALL-DATA-PIC-NEXT: movq extern_data@GOTPCREL(%rip), %rax +; MEDIUM-SMALL-DATA-PIC-NEXT: movl 8(%rax), %eax +; MEDIUM-SMALL-DATA-PIC-NEXT: retq +; ; MEDIUM-PIC-LABEL: load_extern_data: ; MEDIUM-PIC: # %bb.0: ; MEDIUM-PIC-NEXT: movq extern_data@GOTPCREL(%rip), %rax @@ -310,6 +347,13 @@ ; SMALL-PIC-NEXT: movl unknown_size_data+8(%rip), %eax ; SMALL-PIC-NEXT: retq ; +; MEDIUM-SMALL-DATA-PIC-LABEL: load_unknown_size_data: +; MEDIUM-SMALL-DATA-PIC: # %bb.0: +; MEDIUM-SMALL-DATA-PIC-NEXT: leaq _GLOBAL_OFFSET_TABLE_(%rip), %rax +; MEDIUM-SMALL-DATA-PIC-NEXT: movabsq $unknown_size_data@GOTOFF, %rcx +; MEDIUM-SMALL-DATA-PIC-NEXT: movl 8(%rax,%rcx), %eax +; MEDIUM-SMALL-DATA-PIC-NEXT: retq +; ; MEDIUM-PIC-LABEL: load_unknown_size_data: ; MEDIUM-PIC: # %bb.0: ; MEDIUM-PIC-NEXT: leaq _GLOBAL_OFFSET_TABLE_(%rip), %rax @@ -367,6 +411,11 @@ ; SMALL-PIC-NEXT: leaq static_fn(%rip), %rax ; SMALL-PIC-NEXT: retq ; +; MEDIUM-SMALL-DATA-PIC-LABEL: lea_static_fn: +; MEDIUM-SMALL-DATA-PIC: # %bb.0: +; MEDIUM-SMALL-DATA-PIC-NEXT: leaq static_fn(%rip), %rax +; MEDIUM-SMALL-DATA-PIC-NEXT: retq +; ; MEDIUM-PIC-LABEL: lea_static_fn: ; MEDIUM-PIC: # %bb.0: ; MEDIUM-PIC-NEXT: leaq static_fn(%rip), %rax @@ -405,6 +454,11 @@ ; SMALL-PIC-NEXT: leaq global_fn(%rip), %rax ; SMALL-PIC-NEXT: retq ; +; MEDIUM-SMALL-DATA-PIC-LABEL: lea_global_fn: +; MEDIUM-SMALL-DATA-PIC: # %bb.0: +; MEDIUM-SMALL-DATA-PIC-NEXT: leaq global_fn(%rip), %rax +; MEDIUM-SMALL-DATA-PIC-NEXT: retq +; ; MEDIUM-PIC-LABEL: lea_global_fn: ; MEDIUM-PIC: # %bb.0: ; MEDIUM-PIC-NEXT: leaq global_fn(%rip), %rax @@ -443,6 +497,11 @@ ; SMALL-PIC-NEXT: movq extern_fn@GOTPCREL(%rip), %rax ; SMALL-PIC-NEXT: retq ; +; MEDIUM-SMALL-DATA-PIC-LABEL: lea_extern_fn: +; MEDIUM-SMALL-DATA-PIC: # %bb.0: +; MEDIUM-SMALL-DATA-PIC-NEXT: movq extern_fn@GOTPCREL(%rip), %rax +; MEDIUM-SMALL-DATA-PIC-NEXT: retq +; ; MEDIUM-PIC-LABEL: lea_extern_fn: ; MEDIUM-PIC: # %bb.0: ; MEDIUM-PIC-NEXT: movq extern_fn@GOTPCREL(%rip), %rax @@ -516,6 +575,13 @@ ; SMALL-PIC-NEXT: addss {{\.?LCPI[0-9]+_[0-9]+}}(%rip), %xmm0 ; SMALL-PIC-NEXT: retq ; +; MEDIUM-SMALL-DATA-PIC-LABEL: load_constant_pool: +; MEDIUM-SMALL-DATA-PIC: # %bb.0: +; MEDIUM-SMALL-DATA-PIC-NEXT: leaq _GLOBAL_OFFSET_TABLE_(%rip), %rax +; MEDIUM-SMALL-DATA-PIC-NEXT: movabsq ${{\.?LCPI[0-9]+_[0-9]+}}@GOTOFF, %rcx +; MEDIUM-SMALL-DATA-PIC-NEXT: addss (%rax,%rcx), %xmm0 +; MEDIUM-SMALL-DATA-PIC-NEXT: retq +; ; MEDIUM-PIC-LABEL: load_constant_pool: ; MEDIUM-PIC: # %bb.0: ; MEDIUM-PIC-NEXT: leaq _GLOBAL_OFFSET_TABLE_(%rip), %rax