xref: /freebsd/contrib/llvm-project/llvm/lib/Target/SystemZ/SystemZSubtarget.cpp (revision fe6060f10f634930ff71b7c50291ddc610da2475)
10b57cec5SDimitry Andric //===-- SystemZSubtarget.cpp - SystemZ subtarget information --------------===//
20b57cec5SDimitry Andric //
30b57cec5SDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
40b57cec5SDimitry Andric // See https://llvm.org/LICENSE.txt for license information.
50b57cec5SDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
60b57cec5SDimitry Andric //
70b57cec5SDimitry Andric //===----------------------------------------------------------------------===//
80b57cec5SDimitry Andric 
90b57cec5SDimitry Andric #include "SystemZSubtarget.h"
100b57cec5SDimitry Andric #include "MCTargetDesc/SystemZMCTargetDesc.h"
110b57cec5SDimitry Andric #include "llvm/IR/GlobalValue.h"
125ffd83dbSDimitry Andric #include "llvm/Target/TargetMachine.h"
130b57cec5SDimitry Andric 
140b57cec5SDimitry Andric using namespace llvm;
150b57cec5SDimitry Andric 
160b57cec5SDimitry Andric #define DEBUG_TYPE "systemz-subtarget"
170b57cec5SDimitry Andric 
180b57cec5SDimitry Andric #define GET_SUBTARGETINFO_TARGET_DESC
190b57cec5SDimitry Andric #define GET_SUBTARGETINFO_CTOR
200b57cec5SDimitry Andric #include "SystemZGenSubtargetInfo.inc"
210b57cec5SDimitry Andric 
220b57cec5SDimitry Andric static cl::opt<bool> UseSubRegLiveness(
230b57cec5SDimitry Andric     "systemz-subreg-liveness",
240b57cec5SDimitry Andric     cl::desc("Enable subregister liveness tracking for SystemZ (experimental)"),
250b57cec5SDimitry Andric     cl::Hidden);
260b57cec5SDimitry Andric 
270b57cec5SDimitry Andric // Pin the vtable to this file.
280b57cec5SDimitry Andric void SystemZSubtarget::anchor() {}
290b57cec5SDimitry Andric 
300b57cec5SDimitry Andric SystemZSubtarget &
310b57cec5SDimitry Andric SystemZSubtarget::initializeSubtargetDependencies(StringRef CPU, StringRef FS) {
325ffd83dbSDimitry Andric   StringRef CPUName = CPU;
330b57cec5SDimitry Andric   if (CPUName.empty())
340b57cec5SDimitry Andric     CPUName = "generic";
350b57cec5SDimitry Andric   // Parse features string.
36e8d8bef9SDimitry Andric   ParseSubtargetFeatures(CPUName, /*TuneCPU*/ CPUName, FS);
375ffd83dbSDimitry Andric 
385ffd83dbSDimitry Andric   // -msoft-float implies -mno-vx.
395ffd83dbSDimitry Andric   if (HasSoftFloat)
405ffd83dbSDimitry Andric     HasVector = false;
415ffd83dbSDimitry Andric 
42e8d8bef9SDimitry Andric   // -mno-vx implicitly disables all vector-related features.
43e8d8bef9SDimitry Andric   if (!HasVector) {
44e8d8bef9SDimitry Andric     HasVectorEnhancements1 = false;
45e8d8bef9SDimitry Andric     HasVectorEnhancements2 = false;
46e8d8bef9SDimitry Andric     HasVectorPackedDecimal = false;
47e8d8bef9SDimitry Andric     HasVectorPackedDecimalEnhancement = false;
48*fe6060f1SDimitry Andric     HasVectorPackedDecimalEnhancement2 = false;
49e8d8bef9SDimitry Andric   }
50e8d8bef9SDimitry Andric 
510b57cec5SDimitry Andric   return *this;
520b57cec5SDimitry Andric }
530b57cec5SDimitry Andric 
54*fe6060f1SDimitry Andric SystemZCallingConventionRegisters *
55*fe6060f1SDimitry Andric SystemZSubtarget::initializeSpecialRegisters() {
56*fe6060f1SDimitry Andric   if (isTargetXPLINK64())
57*fe6060f1SDimitry Andric     return new SystemZXPLINK64Registers;
58*fe6060f1SDimitry Andric   else if (isTargetELF())
59*fe6060f1SDimitry Andric     return new SystemZELFRegisters;
60*fe6060f1SDimitry Andric   else {
61*fe6060f1SDimitry Andric     llvm_unreachable("Invalid Calling Convention. Cannot initialize Special "
62*fe6060f1SDimitry Andric                      "Call Registers!");
63*fe6060f1SDimitry Andric   }
64*fe6060f1SDimitry Andric }
65*fe6060f1SDimitry Andric 
660b57cec5SDimitry Andric SystemZSubtarget::SystemZSubtarget(const Triple &TT, const std::string &CPU,
670b57cec5SDimitry Andric                                    const std::string &FS,
680b57cec5SDimitry Andric                                    const TargetMachine &TM)
69e8d8bef9SDimitry Andric     : SystemZGenSubtargetInfo(TT, CPU, /*TuneCPU*/ CPU, FS),
70e8d8bef9SDimitry Andric       HasDistinctOps(false), HasLoadStoreOnCond(false), HasHighWord(false),
71e8d8bef9SDimitry Andric       HasFPExtension(false), HasPopulationCount(false),
72e8d8bef9SDimitry Andric       HasMessageSecurityAssist3(false), HasMessageSecurityAssist4(false),
73e8d8bef9SDimitry Andric       HasResetReferenceBitsMultiple(false), HasFastSerialization(false),
74e8d8bef9SDimitry Andric       HasInterlockedAccess1(false), HasMiscellaneousExtensions(false),
750b57cec5SDimitry Andric       HasExecutionHint(false), HasLoadAndTrap(false),
760b57cec5SDimitry Andric       HasTransactionalExecution(false), HasProcessorAssist(false),
77*fe6060f1SDimitry Andric       HasDFPZonedConversion(false), HasEnhancedDAT2(false), HasVector(false),
78*fe6060f1SDimitry Andric       HasLoadStoreOnCond2(false), HasLoadAndZeroRightmostByte(false),
79*fe6060f1SDimitry Andric       HasMessageSecurityAssist5(false), HasDFPPackedConversion(false),
800b57cec5SDimitry Andric       HasMiscellaneousExtensions2(false), HasGuardedStorage(false),
810b57cec5SDimitry Andric       HasMessageSecurityAssist7(false), HasMessageSecurityAssist8(false),
820b57cec5SDimitry Andric       HasVectorEnhancements1(false), HasVectorPackedDecimal(false),
83*fe6060f1SDimitry Andric       HasInsertReferenceBitsMultiple(false), HasMiscellaneousExtensions3(false),
84*fe6060f1SDimitry Andric       HasMessageSecurityAssist9(false), HasVectorEnhancements2(false),
85*fe6060f1SDimitry Andric       HasVectorPackedDecimalEnhancement(false), HasEnhancedSort(false),
86*fe6060f1SDimitry Andric       HasDeflateConversion(false), HasVectorPackedDecimalEnhancement2(false),
87*fe6060f1SDimitry Andric       HasNNPAssist(false), HasBEAREnhancement(false),
88*fe6060f1SDimitry Andric       HasResetDATProtection(false), HasProcessorActivityInstrumentation(false),
89*fe6060f1SDimitry Andric       HasSoftFloat(false), TargetTriple(TT),
90*fe6060f1SDimitry Andric       SpecialRegisters(initializeSpecialRegisters()),
91*fe6060f1SDimitry Andric       InstrInfo(initializeSubtargetDependencies(CPU, FS)), TLInfo(TM, *this),
92*fe6060f1SDimitry Andric       TSInfo(), FrameLowering() {}
930b57cec5SDimitry Andric 
94*fe6060f1SDimitry Andric SystemZSubtarget::~SystemZSubtarget() { delete getSpecialRegisters(); }
950b57cec5SDimitry Andric 
960b57cec5SDimitry Andric bool SystemZSubtarget::enableSubRegLiveness() const {
970b57cec5SDimitry Andric   return UseSubRegLiveness;
980b57cec5SDimitry Andric }
990b57cec5SDimitry Andric 
1000b57cec5SDimitry Andric bool SystemZSubtarget::isPC32DBLSymbol(const GlobalValue *GV,
1010b57cec5SDimitry Andric                                        CodeModel::Model CM) const {
1025ffd83dbSDimitry Andric   // PC32DBL accesses require the low bit to be clear.
1035ffd83dbSDimitry Andric   //
1045ffd83dbSDimitry Andric   // FIXME: Explicitly check for functions: the datalayout is currently
1055ffd83dbSDimitry Andric   // missing information about function pointers.
1065ffd83dbSDimitry Andric   const DataLayout &DL = GV->getParent()->getDataLayout();
1075ffd83dbSDimitry Andric   if (GV->getPointerAlignment(DL) == 1 && !GV->getValueType()->isFunctionTy())
1080b57cec5SDimitry Andric     return false;
1090b57cec5SDimitry Andric 
1100b57cec5SDimitry Andric   // For the small model, all locally-binding symbols are in range.
1110b57cec5SDimitry Andric   if (CM == CodeModel::Small)
1120b57cec5SDimitry Andric     return TLInfo.getTargetMachine().shouldAssumeDSOLocal(*GV->getParent(), GV);
1130b57cec5SDimitry Andric 
1140b57cec5SDimitry Andric   // For Medium and above, assume that the symbol is not within the 4GB range.
1150b57cec5SDimitry Andric   // Taking the address of locally-defined text would be OK, but that
1160b57cec5SDimitry Andric   // case isn't easy to detect.
1170b57cec5SDimitry Andric   return false;
1180b57cec5SDimitry Andric }
119