summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJoseph Tremoulet <jotrem@microsoft.com>2015-11-07 01:11:31 +0000
committerJoseph Tremoulet <jotrem@microsoft.com>2015-11-07 01:11:31 +0000
commitf748c8937e71b70386833829a65436cdff15d286 (patch)
tree834d20fd23c5580659dfb8a881f7f3cc6f12f9c2
parentc22811bbcc02e833a315274f2158add4217f8ca1 (diff)
downloadbcm5719-llvm-f748c8937e71b70386833829a65436cdff15d286.tar.gz
bcm5719-llvm-f748c8937e71b70386833829a65436cdff15d286.zip
[WinEH] Update exception pointer registers
Summary: The CLR's personality routine passes these in rdx/edx, not rax/eax. Make getExceptionPointerRegister a virtual method parameterized by personality function to allow making this distinction. Similarly make getExceptionSelectorRegister a virtual method parameterized by personality function, for symmetry. Reviewers: pgavlin, majnemer, rnk Subscribers: jyknight, dsanders, llvm-commits Differential Revision: http://reviews.llvm.org/D14344 llvm-svn: 252383
-rw-r--r--llvm/include/llvm/Target/TargetLowering.h34
-rw-r--r--llvm/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp5
-rw-r--r--llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp7
-rw-r--r--llvm/lib/CodeGen/TargetLoweringBase.cpp2
-rw-r--r--llvm/lib/Target/AArch64/AArch64ISelLowering.cpp5
-rw-r--r--llvm/lib/Target/AArch64/AArch64ISelLowering.h17
-rw-r--r--llvm/lib/Target/ARM/ARMISelLowering.cpp21
-rw-r--r--llvm/lib/Target/ARM/ARMISelLowering.h10
-rw-r--r--llvm/lib/Target/Hexagon/HexagonISelLowering.cpp2
-rw-r--r--llvm/lib/Target/Hexagon/HexagonISelLowering.h14
-rw-r--r--llvm/lib/Target/Mips/MipsISelLowering.cpp3
-rw-r--r--llvm/lib/Target/Mips/MipsISelLowering.h14
-rw-r--r--llvm/lib/Target/PowerPC/PPCISelLowering.cpp20
-rw-r--r--llvm/lib/Target/PowerPC/PPCISelLowering.h11
-rw-r--r--llvm/lib/Target/Sparc/SparcISelLowering.cpp3
-rw-r--r--llvm/lib/Target/Sparc/SparcISelLowering.h14
-rw-r--r--llvm/lib/Target/SystemZ/SystemZISelLowering.cpp2
-rw-r--r--llvm/lib/Target/SystemZ/SystemZISelLowering.h14
-rw-r--r--llvm/lib/Target/X86/X86ISelLowering.cpp23
-rw-r--r--llvm/lib/Target/X86/X86ISelLowering.h10
-rw-r--r--llvm/lib/Target/XCore/XCoreFrameLowering.cpp31
-rw-r--r--llvm/lib/Target/XCore/XCoreISelLowering.cpp2
-rw-r--r--llvm/lib/Target/XCore/XCoreISelLowering.h14
-rw-r--r--llvm/test/CodeGen/WinEH/wineh-coreclr.ll20
-rw-r--r--llvm/test/CodeGen/WinEH/wineh-exceptionpointer.ll2
25 files changed, 210 insertions, 90 deletions
diff --git a/llvm/include/llvm/Target/TargetLowering.h b/llvm/include/llvm/Target/TargetLowering.h
index e17682f704e..d1770968d43 100644
--- a/llvm/include/llvm/Target/TargetLowering.h
+++ b/llvm/include/llvm/Target/TargetLowering.h
@@ -939,15 +939,19 @@ public:
}
/// If a physical register, this returns the register that receives the
- /// exception address on entry to a landing pad.
- unsigned getExceptionPointerRegister() const {
- return ExceptionPointerRegister;
+ /// exception address on entry to an EH pad.
+ virtual unsigned
+ getExceptionPointerRegister(const Constant *PersonalityFn) const {
+ // 0 is guaranteed to be the NoRegister value on all targets
+ return 0;
}
/// If a physical register, this returns the register that receives the
/// exception typeid on entry to a landing pad.
- unsigned getExceptionSelectorRegister() const {
- return ExceptionSelectorRegister;
+ virtual unsigned
+ getExceptionSelectorRegister(const Constant *PersonalityFn) const {
+ // 0 is guaranteed to be the NoRegister value on all targets
+ return 0;
}
/// Returns the target's jmp_buf size in bytes (if never set, the default is
@@ -1228,18 +1232,6 @@ protected:
StackPointerRegisterToSaveRestore = R;
}
- /// If set to a physical register, this sets the register that receives the
- /// exception address on entry to a landing pad.
- void setExceptionPointerRegister(unsigned R) {
- ExceptionPointerRegister = R;
- }
-
- /// If set to a physical register, this sets the register that receives the
- /// exception typeid on entry to a landing pad.
- void setExceptionSelectorRegister(unsigned R) {
- ExceptionSelectorRegister = R;
- }
-
/// Tells the code generator not to expand operations into sequences that use
/// the select operations if possible.
void setSelectIsExpensive(bool isExpensive = true) {
@@ -1856,14 +1848,6 @@ private:
/// llvm.savestack/llvm.restorestack should save and restore.
unsigned StackPointerRegisterToSaveRestore;
- /// If set to a physical register, this specifies the register that receives
- /// the exception address on entry to a landing pad.
- unsigned ExceptionPointerRegister;
-
- /// If set to a physical register, this specifies the register that receives
- /// the exception typeid on entry to a landing pad.
- unsigned ExceptionSelectorRegister;
-
/// This indicates the default register class to use for each ValueType the
/// target supports natively.
const TargetRegisterClass *RegClassForVT[MVT::LAST_VALUETYPE];
diff --git a/llvm/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp b/llvm/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp
index 75b2960bb37..2f5e329c95b 100644
--- a/llvm/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp
+++ b/llvm/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp
@@ -2184,8 +2184,9 @@ void SelectionDAGBuilder::visitLandingPad(const LandingPadInst &LP) {
// If there aren't registers to copy the values into (e.g., during SjLj
// exceptions), then don't bother to create these DAG nodes.
const TargetLowering &TLI = DAG.getTargetLoweringInfo();
- if (TLI.getExceptionPointerRegister() == 0 &&
- TLI.getExceptionSelectorRegister() == 0)
+ const Constant *PersonalityFn = FuncInfo.Fn->getPersonalityFn();
+ if (TLI.getExceptionPointerRegister(PersonalityFn) == 0 &&
+ TLI.getExceptionSelectorRegister(PersonalityFn) == 0)
return;
SmallVector<EVT, 2> ValueVTs;
diff --git a/llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp b/llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp
index a9113252abb..04895e7702f 100644
--- a/llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp
+++ b/llvm/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp
@@ -938,6 +938,7 @@ static bool hasExceptionPointerOrCodeUser(const CatchPadInst *CPI) {
/// do other setup for EH landing-pad blocks.
bool SelectionDAGISel::PrepareEHLandingPad() {
MachineBasicBlock *MBB = FuncInfo->MBB;
+ const Constant *PersonalityFn = FuncInfo->Fn->getPersonalityFn();
const BasicBlock *LLVMBB = MBB->getBasicBlock();
const TargetRegisterClass *PtrRC =
TLI->getRegClassFor(TLI->getPointerTy(CurDAG->getDataLayout()));
@@ -948,7 +949,7 @@ bool SelectionDAGISel::PrepareEHLandingPad() {
if (hasExceptionPointerOrCodeUser(CPI)) {
// Get or create the virtual register to hold the pointer or code. Mark
// the live in physreg and copy into the vreg.
- MCPhysReg EHPhysReg = TLI->getExceptionPointerRegister();
+ MCPhysReg EHPhysReg = TLI->getExceptionPointerRegister(PersonalityFn);
assert(EHPhysReg && "target lacks exception pointer register");
MBB->addLiveIn(EHPhysReg);
unsigned VReg = FuncInfo->getCatchPadExceptionPointerVReg(CPI, PtrRC);
@@ -974,11 +975,11 @@ bool SelectionDAGISel::PrepareEHLandingPad() {
.addSym(Label);
// Mark exception register as live in.
- if (unsigned Reg = TLI->getExceptionPointerRegister())
+ if (unsigned Reg = TLI->getExceptionPointerRegister(PersonalityFn))
FuncInfo->ExceptionPointerVirtReg = MBB->addLiveIn(Reg, PtrRC);
// Mark exception selector register as live in.
- if (unsigned Reg = TLI->getExceptionSelectorRegister())
+ if (unsigned Reg = TLI->getExceptionSelectorRegister(PersonalityFn))
FuncInfo->ExceptionSelectorVirtReg = MBB->addLiveIn(Reg, PtrRC);
return true;
diff --git a/llvm/lib/CodeGen/TargetLoweringBase.cpp b/llvm/lib/CodeGen/TargetLoweringBase.cpp
index ece2e395c3d..24bdef3040e 100644
--- a/llvm/lib/CodeGen/TargetLoweringBase.cpp
+++ b/llvm/lib/CodeGen/TargetLoweringBase.cpp
@@ -765,8 +765,6 @@ TargetLoweringBase::TargetLoweringBase(const TargetMachine &tm) : TM(tm) {
EnableExtLdPromotion = false;
HasFloatingPointExceptions = true;
StackPointerRegisterToSaveRestore = 0;
- ExceptionPointerRegister = 0;
- ExceptionSelectorRegister = 0;
BooleanContents = UndefinedBooleanContent;
BooleanFloatContents = UndefinedBooleanContent;
BooleanVectorContents = UndefinedBooleanContent;
diff --git a/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp b/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp
index 428624cd894..77dfb8afe3f 100644
--- a/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp
+++ b/llvm/lib/Target/AArch64/AArch64ISelLowering.cpp
@@ -196,11 +196,6 @@ AArch64TargetLowering::AArch64TargetLowering(const TargetMachine &TM,
setOperationAction(ISD::STACKRESTORE, MVT::Other, Expand);
setOperationAction(ISD::DYNAMIC_STACKALLOC, MVT::i64, Expand);
- // Exception handling.
- // FIXME: These are guesses. Has this been defined yet?
- setExceptionPointerRegister(AArch64::X0);
- setExceptionSelectorRegister(AArch64::X1);
-
// Constant pool entries
setOperationAction(ISD::ConstantPool, MVT::i64, Custom);
diff --git a/llvm/lib/Target/AArch64/AArch64ISelLowering.h b/llvm/lib/Target/AArch64/AArch64ISelLowering.h
index 64a2934d1d5..7c10cb11669 100644
--- a/llvm/lib/Target/AArch64/AArch64ISelLowering.h
+++ b/llvm/lib/Target/AArch64/AArch64ISelLowering.h
@@ -15,6 +15,7 @@
#ifndef LLVM_LIB_TARGET_AARCH64_AARCH64ISELLOWERING_H
#define LLVM_LIB_TARGET_AARCH64_AARCH64ISELLOWERING_H
+#include "AArch64.h"
#include "llvm/CodeGen/CallingConvLower.h"
#include "llvm/CodeGen/SelectionDAG.h"
#include "llvm/IR/CallingConv.h"
@@ -366,6 +367,22 @@ public:
/// returns the address of that location. Otherwise, returns nullptr.
Value *getSafeStackPointerLocation(IRBuilder<> &IRB) const override;
+ /// If a physical register, this returns the register that receives the
+ /// exception address on entry to an EH pad.
+ unsigned
+ getExceptionPointerRegister(const Constant *PersonalityFn) const override {
+ // FIXME: This is a guess. Has this been defined yet?
+ return AArch64::X0;
+ }
+
+ /// If a physical register, this returns the register that receives the
+ /// exception typeid on entry to a landing pad.
+ unsigned
+ getExceptionSelectorRegister(const Constant *PersonalityFn) const override {
+ // FIXME: This is a guess. Has this been defined yet?
+ return AArch64::X1;
+ }
+
private:
bool isExtFreeImpl(const Instruction *Ext) const override;
diff --git a/llvm/lib/Target/ARM/ARMISelLowering.cpp b/llvm/lib/Target/ARM/ARMISelLowering.cpp
index 992902d6f6e..da8ecfa1102 100644
--- a/llvm/lib/Target/ARM/ARMISelLowering.cpp
+++ b/llvm/lib/Target/ARM/ARMISelLowering.cpp
@@ -813,13 +813,6 @@ ARMTargetLowering::ARMTargetLowering(const TargetMachine &TM,
setOperationAction(ISD::STACKSAVE, MVT::Other, Expand);
setOperationAction(ISD::STACKRESTORE, MVT::Other, Expand);
- if (!Subtarget->useSjLjEH()) {
- // Platforms which do not use SjLj EH may return values in these registers
- // via the personality function.
- setExceptionPointerRegister(ARM::R0);
- setExceptionSelectorRegister(ARM::R1);
- }
-
if (Subtarget->getTargetTriple().isWindowsItaniumEnvironment())
setOperationAction(ISD::DYNAMIC_STACKALLOC, MVT::i32, Custom);
else
@@ -12147,3 +12140,17 @@ bool ARMTargetLowering::functionArgumentNeedsConsecutiveRegisters(
bool IsIntArray = Ty->isArrayTy() && Ty->getArrayElementType()->isIntegerTy();
return IsHA || IsIntArray;
}
+
+unsigned ARMTargetLowering::getExceptionPointerRegister(
+ const Constant *PersonalityFn) const {
+ // Platforms which do not use SjLj EH may return values in these registers
+ // via the personality function.
+ return Subtarget->useSjLjEH() ? ARM::NoRegister : ARM::R0;
+}
+
+unsigned ARMTargetLowering::getExceptionSelectorRegister(
+ const Constant *PersonalityFn) const {
+ // Platforms which do not use SjLj EH may return values in these registers
+ // via the personality function.
+ return Subtarget->useSjLjEH() ? ARM::NoRegister : ARM::R1;
+}
diff --git a/llvm/lib/Target/ARM/ARMISelLowering.h b/llvm/lib/Target/ARM/ARMISelLowering.h
index 852a36b0c12..534f92b941c 100644
--- a/llvm/lib/Target/ARM/ARMISelLowering.h
+++ b/llvm/lib/Target/ARM/ARMISelLowering.h
@@ -423,6 +423,16 @@ namespace llvm {
bool functionArgumentNeedsConsecutiveRegisters(
Type *Ty, CallingConv::ID CallConv, bool isVarArg) const override;
+ /// If a physical register, this returns the register that receives the
+ /// exception address on entry to an EH pad.
+ unsigned
+ getExceptionPointerRegister(const Constant *PersonalityFn) const override;
+
+ /// If a physical register, this returns the register that receives the
+ /// exception typeid on entry to a landing pad.
+ unsigned
+ getExceptionSelectorRegister(const Constant *PersonalityFn) const override;
+
Instruction *makeDMB(IRBuilder<> &Builder, ARM_MB::MemBOpt Domain) const;
Value *emitLoadLinked(IRBuilder<> &Builder, Value *Addr,
AtomicOrdering Ord) const override;
diff --git a/llvm/lib/Target/Hexagon/HexagonISelLowering.cpp b/llvm/lib/Target/Hexagon/HexagonISelLowering.cpp
index 4ebc596b34a..564eb1fa6fa 100644
--- a/llvm/lib/Target/Hexagon/HexagonISelLowering.cpp
+++ b/llvm/lib/Target/Hexagon/HexagonISelLowering.cpp
@@ -1286,8 +1286,6 @@ HexagonTargetLowering::HexagonTargetLowering(const TargetMachine &TM,
setPrefFunctionAlignment(4);
setMinFunctionAlignment(2);
setInsertFencesForAtomic(false);
- setExceptionPointerRegister(Hexagon::R0);
- setExceptionSelectorRegister(Hexagon::R1);
setStackPointerRegisterToSaveRestore(HRI.getStackRegister());
if (EnableHexSDNodeSched)
diff --git a/llvm/lib/Target/Hexagon/HexagonISelLowering.h b/llvm/lib/Target/Hexagon/HexagonISelLowering.h
index 2987cc252e0..80ab2ce9970 100644
--- a/llvm/lib/Target/Hexagon/HexagonISelLowering.h
+++ b/llvm/lib/Target/Hexagon/HexagonISelLowering.h
@@ -163,6 +163,20 @@ bool isPositiveHalfWord(SDNode *N);
MachineBasicBlock * EmitInstrWithCustomInserter(MachineInstr *MI,
MachineBasicBlock *BB) const override;
+ /// If a physical register, this returns the register that receives the
+ /// exception address on entry to an EH pad.
+ unsigned
+ getExceptionPointerRegister(const Constant *PersonalityFn) const override {
+ return Hexagon::R0;
+ }
+
+ /// If a physical register, this returns the register that receives the
+ /// exception typeid on entry to a landing pad.
+ unsigned
+ getExceptionSelectorRegister(const Constant *PersonalityFn) const override {
+ return Hexagon::R1;
+ }
+
SDValue LowerVASTART(SDValue Op, SelectionDAG &DAG) const;
SDValue LowerConstantPool(SDValue Op, SelectionDAG &DAG) const;
EVT getSetCCResultType(const DataLayout &, LLVMContext &C,
diff --git a/llvm/lib/Target/Mips/MipsISelLowering.cpp b/llvm/lib/Target/Mips/MipsISelLowering.cpp
index 75dc2f1e0f3..66c495bc3e9 100644
--- a/llvm/lib/Target/Mips/MipsISelLowering.cpp
+++ b/llvm/lib/Target/Mips/MipsISelLowering.cpp
@@ -438,9 +438,6 @@ MipsTargetLowering::MipsTargetLowering(const MipsTargetMachine &TM,
setStackPointerRegisterToSaveRestore(ABI.IsN64() ? Mips::SP_64 : Mips::SP);
- setExceptionPointerRegister(ABI.IsN64() ? Mips::A0_64 : Mips::A0);
- setExceptionSelectorRegister(ABI.IsN64() ? Mips::A1_64 : Mips::A1);
-
MaxStoresPerMemcpy = 16;
isMicroMips = Subtarget.inMicroMipsMode();
diff --git a/llvm/lib/Target/Mips/MipsISelLowering.h b/llvm/lib/Target/Mips/MipsISelLowering.h
index 85462275edb..8e2cb0b4a6c 100644
--- a/llvm/lib/Target/Mips/MipsISelLowering.h
+++ b/llvm/lib/Target/Mips/MipsISelLowering.h
@@ -267,6 +267,20 @@ namespace llvm {
unsigned getRegisterByName(const char* RegName, EVT VT,
SelectionDAG &DAG) const override;
+ /// If a physical register, this returns the register that receives the
+ /// exception address on entry to an EH pad.
+ unsigned
+ getExceptionPointerRegister(const Constant *PersonalityFn) const override {
+ return ABI.IsN64() ? Mips::A0_64 : Mips::A0;
+ }
+
+ /// If a physical register, this returns the register that receives the
+ /// exception typeid on entry to a landing pad.
+ unsigned
+ getExceptionSelectorRegister(const Constant *PersonalityFn) const override {
+ return ABI.IsN64() ? Mips::A1_64 : Mips::A1;
+ }
+
/// Returns true if a cast between SrcAS and DestAS is a noop.
bool isNoopAddrSpaceCast(unsigned SrcAS, unsigned DestAS) const override {
// Mips doesn't have any special address spaces so we just reserve
diff --git a/llvm/lib/Target/PowerPC/PPCISelLowering.cpp b/llvm/lib/Target/PowerPC/PPCISelLowering.cpp
index f4919dd9acc..8a4dd5fab3d 100644
--- a/llvm/lib/Target/PowerPC/PPCISelLowering.cpp
+++ b/llvm/lib/Target/PowerPC/PPCISelLowering.cpp
@@ -827,15 +827,7 @@ PPCTargetLowering::PPCTargetLowering(const PPCTargetMachine &TM,
setLibcallName(RTLIB::SRA_I128, nullptr);
}
- if (isPPC64) {
- setStackPointerRegisterToSaveRestore(PPC::X1);
- setExceptionPointerRegister(PPC::X3);
- setExceptionSelectorRegister(PPC::X4);
- } else {
- setStackPointerRegisterToSaveRestore(PPC::R1);
- setExceptionPointerRegister(PPC::R3);
- setExceptionSelectorRegister(PPC::R4);
- }
+ setStackPointerRegisterToSaveRestore(isPPC64 ? PPC::X1 : PPC::R1);
// We have target-specific dag combine patterns for the following nodes:
setTargetDAGCombine(ISD::SINT_TO_FP);
@@ -11532,6 +11524,16 @@ PPCTargetLowering::getScratchRegisters(CallingConv::ID) const {
return ScratchRegs;
}
+unsigned PPCTargetLowering::getExceptionPointerRegister(
+ const Constant *PersonalityFn) const {
+ return Subtarget.isPPC64() ? PPC::X3 : PPC::R3;
+}
+
+unsigned PPCTargetLowering::getExceptionSelectorRegister(
+ const Constant *PersonalityFn) const {
+ return Subtarget.isPPC64() ? PPC::X4 : PPC::R4;
+}
+
bool
PPCTargetLowering::shouldExpandBuildVectorWithShuffles(
EVT VT , unsigned DefinedValues) const {
diff --git a/llvm/lib/Target/PowerPC/PPCISelLowering.h b/llvm/lib/Target/PowerPC/PPCISelLowering.h
index cbd5add8488..415c47c286e 100644
--- a/llvm/lib/Target/PowerPC/PPCISelLowering.h
+++ b/llvm/lib/Target/PowerPC/PPCISelLowering.h
@@ -655,8 +655,17 @@ namespace llvm {
return Ty->isArrayTy();
}
- private:
+ /// If a physical register, this returns the register that receives the
+ /// exception address on entry to an EH pad.
+ unsigned
+ getExceptionPointerRegister(const Constant *PersonalityFn) const override;
+ /// If a physical register, this returns the register that receives the
+ /// exception typeid on entry to a landing pad.
+ unsigned
+ getExceptionSelectorRegister(const Constant *PersonalityFn) const override;
+
+ private:
struct ReuseLoadInfo {
SDValue Ptr;
SDValue Chain;
diff --git a/llvm/lib/Target/Sparc/SparcISelLowering.cpp b/llvm/lib/Target/Sparc/SparcISelLowering.cpp
index 6138f54352a..c496a3c5a11 100644
--- a/llvm/lib/Target/Sparc/SparcISelLowering.cpp
+++ b/llvm/lib/Target/Sparc/SparcISelLowering.cpp
@@ -1674,9 +1674,6 @@ SparcTargetLowering::SparcTargetLowering(TargetMachine &TM,
setOperationAction(ISD::STACKRESTORE , MVT::Other, Expand);
setOperationAction(ISD::DYNAMIC_STACKALLOC, MVT::i32 , Custom);
- setExceptionPointerRegister(SP::I0);
- setExceptionSelectorRegister(SP::I1);
-
setStackPointerRegisterToSaveRestore(SP::O6);
setOperationAction(ISD::CTPOP, MVT::i32,
diff --git a/llvm/lib/Target/Sparc/SparcISelLowering.h b/llvm/lib/Target/Sparc/SparcISelLowering.h
index 6786b9e3cd3..4e46709cfc0 100644
--- a/llvm/lib/Target/Sparc/SparcISelLowering.h
+++ b/llvm/lib/Target/Sparc/SparcISelLowering.h
@@ -89,6 +89,20 @@ namespace llvm {
return MVT::i32;
}
+ /// If a physical register, this returns the register that receives the
+ /// exception address on entry to an EH pad.
+ unsigned
+ getExceptionPointerRegister(const Constant *PersonalityFn) const override {
+ return SP::I0;
+ }
+
+ /// If a physical register, this returns the register that receives the
+ /// exception typeid on entry to a landing pad.
+ unsigned
+ getExceptionSelectorRegister(const Constant *PersonalityFn) const override {
+ return SP::I1;
+ }
+
/// getSetCCResultType - Return the ISD::SETCC ValueType
EVT getSetCCResultType(const DataLayout &DL, LLVMContext &Context,
EVT VT) const override;
diff --git a/llvm/lib/Target/SystemZ/SystemZISelLowering.cpp b/llvm/lib/Target/SystemZ/SystemZISelLowering.cpp
index b3e2340fee8..f598bc0189d 100644
--- a/llvm/lib/Target/SystemZ/SystemZISelLowering.cpp
+++ b/llvm/lib/Target/SystemZ/SystemZISelLowering.cpp
@@ -114,8 +114,6 @@ SystemZTargetLowering::SystemZTargetLowering(const TargetMachine &TM,
computeRegisterProperties(Subtarget.getRegisterInfo());
// Set up special registers.
- setExceptionPointerRegister(SystemZ::R6D);
- setExceptionSelectorRegister(SystemZ::R7D);
setStackPointerRegisterToSaveRestore(SystemZ::R15D);
// TODO: It may be better to default to latency-oriented scheduling, however
diff --git a/llvm/lib/Target/SystemZ/SystemZISelLowering.h b/llvm/lib/Target/SystemZ/SystemZISelLowering.h
index 8a2839acd24..391636e5467 100644
--- a/llvm/lib/Target/SystemZ/SystemZISelLowering.h
+++ b/llvm/lib/Target/SystemZ/SystemZISelLowering.h
@@ -409,6 +409,20 @@ public:
return TargetLowering::getInlineAsmMemConstraint(ConstraintCode);
}
+ /// If a physical register, this returns the register that receives the
+ /// exception address on entry to an EH pad.
+ unsigned
+ getExceptionPointerRegister(const Constant *PersonalityFn) const override {
+ return SystemZ::R6D;
+ }
+
+ /// If a physical register, this returns the register that receives the
+ /// exception typeid on entry to a landing pad.
+ unsigned
+ getExceptionSelectorRegister(const Constant *PersonalityFn) const override {
+ return SystemZ::R7D;
+ }
+
MachineBasicBlock *EmitInstrWithCustomInserter(MachineInstr *MI,
MachineBasicBlock *BB) const
override;
diff --git a/llvm/lib/Target/X86/X86ISelLowering.cpp b/llvm/lib/Target/X86/X86ISelLowering.cpp
index 672ecc50103..f5efd58e7a3 100644
--- a/llvm/lib/Target/X86/X86ISelLowering.cpp
+++ b/llvm/lib/Target/X86/X86ISelLowering.cpp
@@ -25,6 +25,7 @@
#include "llvm/ADT/Statistic.h"
#include "llvm/ADT/StringExtras.h"
#include "llvm/ADT/StringSwitch.h"
+#include "llvm/Analysis/LibCallSemantics.h"
#include "llvm/CodeGen/IntrinsicLowering.h"
#include "llvm/CodeGen/MachineFrameInfo.h"
#include "llvm/CodeGen/MachineFunction.h"
@@ -476,13 +477,6 @@ X86TargetLowering::X86TargetLowering(const X86TargetMachine &TM,
setOperationAction(ISD::EH_LABEL, MVT::Other, Expand);
}
- if (Subtarget->isTarget64BitLP64()) {
- setExceptionPointerRegister(X86::RAX);
- setExceptionSelectorRegister(X86::RDX);
- } else {
- setExceptionPointerRegister(X86::EAX);
- setExceptionSelectorRegister(X86::EDX);
- }
setOperationAction(ISD::FRAME_TO_ARGS_OFFSET, MVT::i32, Custom);
setOperationAction(ISD::FRAME_TO_ARGS_OFFSET, MVT::i64, Custom);
@@ -17246,6 +17240,21 @@ SDValue X86TargetLowering::LowerFRAME_TO_ARGS_OFFSET(SDValue Op,
return DAG.getIntPtrConstant(2 * RegInfo->getSlotSize(), SDLoc(Op));
}
+unsigned X86TargetLowering::getExceptionPointerRegister(
+ const Constant *PersonalityFn) const {
+ if (classifyEHPersonality(PersonalityFn) == EHPersonality::CoreCLR)
+ return Subtarget->isTarget64BitLP64() ? X86::RDX : X86::EDX;
+
+ return Subtarget->isTarget64BitLP64() ? X86::RAX : X86::EAX;
+}
+
+unsigned X86TargetLowering::getExceptionSelectorRegister(
+ const Constant *PersonalityFn) const {
+ // Funclet personalities don't use selectors (the runtime does the selection).
+ assert(!isFuncletEHPersonality(classifyEHPersonality(PersonalityFn)));
+ return Subtarget->isTarget64BitLP64() ? X86::RDX : X86::EDX;
+}
+
SDValue X86TargetLowering::LowerEH_RETURN(SDValue Op, SelectionDAG &DAG) const {
SDValue Chain = Op.getOperand(0);
SDValue Offset = Op.getOperand(1);
diff --git a/llvm/lib/Target/X86/X86ISelLowering.h b/llvm/lib/Target/X86/X86ISelLowering.h
index 6bd7ef9a3b5..e7dbaa995c8 100644
--- a/llvm/lib/Target/X86/X86ISelLowering.h
+++ b/llvm/lib/Target/X86/X86ISelLowering.h
@@ -889,6 +889,16 @@ namespace llvm {
unsigned getRegisterByName(const char* RegName, EVT VT,
SelectionDAG &DAG) const override;
+ /// If a physical register, this returns the register that receives the
+ /// exception address on entry to an EH pad.
+ unsigned
+ getExceptionPointerRegister(const Constant *PersonalityFn) const override;
+
+ /// If a physical register, this returns the register that receives the
+ /// exception typeid on entry to a landing pad.
+ unsigned
+ getExceptionSelectorRegister(const Constant *PersonalityFn) const override;
+
/// This method returns a target specific FastISel object,
/// or null if the target does not support "fast" ISel.
FastISel *createFastISel(FunctionLoweringInfo &funcInfo,
diff --git a/llvm/lib/Target/XCore/XCoreFrameLowering.cpp b/llvm/lib/Target/XCore/XCoreFrameLowering.cpp
index f7c6159e3e1..ae493de083b 100644
--- a/llvm/lib/Target/XCore/XCoreFrameLowering.cpp
+++ b/llvm/lib/Target/XCore/XCoreFrameLowering.cpp
@@ -160,19 +160,19 @@ static void GetSpillList(SmallVectorImpl<StackSlotInfo> &SpillList,
/// As offsets are negative, the largest offsets will be first.
static void GetEHSpillList(SmallVectorImpl<StackSlotInfo> &SpillList,
MachineFrameInfo *MFI, XCoreFunctionInfo *XFI,
+ const Constant *PersonalityFn,
const TargetLowering *TL) {
assert(XFI->hasEHSpillSlot() && "There are no EH register spill slots");
- const int* EHSlot = XFI->getEHSpillSlot();
- SpillList.push_back(StackSlotInfo(EHSlot[0],
- MFI->getObjectOffset(EHSlot[0]),
- TL->getExceptionPointerRegister()));
- SpillList.push_back(StackSlotInfo(EHSlot[0],
- MFI->getObjectOffset(EHSlot[1]),
- TL->getExceptionSelectorRegister()));
+ const int *EHSlot = XFI->getEHSpillSlot();
+ SpillList.push_back(
+ StackSlotInfo(EHSlot[0], MFI->getObjectOffset(EHSlot[0]),
+ TL->getExceptionPointerRegister(PersonalityFn)));
+ SpillList.push_back(
+ StackSlotInfo(EHSlot[0], MFI->getObjectOffset(EHSlot[1]),
+ TL->getExceptionSelectorRegister(PersonalityFn)));
std::sort(SpillList.begin(), SpillList.end(), CompareSSIOffset);
}
-
static MachineMemOperand *
getFrameIndexMMO(MachineBasicBlock &MBB, int FrameIndex, unsigned flags) {
MachineFunction *MF = MBB.getParent();
@@ -322,8 +322,11 @@ void XCoreFrameLowering::emitPrologue(MachineFunction &MF,
if (XFI->hasEHSpillSlot()) {
// The unwinder requires stack slot & CFI offsets for the exception info.
// We do not save/spill these registers.
- SmallVector<StackSlotInfo,2> SpillList;
- GetEHSpillList(SpillList, MFI, XFI,
+ const Function *Fn = MF.getFunction();
+ const Constant *PersonalityFn =
+ Fn->hasPersonalityFn() ? Fn->getPersonalityFn() : nullptr;
+ SmallVector<StackSlotInfo, 2> SpillList;
+ GetEHSpillList(SpillList, MFI, XFI, PersonalityFn,
MF.getSubtarget().getTargetLowering());
assert(SpillList.size()==2 && "Unexpected SpillList size");
EmitCfiOffset(MBB, MBBI, dl, TII, MMI,
@@ -354,8 +357,12 @@ void XCoreFrameLowering::emitEpilogue(MachineFunction &MF,
if (RetOpcode == XCore::EH_RETURN) {
// 'Restore' the exception info the unwinder has placed into the stack
// slots.
- SmallVector<StackSlotInfo,2> SpillList;
- GetEHSpillList(SpillList, MFI, XFI, MF.getSubtarget().getTargetLowering());
+ const Function *Fn = MF.getFunction();
+ const Constant *PersonalityFn =
+ Fn->hasPersonalityFn() ? Fn->getPersonalityFn() : nullptr;
+ SmallVector<StackSlotInfo, 2> SpillList;
+ GetEHSpillList(SpillList, MFI, XFI, PersonalityFn,
+ MF.getSubtarget().getTargetLowering());
RestoreSpillList(MBB, MBBI, dl, TII, RemainingAdj, SpillList);
// Return to the landing pad.
diff --git a/llvm/lib/Target/XCore/XCoreISelLowering.cpp b/llvm/lib/Target/XCore/XCoreISelLowering.cpp
index 28735567721..105b2cfb1be 100644
--- a/llvm/lib/Target/XCore/XCoreISelLowering.cpp
+++ b/llvm/lib/Target/XCore/XCoreISelLowering.cpp
@@ -151,8 +151,6 @@ XCoreTargetLowering::XCoreTargetLowering(const TargetMachine &TM,
// Exception handling
setOperationAction(ISD::EH_RETURN, MVT::Other, Custom);
- setExceptionPointerRegister(XCore::R0);
- setExceptionSelectorRegister(XCore::R1);
setOperationAction(ISD::FRAME_TO_ARGS_OFFSET, MVT::i32, Custom);
// Atomic operations
diff --git a/llvm/lib/Target/XCore/XCoreISelLowering.h b/llvm/lib/Target/XCore/XCoreISelLowering.h
index ddd675c5164..b6f09ff418b 100644
--- a/llvm/lib/Target/XCore/XCoreISelLowering.h
+++ b/llvm/lib/Target/XCore/XCoreISelLowering.h
@@ -125,6 +125,20 @@ namespace llvm {
bool isLegalAddressingMode(const DataLayout &DL, const AddrMode &AM,
Type *Ty, unsigned AS) const override;
+ /// If a physical register, this returns the register that receives the
+ /// exception address on entry to an EH pad.
+ unsigned
+ getExceptionPointerRegister(const Constant *PersonalityFn) const override {
+ return XCore::R0;
+ }
+
+ /// If a physical register, this returns the register that receives the
+ /// exception typeid on entry to a landing pad.
+ unsigned
+ getExceptionSelectorRegister(const Constant *PersonalityFn) const override {
+ return XCore::R1;
+ }
+
private:
const TargetMachine &TM;
const XCoreSubtarget &Subtarget;
diff --git a/llvm/test/CodeGen/WinEH/wineh-coreclr.ll b/llvm/test/CodeGen/WinEH/wineh-coreclr.ll
index f5e046aa01c..923d966a5f6 100644
--- a/llvm/test/CodeGen/WinEH/wineh-coreclr.ll
+++ b/llvm/test/CodeGen/WinEH/wineh-coreclr.ll
@@ -2,6 +2,8 @@
declare void @ProcessCLRException()
declare void @f(i32)
+declare void @g(i8 addrspace(1)*)
+declare i8 addrspace(1)* @llvm.eh.exceptionpointer.p1i8(token)
; Simplified IR for pseudo-C# like the following:
; void test1() {
@@ -51,8 +53,13 @@ catch1.pad:
to label %catch1.body unwind label %catch2.pad
catch1.body:
; CHECK: leaq {{[0-9]+}}(%rcx), %rbp
-; ^ establisher frame pointer passed in rcx
+; ^ establisher frame pointer passed in rcx
; CHECK: .seh_endprologue
+; CHECK: movq %rdx, %rcx
+; ^ exception pointer passed in rdx
+; CHECK-NEXT: callq g
+ %exn1 = call i8 addrspace(1)* @llvm.eh.exceptionpointer.p1i8(token %catch1)
+ call void @g(i8 addrspace(1)* %exn1)
; CHECK: [[L_before_f3:.+]]:
; CHECK-NEXT: movl $3, %ecx
; CHECK-NEXT: callq f
@@ -67,8 +74,13 @@ catch2.pad:
to label %catch2.body unwind label %catch.end
catch2.body:
; CHECK: leaq {{[0-9]+}}(%rcx), %rbp
-; ^ establisher frame pointer passed in rcx
+; ^ establisher frame pointer passed in rcx
; CHECK: .seh_endprologue
+; CHECK: movq %rdx, %rcx
+; ^ exception pointer passed in rdx
+; CHECK-NEXT: callq g
+ %exn2 = call i8 addrspace(1)* @llvm.eh.exceptionpointer.p1i8(token %catch2)
+ call void @g(i8 addrspace(1)* %exn2)
; CHECK: [[L_before_f4:.+]]:
; CHECK-NEXT: movl $4, %ecx
; CHECK-NEXT: callq f
@@ -87,7 +99,7 @@ fault.pad:
; CHECK: .seh_proc [[L_fault:[^ ]+]]
%fault = cleanuppad [i32 undef]
; CHECK: leaq {{[0-9]+}}(%rcx), %rbp
-; ^ establisher frame pointer passed in rcx
+; ^ establisher frame pointer passed in rcx
; CHECK: .seh_endprologue
; CHECK: [[L_before_f6:.+]]:
; CHECK-NEXT: movl $6, %ecx
@@ -110,7 +122,7 @@ finally.pad:
; CHECK: .seh_proc [[L_finally:[^ ]+]]
%finally = cleanuppad []
; CHECK: leaq {{[0-9]+}}(%rcx), %rbp
-; ^ establisher frame pointer passed in rcx
+; ^ establisher frame pointer passed in rcx
; CHECK: .seh_endprologue
; CHECK: [[L_before_f7:.+]]:
; CHECK-NEXT: movl $7, %ecx
diff --git a/llvm/test/CodeGen/WinEH/wineh-exceptionpointer.ll b/llvm/test/CodeGen/WinEH/wineh-exceptionpointer.ll
index 05139ef1bd9..47ffc35acac 100644
--- a/llvm/test/CodeGen/WinEH/wineh-exceptionpointer.ll
+++ b/llvm/test/CodeGen/WinEH/wineh-exceptionpointer.ll
@@ -17,7 +17,7 @@ catch.pad:
catch.body:
%exn = call i8 addrspace(1)* @llvm.eh.exceptionpointer.p1i8(token %catch)
%cast_exn = bitcast i8 addrspace(1)* %exn to i32 addrspace(1)*
- ; CHECK: movq %rax, %rcx
+ ; CHECK: movq %rdx, %rcx
; CHECK-NEXT: callq g
call void @g(i32 addrspace(1)* %cast_exn)
catchret %catch to label %exit
OpenPOWER on IntegriCloud