diff options
author | Dimitry Andric <dim@FreeBSD.org> | 2017-12-18 20:10:56 +0000 |
---|---|---|
committer | Dimitry Andric <dim@FreeBSD.org> | 2017-12-18 20:10:56 +0000 |
commit | 044eb2f6afba375a914ac9d8024f8f5142bb912e (patch) | |
tree | 1475247dc9f9fe5be155ebd4c9069c75aadf8c20 /lib/Target/SystemZ/SystemZTargetMachine.cpp | |
parent | eb70dddbd77e120e5d490bd8fbe7ff3f8fa81c6b (diff) |
Notes
Diffstat (limited to 'lib/Target/SystemZ/SystemZTargetMachine.cpp')
-rw-r--r-- | lib/Target/SystemZ/SystemZTargetMachine.cpp | 50 |
1 files changed, 45 insertions, 5 deletions
diff --git a/lib/Target/SystemZ/SystemZTargetMachine.cpp b/lib/Target/SystemZ/SystemZTargetMachine.cpp index 025bf73d2df0..e74d68182949 100644 --- a/lib/Target/SystemZ/SystemZTargetMachine.cpp +++ b/lib/Target/SystemZ/SystemZTargetMachine.cpp @@ -18,12 +18,12 @@ #include "llvm/ADT/StringRef.h" #include "llvm/Analysis/TargetTransformInfo.h" #include "llvm/CodeGen/Passes.h" +#include "llvm/CodeGen/TargetLoweringObjectFile.h" #include "llvm/CodeGen/TargetLoweringObjectFileImpl.h" #include "llvm/CodeGen/TargetPassConfig.h" #include "llvm/IR/DataLayout.h" #include "llvm/Support/CodeGen.h" #include "llvm/Support/TargetRegistry.h" -#include "llvm/Target/TargetLoweringObjectFile.h" #include "llvm/Transforms/Scalar.h" #include <string> @@ -99,14 +99,54 @@ static Reloc::Model getEffectiveRelocModel(Optional<Reloc::Model> RM) { return *RM; } +// For SystemZ we define the models as follows: +// +// Small: BRASL can call any function and will use a stub if necessary. +// Locally-binding symbols will always be in range of LARL. +// +// Medium: BRASL can call any function and will use a stub if necessary. +// GOT slots and locally-defined text will always be in range +// of LARL, but other symbols might not be. +// +// Large: Equivalent to Medium for now. +// +// Kernel: Equivalent to Medium for now. +// +// This means that any PIC module smaller than 4GB meets the +// requirements of Small, so Small seems like the best default there. +// +// All symbols bind locally in a non-PIC module, so the choice is less +// obvious. There are two cases: +// +// - When creating an executable, PLTs and copy relocations allow +// us to treat external symbols as part of the executable. +// Any executable smaller than 4GB meets the requirements of Small, +// so that seems like the best default. +// +// - When creating JIT code, stubs will be in range of BRASL if the +// image is less than 4GB in size. GOT entries will likewise be +// in range of LARL. However, the JIT environment has no equivalent +// of copy relocs, so locally-binding data symbols might not be in +// the range of LARL. We need the Medium model in that case. +static CodeModel::Model getEffectiveCodeModel(Optional<CodeModel::Model> CM, + Reloc::Model RM, bool JIT) { + if (CM) + return *CM; + if (JIT) + return RM == Reloc::PIC_ ? CodeModel::Small : CodeModel::Medium; + return CodeModel::Small; +} + SystemZTargetMachine::SystemZTargetMachine(const Target &T, const Triple &TT, StringRef CPU, StringRef FS, const TargetOptions &Options, Optional<Reloc::Model> RM, - CodeModel::Model CM, - CodeGenOpt::Level OL) - : LLVMTargetMachine(T, computeDataLayout(TT, CPU, FS), TT, CPU, FS, Options, - getEffectiveRelocModel(RM), CM, OL), + Optional<CodeModel::Model> CM, + CodeGenOpt::Level OL, bool JIT) + : LLVMTargetMachine( + T, computeDataLayout(TT, CPU, FS), TT, CPU, FS, Options, + getEffectiveRelocModel(RM), + getEffectiveCodeModel(CM, getEffectiveRelocModel(RM), JIT), OL), TLOF(llvm::make_unique<TargetLoweringObjectFileELF>()), Subtarget(TT, CPU, FS, *this) { initAsmInfo(); |