Index: llvm/trunk/lib/Transforms/Utils/SimplifyCFG.cpp =================================================================== --- llvm/trunk/lib/Transforms/Utils/SimplifyCFG.cpp +++ llvm/trunk/lib/Transforms/Utils/SimplifyCFG.cpp @@ -4189,6 +4189,7 @@ Builder.CreateAssumption(Builder.CreateNot(Cond)); Builder.CreateBr(BI->getSuccessor(1)); EraseTerminatorAndDCECond(BI); + Changed = true; } else if (BI->getSuccessor(1) == BB) { Builder.CreateAssumption(Cond); Builder.CreateBr(BI->getSuccessor(0)); Index: llvm/trunk/test/Transforms/SimplifyCFG/invalidate-dom.ll =================================================================== --- llvm/trunk/test/Transforms/SimplifyCFG/invalidate-dom.ll +++ llvm/trunk/test/Transforms/SimplifyCFG/invalidate-dom.ll @@ -0,0 +1,90 @@ +; RUN: opt -aa-pipeline=default -passes="default" -disable-output %s +; REQUIRES: asserts +; PR42272 + +target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128" +target triple = "x86_64-unknown-linux-gnu" + +@b = external global i32, align 4 +@f = external global i32, align 4 +@g = external global i32, align 4 + +define i32* @a(i32 %h) #0 { +entry: + %h.addr = alloca i32, align 4 + store i32 %h, i32* %h.addr, align 4 + %tmp0 = load i32, i32* %h.addr, align 4 + switch i32 %tmp0, label %sw.default [ + i32 4, label %sw.bb + i32 3, label %sw.bb1 + i32 2, label %sw.bb3 + ] + +sw.bb: ; preds = %entry + %call = call i32 (...) @c() + unreachable + +sw.bb1: ; preds = %entry + %call2 = call i32 (...) @c() + unreachable + +sw.bb3: ; preds = %entry + %call4 = call i32 (...) @c() + %conv = sext i32 %call4 to i64 + %tmp1 = inttoptr i64 %conv to i32* + ret i32* %tmp1 + +sw.default: ; preds = %entry + unreachable +} + +define i32 @m() #1 { +entry: + %call = call i32 @j() + %call1 = call i32 @j() + ret i32 undef +} + +define internal i32 @j() #0 { +entry: + %i = alloca i32, align 4 + store i32 0, i32* %i, align 4 + br label %for.cond + +for.cond: ; preds = %for.body, %entry + %tmp0 = load i32, i32* %i, align 4 + %tmp1 = load i32, i32* @f, align 4 + %cmp = icmp ult i32 %tmp0, %tmp1 + br i1 %cmp, label %for.body, label %for.cond.cleanup + +for.cond.cleanup: ; preds = %for.cond + %tmp2 = load i32, i32* @f, align 4 + %call3 = call i32* @a(i32 %tmp2) + ret i32 undef + +for.body: ; preds = %for.cond + %call = call i32 (...) @c() + %call1 = call i32 (...) @c() + %call2 = call i32 (...) @c() + %tmp3 = load i32, i32* @b, align 4 + %tmp4 = load i32, i32* @g, align 4 + %sub = sub nsw i32 %tmp4, %tmp3 + store i32 %sub, i32* @g, align 4 + %tmp5 = load i32, i32* %i, align 4 + %inc = add i32 %tmp5, 1 + store i32 %inc, i32* %i, align 4 + br label %for.cond +} + +declare i32 @c(...) #0 + +; Function Attrs: argmemonly nounwind +declare void @llvm.lifetime.start.p0i8(i64 immarg, i8* nocapture) #2 + +; Function Attrs: argmemonly nounwind +declare void @llvm.lifetime.end.p0i8(i64 immarg, i8* nocapture) #2 + +attributes #0 = { "use-soft-float"="false" } +attributes #1 = { "target-cpu"="x86-64" } +attributes #2 = { argmemonly nounwind } +