diff --git a/llvm/lib/Transforms/Utils/SimplifyCFG.cpp b/llvm/lib/Transforms/Utils/SimplifyCFG.cpp --- a/llvm/lib/Transforms/Utils/SimplifyCFG.cpp +++ b/llvm/lib/Transforms/Utils/SimplifyCFG.cpp @@ -4673,17 +4673,13 @@ if (BBI->mayHaveSideEffects()) { if (auto *SI = dyn_cast(BBI)) { + // Temporarily disable removal of volatile stores preceding unreachable, + // pending a potential LangRef change permitting volatile stores to + // trap. + // TODO: Either remove this code, or properly integrate the check into + // isGuaranteedToTransferExecutionToSuccessor(). if (SI->isVolatile()) break; - } else if (auto *LI = dyn_cast(BBI)) { - if (LI->isVolatile()) - break; - } else if (auto *RMWI = dyn_cast(BBI)) { - if (RMWI->isVolatile()) - break; - } else if (auto *CXI = dyn_cast(BBI)) { - if (CXI->isVolatile()) - break; } else if (isa(BBI)) { // A catchpad may invoke exception object constructors and such, which // in some languages can be arbitrary code, so be conservative by @@ -4692,8 +4688,9 @@ if (classifyEHPersonality(BB->getParent()->getPersonalityFn()) != EHPersonality::CoreCLR) break; - } else if (!isa(BBI) && !isa(BBI) && - !isa(BBI)) { + } else if (!isa(BBI) && !isa(BBI) && + !isa(BBI) && !isa(BBI) && + !isa(BBI) && !isa(BBI)) { break; } // Note that deleting LandingPad's here is in fact okay, although it diff --git a/llvm/test/Transforms/SimplifyCFG/trapping-load-unreachable.ll b/llvm/test/Transforms/SimplifyCFG/trapping-load-unreachable.ll --- a/llvm/test/Transforms/SimplifyCFG/trapping-load-unreachable.ll +++ b/llvm/test/Transforms/SimplifyCFG/trapping-load-unreachable.ll @@ -10,11 +10,8 @@ ; CHECK-LABEL: @test1( ; CHECK-NEXT: entry: ; CHECK-NEXT: [[TMP0:%.*]] = icmp eq i32 [[X:%.*]], 0 -; CHECK-NEXT: br i1 [[TMP0]], label [[BB:%.*]], label [[RETURN:%.*]] -; CHECK: bb: -; CHECK-NEXT: [[TMP1:%.*]] = load volatile i32, i32* null, align 4 -; CHECK-NEXT: unreachable -; CHECK: return: +; CHECK-NEXT: [[TMP1:%.*]] = xor i1 [[TMP0]], true +; CHECK-NEXT: call void @llvm.assume(i1 [[TMP1]]) ; CHECK-NEXT: ret void ; entry: @@ -34,11 +31,8 @@ ; CHECK-LABEL: @test1_no_null_opt( ; CHECK-NEXT: entry: ; CHECK-NEXT: [[TMP0:%.*]] = icmp eq i32 [[X:%.*]], 0 -; CHECK-NEXT: br i1 [[TMP0]], label [[BB:%.*]], label [[RETURN:%.*]] -; CHECK: bb: -; CHECK-NEXT: [[TMP1:%.*]] = load volatile i32, i32* null, align 4 -; CHECK-NEXT: unreachable -; CHECK: return: +; CHECK-NEXT: [[TMP1:%.*]] = xor i1 [[TMP0]], true +; CHECK-NEXT: call void @llvm.assume(i1 [[TMP1]]) ; CHECK-NEXT: ret void ; entry: @@ -127,11 +121,8 @@ define void @test5(i1 %C, i32* %P) { ; CHECK-LABEL: @test5( ; CHECK-NEXT: entry: -; CHECK-NEXT: br i1 [[C:%.*]], label [[T:%.*]], label [[F:%.*]] -; CHECK: T: -; CHECK-NEXT: [[TMP0:%.*]] = cmpxchg volatile i32* [[P:%.*]], i32 0, i32 1 seq_cst seq_cst, align 4 -; CHECK-NEXT: unreachable -; CHECK: F: +; CHECK-NEXT: [[TMP0:%.*]] = xor i1 [[C:%.*]], true +; CHECK-NEXT: call void @llvm.assume(i1 [[TMP0]]) ; CHECK-NEXT: ret void ; entry: @@ -147,11 +138,8 @@ define void @test6(i1 %C, i32* %P) { ; CHECK-LABEL: @test6( ; CHECK-NEXT: entry: -; CHECK-NEXT: br i1 [[C:%.*]], label [[T:%.*]], label [[F:%.*]] -; CHECK: T: -; CHECK-NEXT: [[TMP0:%.*]] = atomicrmw volatile xchg i32* [[P:%.*]], i32 0 seq_cst, align 4 -; CHECK-NEXT: unreachable -; CHECK: F: +; CHECK-NEXT: [[TMP0:%.*]] = xor i1 [[C:%.*]], true +; CHECK-NEXT: call void @llvm.assume(i1 [[TMP0]]) ; CHECK-NEXT: ret void ; entry: