From 55a90ab4ef8db0c23127f297b49a0ea3ed8e0421 Mon Sep 17 00:00:00 2001 From: Eric Christopher Date: Fri, 26 Sep 2014 01:44:08 +0000 Subject: [PATCH] Add the first backend support for on demand subtarget creation based on the Function. This is currently used to implement mips16 support in the mips backend via the existing module pass resetting the subtarget. Things to note: a) This involved running resetTargetOptions before creating a new subtarget so that code generation options like soft-float could be recognized when creating the new subtarget. This is to deal with initialization code in isel lowering that only paid attention to the initial value. b) Many of the existing testcases weren't using the soft-float feature correctly. I've corrected these based on the check values assuming that was the desired behavior. c) The mips port now pays attention to the target-cpu and target-features strings when generating code for a particular function. I've removed these from one function where the requested cpu and features didn't match the check lines in the testcase. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@218492 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/Target/Mips/MipsTargetMachine.cpp | 54 ++++++++++++++++++++------- lib/Target/Mips/MipsTargetMachine.h | 5 +++ test/CodeGen/Mips/fp16instrinsmc.ll | 2 +- test/CodeGen/Mips/hfptrcall.ll | 4 +- test/CodeGen/Mips/nomips16.ll | 4 +- test/CodeGen/Mips/seleq.ll | 2 +- 6 files changed, 52 insertions(+), 19 deletions(-) diff --git a/lib/Target/Mips/MipsTargetMachine.cpp b/lib/Target/Mips/MipsTargetMachine.cpp index 79d1b4b13e9..afa60d2340e 100644 --- a/lib/Target/Mips/MipsTargetMachine.cpp +++ b/lib/Target/Mips/MipsTargetMachine.cpp @@ -56,7 +56,8 @@ MipsTargetMachine::MipsTargetMachine(const Target &T, StringRef TT, Reloc::Model RM, CodeModel::Model CM, CodeGenOpt::Level OL, bool isLittle) : LLVMTargetMachine(T, TT, CPU, FS, Options, RM, CM, OL), - Subtarget(nullptr), DefaultSubtarget(TT, CPU, FS, isLittle, this), + isLittle(isLittle), Subtarget(nullptr), + DefaultSubtarget(TT, CPU, FS, isLittle, this), NoMips16Subtarget(TT, CPU, FS.empty() ? "-mips16" : FS.str() + ",-mips16", isLittle, this), Mips16Subtarget(TT, CPU, FS.empty() ? "+mips16" : FS.str() + ",+mips16", @@ -83,20 +84,47 @@ MipselTargetMachine(const Target &T, StringRef TT, CodeGenOpt::Level OL) : MipsTargetMachine(T, TT, CPU, FS, Options, RM, CM, OL, true) {} +const MipsSubtarget * +MipsTargetMachine::getSubtargetImpl(const Function &F) const override { + AttributeSet FnAttrs = F.getAttributes(); + Attribute CPUAttr = + FnAttrs.getAttribute(AttributeSet::FunctionIndex, "target-cpu"); + Attribute FSAttr = + FnAttrs.getAttribute(AttributeSet::FunctionIndex, "target-features"); + + std::string CPU = !CPUAttr.hasAttribute(Attribute::None) + ? CPUAttr.getValueAsString().str() + : TargetCPU; + std::string FS = !FSAttr.hasAttribute(Attribute::None) + ? FSAttr.getValueAsString().str() + : TargetFS; + bool hasMips16Attr = + !FnAttrs.getAttribute(AttributeSet::FunctionIndex, "mips16") + .hasAttribute(Attribute::None); + bool hasNoMips16Attr = + !FnAttrs.getAttribute(AttributeSet::FunctionIndex, "nomips16") + .hasAttribute(Attribute::None); + + if (hasMips16Attr) + FS += FS.empty() ? "+mips16" : ",+mips16"; + else if (hasNoMips16Attr) + FS += FS.empty() ? "-mips16" : ",-mips16"; + + auto &I = SubtargetMap[CPU + FS]; + if (!I) { + // This needs to be done before we create a new subtarget since any + // creation will depend on the TM and the code generation flags on the + // function that reside in TargetOptions. + resetTargetOptions(F); + I = make_unique(TargetTriple, CPU, FS, isLittle, this); + } + return I.get(); +} + void MipsTargetMachine::resetSubtarget(MachineFunction *MF) { DEBUG(dbgs() << "resetSubtarget\n"); - AttributeSet FnAttrs = MF->getFunction()->getAttributes(); - bool Mips16Attr = FnAttrs.hasAttribute(AttributeSet::FunctionIndex, "mips16"); - bool NoMips16Attr = - FnAttrs.hasAttribute(AttributeSet::FunctionIndex, "nomips16"); - assert(!(Mips16Attr && NoMips16Attr) && - "mips16 and nomips16 specified on the same function"); - if (Mips16Attr) - Subtarget = &Mips16Subtarget; - else if (NoMips16Attr) - Subtarget = &NoMips16Subtarget; - else - Subtarget = &DefaultSubtarget; + + Subtarget = const_cast(getSubtargetImpl(MF->getFunction())); MF->setSubtarget(Subtarget); return; } diff --git a/lib/Target/Mips/MipsTargetMachine.h b/lib/Target/Mips/MipsTargetMachine.h index 58400cd1b48..5ddbbcccfbb 100644 --- a/lib/Target/Mips/MipsTargetMachine.h +++ b/lib/Target/Mips/MipsTargetMachine.h @@ -25,11 +25,14 @@ class formatted_raw_ostream; class MipsRegisterInfo; class MipsTargetMachine : public LLVMTargetMachine { + bool isLittle; MipsSubtarget *Subtarget; MipsSubtarget DefaultSubtarget; MipsSubtarget NoMips16Subtarget; MipsSubtarget Mips16Subtarget; + mutable StringMap> SubtargetMap; + public: MipsTargetMachine(const Target &T, StringRef TT, StringRef CPU, StringRef FS, const TargetOptions &Options, Reloc::Model RM, @@ -45,6 +48,8 @@ public: return &DefaultSubtarget; } + const MipsSubtarget *getSubtargetImpl(const Function &F) const override; + /// \brief Reset the subtarget for the Mips target. void resetSubtarget(MachineFunction *MF); diff --git a/test/CodeGen/Mips/fp16instrinsmc.ll b/test/CodeGen/Mips/fp16instrinsmc.ll index 7ced36c016f..84d3814ee8b 100644 --- a/test/CodeGen/Mips/fp16instrinsmc.ll +++ b/test/CodeGen/Mips/fp16instrinsmc.ll @@ -385,7 +385,7 @@ entry: ; Function Attrs: nounwind declare double @exp2(double) #0 -attributes #0 = { nounwind "less-precise-fpmad"="false" "no-frame-pointer-elim"="true" "no-frame-pointer-elim-non-leaf" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "stack-protector-buffer-size"="8" "unsafe-fp-math"="false" "use-soft-float"="true" } +attributes #0 = { nounwind "less-precise-fpmad"="false" "no-frame-pointer-elim"="true" "no-frame-pointer-elim-non-leaf" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "stack-protector-buffer-size"="8" "unsafe-fp-math"="false" "use-soft-float"="false" } attributes #1 = { nounwind readnone "less-precise-fpmad"="false" "no-frame-pointer-elim"="true" "no-frame-pointer-elim-non-leaf" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "stack-protector-buffer-size"="8" "unsafe-fp-math"="false" "use-soft-float"="true" } attributes #2 = { nounwind readnone } attributes #3 = { nounwind } diff --git a/test/CodeGen/Mips/hfptrcall.ll b/test/CodeGen/Mips/hfptrcall.ll index 9df8d900693..683952d0e4e 100644 --- a/test/CodeGen/Mips/hfptrcall.ll +++ b/test/CodeGen/Mips/hfptrcall.ll @@ -118,8 +118,8 @@ entry: declare i32 @printf(i8*, ...) #1 -attributes #0 = { nounwind "less-precise-fpmad"="false" "no-frame-pointer-elim"="true" "no-frame-pointer-elim-non-leaf" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "unsafe-fp-math"="false" "use-soft-float"="true" } -attributes #1 = { "less-precise-fpmad"="false" "no-frame-pointer-elim"="true" "no-frame-pointer-elim-non-leaf" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "unsafe-fp-math"="false" "use-soft-float"="true" } +attributes #0 = { nounwind "less-precise-fpmad"="false" "no-frame-pointer-elim"="true" "no-frame-pointer-elim-non-leaf" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "unsafe-fp-math"="false" "use-soft-float"="false" } +attributes #1 = { "less-precise-fpmad"="false" "no-frame-pointer-elim"="true" "no-frame-pointer-elim-non-leaf" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "unsafe-fp-math"="false" "use-soft-float"="false" } diff --git a/test/CodeGen/Mips/nomips16.ll b/test/CodeGen/Mips/nomips16.ll index 0affb16ac7c..5f7d74e4197 100644 --- a/test/CodeGen/Mips/nomips16.ll +++ b/test/CodeGen/Mips/nomips16.ll @@ -33,6 +33,6 @@ entry: ; CHECK: .end nofoo -attributes #0 = { nounwind "less-precise-fpmad"="false" "mips16" "no-frame-pointer-elim"="true" "no-frame-pointer-elim-non-leaf" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "stack-protector-buffer-size"="8" "unsafe-fp-math"="false" "use-soft-float"="true" } -attributes #1 = { nounwind "less-precise-fpmad"="false" "no-frame-pointer-elim"="true" "no-frame-pointer-elim-non-leaf" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "nomips16" "stack-protector-buffer-size"="8" "unsafe-fp-math"="false" "use-soft-float"="true" } +attributes #0 = { nounwind "less-precise-fpmad"="false" "mips16" "no-frame-pointer-elim"="true" "no-frame-pointer-elim-non-leaf" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "stack-protector-buffer-size"="8" "unsafe-fp-math"="false" "use-soft-float"="false" } +attributes #1 = { nounwind "less-precise-fpmad"="false" "no-frame-pointer-elim"="true" "no-frame-pointer-elim-non-leaf" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "nomips16" "stack-protector-buffer-size"="8" "unsafe-fp-math"="false" "use-soft-float"="false" } diff --git a/test/CodeGen/Mips/seleq.ll b/test/CodeGen/Mips/seleq.ll index 190baad0b1d..9af422fa1bd 100644 --- a/test/CodeGen/Mips/seleq.ll +++ b/test/CodeGen/Mips/seleq.ll @@ -10,7 +10,7 @@ @z3 = common global i32 0, align 4 @z4 = common global i32 0, align 4 -define void @calc_seleq() nounwind "target-cpu"="mips32" "target-features"="+o32,+mips32" { +define void @calc_seleq() nounwind { entry: %0 = load i32* @a, align 4 %1 = load i32* @b, align 4 -- 2.34.1