diff --git a/llvm/lib/Target/M68k/M68kISelLowering.cpp b/llvm/lib/Target/M68k/M68kISelLowering.cpp index cd5ff2fb9dcdb1..c9bbb23f31df86 100644 --- a/llvm/lib/Target/M68k/M68kISelLowering.cpp +++ b/llvm/lib/Target/M68k/M68kISelLowering.cpp @@ -191,6 +191,16 @@ M68kTargetLowering::shouldExpandAtomicRMWInIR(AtomicRMWInst *RMW) const { : TargetLoweringBase::AtomicExpansionKind::None; } +Register +M68kTargetLowering::getExceptionPointerRegister(const Constant *) const { + return M68k::D0; +} + +Register +M68kTargetLowering::getExceptionSelectorRegister(const Constant *) const { + return M68k::D1; +} + EVT M68kTargetLowering::getSetCCResultType(const DataLayout &DL, LLVMContext &Context, EVT VT) const { // M68k SETcc producess either 0x00 or 0xFF diff --git a/llvm/lib/Target/M68k/M68kISelLowering.h b/llvm/lib/Target/M68k/M68kISelLowering.h index ec525bc4c6b3c4..e6242f76c56fb5 100644 --- a/llvm/lib/Target/M68k/M68kISelLowering.h +++ b/llvm/lib/Target/M68k/M68kISelLowering.h @@ -177,6 +177,16 @@ class M68kTargetLowering : public TargetLowering { AtomicExpansionKind shouldExpandAtomicRMWInIR(AtomicRMWInst *RMW) const override; + /// If a physical register, this returns the register that receives the + /// exception address on entry to an EH pad. + Register + 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. + Register + getExceptionSelectorRegister(const Constant *PersonalityFn) const override; + private: unsigned GetAlignedArgumentStackSize(unsigned StackSize, SelectionDAG &DAG) const; diff --git a/llvm/test/CodeGen/M68k/gcc_except_table.ll b/llvm/test/CodeGen/M68k/gcc_except_table.ll new file mode 100644 index 00000000000000..a7d2a6662724ed --- /dev/null +++ b/llvm/test/CodeGen/M68k/gcc_except_table.ll @@ -0,0 +1,48 @@ +; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py +; RUN: llc -mtriple=m68k < %s | FileCheck %s + +; (Copied from test/CodeGen/X86/gcc_except_table.ll) +; Testing whether exception pointer register (d0) and exception selector +; register (d1) are correctly used by landing and EH pad, respectively. +@_ZTIi = external constant ptr + +define i32 @foo() uwtable ssp personality ptr @__gxx_personality_v0 { +; CHECK-LABEL: foo: +; CHECK: .Lfunc_begin0: +; CHECK-NEXT: .cfi_startproc +; CHECK-NEXT: .cfi_personality 0, __gxx_personality_v0 +; CHECK-NEXT: .cfi_lsda 0, .Lexception0 +; CHECK-NEXT: ; %bb.0: ; %entry +; CHECK-NEXT: suba.l #4, %sp +; CHECK-NEXT: .cfi_def_cfa_offset -8 +; CHECK-NEXT: .Ltmp0: +; CHECK-NEXT: jsr _Z1fv@PLT +; CHECK-NEXT: .Ltmp1: +; CHECK-NEXT: ; %bb.1: ; %try.cont +; CHECK-NEXT: move.l #0, %d0 +; CHECK-NEXT: adda.l #4, %sp +; CHECK-NEXT: rts +; CHECK-NEXT: .LBB0_2: ; %lpad +; CHECK-NEXT: .Ltmp2: +; CHECK-NEXT: move.l %d0, (%sp) +; CHECK-NEXT: jsr _Unwind_Resume@PLT +entry: + invoke void @_Z1fv() optsize + to label %try.cont unwind label %lpad + +lpad: + %0 = landingpad { ptr, i32 } + cleanup + catch ptr @_ZTIi + br label %eh.resume + +try.cont: + ret i32 0 + +eh.resume: + resume { ptr, i32 } %0 +} + +declare void @_Z1fv() optsize + +declare i32 @__gxx_personality_v0(...)