diff --git a/llvm/lib/Target/X86/X86IndirectBranchTracking.cpp b/llvm/lib/Target/X86/X86IndirectBranchTracking.cpp --- a/llvm/lib/Target/X86/X86IndirectBranchTracking.cpp +++ b/llvm/lib/Target/X86/X86IndirectBranchTracking.cpp @@ -127,15 +127,27 @@ if (MBB.hasAddressTaken()) Changed |= addENDBR(MBB, MBB.begin()); - // Exception handle may indirectly jump to catch pad, So we should add - // ENDBR before catch pad instructions. - bool EHPadIBTNeeded = MBB.isEHPad(); + bool EHPadIBTNeeded = true; + bool isEHPadBB = MBB.isEHPad(); for (MachineBasicBlock::iterator I = MBB.begin(); I != MBB.end(); ++I) { if (I->isCall() && IsCallReturnTwice(I->getOperand(0))) Changed |= addENDBR(MBB, std::next(I)); - if (EHPadIBTNeeded && I->isEHLabel()) { + // Exception handle may indirectly jump to catch pad, So we should add + // ENDBR before catch pad instructions. For some exception mode, the old + // landingpad BB may create a new landingpad BB and use indirect branch + // jump to the old landingpad BB in lowering. + if (isEHPadBB && !I->isDebugInstr() && EHPadIBTNeeded) { + if (I->isEHLabel()) + Changed |= addENDBR(MBB, std::next(I)); + else + Changed |= addENDBR(MBB, I); + EHPadIBTNeeded = false; + } + if (!isEHPadBB && I->isEHLabel() && EHPadIBTNeeded) { + MCSymbol *Sym = I->getOperand(0).getMCSymbol(); + if (MF.hasCallSiteLandingPad(Sym)) Changed |= addENDBR(MBB, std::next(I)); EHPadIBTNeeded = false; } diff --git a/llvm/test/CodeGen/X86/indirect-branch-tracking-eh.ll b/llvm/test/CodeGen/X86/indirect-branch-tracking-eh.ll --- a/llvm/test/CodeGen/X86/indirect-branch-tracking-eh.ll +++ b/llvm/test/CodeGen/X86/indirect-branch-tracking-eh.ll @@ -1,15 +1,25 @@ -; RUN: llc -mtriple=x86_64-unknown-unknown < %s | FileCheck %s -; RUN: llc -mtriple=i386-unknown-unknown < %s | FileCheck %s +; RUN: llc -mtriple=x86_64-unknown-unknown < %s | FileCheck %s --check-prefix=X86_64 +; RUN: llc -mtriple=i386-unknown-unknown < %s | FileCheck %s --check-prefix=X86 +; RUN: llc -mtriple i386-windows-gnu -exception-model sjlj -verify-machineinstrs=0 < %s | FileCheck %s --check-prefix=SJLJ -;There should be 2 endbr* instruction at entry and catch pad. -;CHECK-COUNT-2: endbr +; ALL-LABEL: test_eh +; X86_64: endbr64 +; X86: endbr32 +; SJLJ: endbr32 +; ALL: call{{.}} __Z20function_that_throwsv +; SJLJ: LBB0_{{.}}: +; SJLJ: endbr32 +; ALL: LBB0_{{.}}: # %lpad +; X86_64: endbr64 +; X86: endbr32 +; SJLJ: endbr32 declare void @_Z20function_that_throwsv() declare i32 @__gxx_personality_sj0(...) declare i8* @__cxa_begin_catch(i8*) declare void @__cxa_end_catch() -define void @test8() personality i8* bitcast (i32 (...)* @__gxx_personality_sj0 to i8*) { +define void @test_eh() personality i8* bitcast (i32 (...)* @__gxx_personality_sj0 to i8*) { entry: invoke void @_Z20function_that_throwsv() to label %try.cont unwind label %lpad