@@ -3546,7 +3546,7 @@ static void emitCheckHandlerCall(CodeGenFunction &CGF,
35463546 ArrayRef<llvm::Value *> FnArgs,
35473547 SanitizerHandler CheckHandler,
35483548 CheckRecoverableKind RecoverKind, bool IsFatal,
3549- llvm::BasicBlock *ContBB) {
3549+ llvm::BasicBlock *ContBB, bool NoMerge ) {
35503550 assert (IsFatal || RecoverKind != CheckRecoverableKind::Unrecoverable);
35513551 std::optional<ApplyDebugLocation> DL;
35523552 if (!CGF.Builder .getCurrentDebugLocation ()) {
@@ -3581,10 +3581,9 @@ static void emitCheckHandlerCall(CodeGenFunction &CGF,
35813581 llvm::AttributeList::FunctionIndex, B),
35823582 /* Local=*/ true );
35833583 llvm::CallInst *HandlerCall = CGF.EmitNounwindRuntimeCall (Fn, FnArgs);
3584- bool NoMerge =
3585- ClSanitizeDebugDeoptimization ||
3586- !CGF.CGM .getCodeGenOpts ().OptimizationLevel ||
3587- (CGF.CurCodeDecl && CGF.CurCodeDecl ->hasAttr <OptimizeNoneAttr>());
3584+ NoMerge = NoMerge || ClSanitizeDebugDeoptimization ||
3585+ !CGF.CGM .getCodeGenOpts ().OptimizationLevel ||
3586+ (CGF.CurCodeDecl && CGF.CurCodeDecl ->hasAttr <OptimizeNoneAttr>());
35883587 if (NoMerge)
35893588 HandlerCall->addFnAttr (llvm::Attribute::NoMerge);
35903589 if (!MayReturn) {
@@ -3608,6 +3607,7 @@ void CodeGenFunction::EmitCheck(
36083607 llvm::Value *FatalCond = nullptr ;
36093608 llvm::Value *RecoverableCond = nullptr ;
36103609 llvm::Value *TrapCond = nullptr ;
3610+ bool NoMerge = false ;
36113611 for (int i = 0 , n = Checked.size (); i < n; ++i) {
36123612 llvm::Value *Check = Checked[i].first ;
36133613 // -fsanitize-trap= overrides -fsanitize-recover=.
@@ -3618,6 +3618,9 @@ void CodeGenFunction::EmitCheck(
36183618 ? RecoverableCond
36193619 : FatalCond;
36203620 Cond = Cond ? Builder.CreateAnd (Cond, Check) : Check;
3621+
3622+ if (!CGM.getCodeGenOpts ().SanitizeMergeHandlers .has (Checked[i].second ))
3623+ NoMerge = true ;
36213624 }
36223625
36233626 if (ClSanitizeGuardChecks) {
@@ -3632,7 +3635,7 @@ void CodeGenFunction::EmitCheck(
36323635 }
36333636
36343637 if (TrapCond)
3635- EmitTrapCheck (TrapCond, CheckHandler);
3638+ EmitTrapCheck (TrapCond, CheckHandler, NoMerge );
36363639 if (!FatalCond && !RecoverableCond)
36373640 return ;
36383641
@@ -3698,7 +3701,7 @@ void CodeGenFunction::EmitCheck(
36983701 // Simple case: we need to generate a single handler call, either
36993702 // fatal, or non-fatal.
37003703 emitCheckHandlerCall (*this , FnType, Args, CheckHandler, RecoverKind,
3701- (FatalCond != nullptr ), Cont);
3704+ (FatalCond != nullptr ), Cont, NoMerge );
37023705 } else {
37033706 // Emit two handler calls: first one for set of unrecoverable checks,
37043707 // another one for recoverable.
@@ -3708,10 +3711,10 @@ void CodeGenFunction::EmitCheck(
37083711 Builder.CreateCondBr (FatalCond, NonFatalHandlerBB, FatalHandlerBB);
37093712 EmitBlock (FatalHandlerBB);
37103713 emitCheckHandlerCall (*this , FnType, Args, CheckHandler, RecoverKind, true ,
3711- NonFatalHandlerBB);
3714+ NonFatalHandlerBB, NoMerge );
37123715 EmitBlock (NonFatalHandlerBB);
37133716 emitCheckHandlerCall (*this , FnType, Args, CheckHandler, RecoverKind, false ,
3714- Cont);
3717+ Cont, NoMerge );
37153718 }
37163719
37173720 EmitBlock (Cont);
@@ -3901,7 +3904,8 @@ void CodeGenFunction::EmitUnreachable(SourceLocation Loc) {
39013904}
39023905
39033906void CodeGenFunction::EmitTrapCheck (llvm::Value *Checked,
3904- SanitizerHandler CheckHandlerID) {
3907+ SanitizerHandler CheckHandlerID,
3908+ bool NoMerge) {
39053909 llvm::BasicBlock *Cont = createBasicBlock (" cont" );
39063910
39073911 // If we're optimizing, collapse all calls to trap down to just one per
@@ -3911,9 +3915,9 @@ void CodeGenFunction::EmitTrapCheck(llvm::Value *Checked,
39113915
39123916 llvm::BasicBlock *&TrapBB = TrapBBs[CheckHandlerID];
39133917
3914- bool NoMerge = ClSanitizeDebugDeoptimization ||
3915- !CGM.getCodeGenOpts ().OptimizationLevel ||
3916- (CurCodeDecl && CurCodeDecl->hasAttr <OptimizeNoneAttr>());
3918+ NoMerge = NoMerge || ClSanitizeDebugDeoptimization ||
3919+ !CGM.getCodeGenOpts ().OptimizationLevel ||
3920+ (CurCodeDecl && CurCodeDecl->hasAttr <OptimizeNoneAttr>());
39173921
39183922 if (TrapBB && !NoMerge) {
39193923 auto Call = TrapBB->begin ();
0 commit comments