From 2824927e8ac2ab3074f09ededd2b9c67d490a288 Mon Sep 17 00:00:00 2001 From: Sanjay Patel Date: Sun, 9 Apr 2017 16:16:32 +0000 Subject: [PATCH] [SimplifyCFG] auto-generate better checks; NFC llvm-svn: 299825 --- .../Transforms/SimplifyCFG/merge-cond-stores.ll | 163 ++++++++++++++++----- 1 file changed, 130 insertions(+), 33 deletions(-) diff --git a/llvm/test/Transforms/SimplifyCFG/merge-cond-stores.ll b/llvm/test/Transforms/SimplifyCFG/merge-cond-stores.ll index 77e3158..baec524 100644 --- a/llvm/test/Transforms/SimplifyCFG/merge-cond-stores.ll +++ b/llvm/test/Transforms/SimplifyCFG/merge-cond-stores.ll @@ -1,16 +1,21 @@ +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py ; RUN: opt -simplifycfg -instcombine < %s -simplifycfg-merge-cond-stores=true -simplifycfg-merge-cond-stores-aggressively=false -phi-node-folding-threshold=2 -S | FileCheck %s -; CHECK-LABEL: @test_simple ; This test should succeed and end up if-converted. -; CHECK: icmp eq i32 %b, 0 -; CHECK-NEXT: icmp ne i32 %a, 0 -; CHECK-NEXT: xor i1 %x2, true -; CHECK-NEXT: %[[x:.*]] = or i1 %{{.*}}, %{{.*}} -; CHECK-NEXT: br i1 %[[x]] -; CHECK: store -; CHECK-NOT: store -; CHECK: ret define void @test_simple(i32* %p, i32 %a, i32 %b) { +; CHECK-LABEL: @test_simple( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[X2:%.*]] = icmp eq i32 [[B:%.*]], 0 +; CHECK-NEXT: [[TMP0:%.*]] = icmp ne i32 [[A:%.*]], 0 +; CHECK-NEXT: [[TMP1:%.*]] = xor i1 [[X2]], true +; CHECK-NEXT: [[TMP2:%.*]] = or i1 [[TMP0]], [[TMP1]] +; CHECK-NEXT: br i1 [[TMP2]], label [[TMP3:%.*]], label [[TMP4:%.*]] +; CHECK: [[NOT_X2:%.*]] = xor i1 [[X2]], true +; CHECK-NEXT: [[DOT:%.*]] = zext i1 [[NOT_X2]] to i32 +; CHECK-NEXT: store i32 [[DOT]], i32* [[P:%.*]], align 4 +; CHECK-NEXT: br label [[TMP4]] +; CHECK: ret void +; entry: %x1 = icmp eq i32 %a, 0 br i1 %x1, label %fallthrough, label %yes1 @@ -31,12 +36,26 @@ end: ret void } -; CHECK-LABEL: @test_recursive ; This test should entirely fold away, leaving one large basic block. -; CHECK: store -; CHECK-NOT: store -; CHECK: ret define void @test_recursive(i32* %p, i32 %a, i32 %b, i32 %c, i32 %d) { +; CHECK-LABEL: @test_recursive( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[TMP0:%.*]] = or i32 [[B:%.*]], [[A:%.*]] +; CHECK-NEXT: [[X4:%.*]] = icmp eq i32 [[D:%.*]], 0 +; CHECK-NEXT: [[TMP1:%.*]] = or i32 [[TMP0]], [[C:%.*]] +; CHECK-NEXT: [[TMP2:%.*]] = xor i1 [[X4]], true +; CHECK-NEXT: [[TMP3:%.*]] = icmp ne i32 [[TMP1]], 0 +; CHECK-NEXT: [[TMP4:%.*]] = or i1 [[TMP3]], [[TMP2]] +; CHECK-NEXT: br i1 [[TMP4]], label [[TMP5:%.*]], label [[TMP6:%.*]] +; CHECK: [[X3:%.*]] = icmp eq i32 [[C]], 0 +; CHECK-NEXT: [[NOT_X2:%.*]] = icmp ne i32 [[B]], 0 +; CHECK-NEXT: [[DOT:%.*]] = zext i1 [[NOT_X2]] to i32 +; CHECK-NEXT: [[DOT_:%.*]] = select i1 [[X3]], i32 [[DOT]], i32 2 +; CHECK-NEXT: [[DOT__:%.*]] = select i1 [[X4]], i32 [[DOT_]], i32 3 +; CHECK-NEXT: store i32 [[DOT__]], i32* [[P:%.*]], align 4 +; CHECK-NEXT: br label [[TMP6]] +; CHECK: ret void +; entry: %x1 = icmp eq i32 %a, 0 br i1 %x1, label %fallthrough, label %yes1 @@ -74,13 +93,31 @@ end: ret void } -; CHECK-LABEL: @test_not_ifconverted ; The code in each diamond is too large - it won't be if-converted so our ; heuristics should say no. -; CHECK: store -; CHECK: store -; CHECK: ret define void @test_not_ifconverted(i32* %p, i32 %a, i32 %b) { +; CHECK-LABEL: @test_not_ifconverted( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[X1:%.*]] = icmp eq i32 [[A:%.*]], 0 +; CHECK-NEXT: br i1 [[X1]], label [[FALLTHROUGH:%.*]], label [[YES1:%.*]] +; CHECK: yes1: +; CHECK-NEXT: [[Y1:%.*]] = or i32 [[B:%.*]], 55 +; CHECK-NEXT: [[Y2:%.*]] = add i32 [[Y1]], 24 +; CHECK-NEXT: [[Y3:%.*]] = and i32 [[Y2]], 67 +; CHECK-NEXT: store i32 [[Y3]], i32* [[P:%.*]], align 4 +; CHECK-NEXT: br label [[FALLTHROUGH]] +; CHECK: fallthrough: +; CHECK-NEXT: [[X2:%.*]] = icmp eq i32 [[B]], 0 +; CHECK-NEXT: br i1 [[X2]], label [[END:%.*]], label [[YES2:%.*]] +; CHECK: yes2: +; CHECK-NEXT: [[Z1:%.*]] = or i32 [[A]], 55 +; CHECK-NEXT: [[Z2:%.*]] = add i32 [[Z1]], 24 +; CHECK-NEXT: [[Z3:%.*]] = and i32 [[Z2]], 67 +; CHECK-NEXT: store i32 [[Z3]], i32* [[P]], align 4 +; CHECK-NEXT: br label [[END]] +; CHECK: end: +; CHECK-NEXT: ret void +; entry: %x1 = icmp eq i32 %a, 0 br i1 %x1, label %fallthrough, label %yes1 @@ -107,13 +144,26 @@ end: ret void } -; CHECK-LABEL: @test_aliasing1 ; The store to %p clobbers the previous store, so if-converting this would ; be illegal. -; CHECK: store -; CHECK: store -; CHECK: ret define void @test_aliasing1(i32* %p, i32 %a, i32 %b) { +; CHECK-LABEL: @test_aliasing1( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[X1:%.*]] = icmp eq i32 [[A:%.*]], 0 +; CHECK-NEXT: br i1 [[X1]], label [[FALLTHROUGH:%.*]], label [[YES1:%.*]] +; CHECK: yes1: +; CHECK-NEXT: store i32 0, i32* [[P:%.*]], align 4 +; CHECK-NEXT: br label [[FALLTHROUGH]] +; CHECK: fallthrough: +; CHECK-NEXT: [[Y1:%.*]] = load i32, i32* [[P]], align 4 +; CHECK-NEXT: [[X2:%.*]] = icmp eq i32 [[Y1]], 0 +; CHECK-NEXT: br i1 [[X2]], label [[END:%.*]], label [[YES2:%.*]] +; CHECK: yes2: +; CHECK-NEXT: store i32 1, i32* [[P]], align 4 +; CHECK-NEXT: br label [[END]] +; CHECK: end: +; CHECK-NEXT: ret void +; entry: %x1 = icmp eq i32 %a, 0 br i1 %x1, label %fallthrough, label %yes1 @@ -135,12 +185,25 @@ end: ret void } -; CHECK-LABEL: @test_aliasing2 ; The load from %q aliases with %p, so if-converting this would be illegal. -; CHECK: store -; CHECK: store -; CHECK: ret define void @test_aliasing2(i32* %p, i32* %q, i32 %a, i32 %b) { +; CHECK-LABEL: @test_aliasing2( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[X1:%.*]] = icmp eq i32 [[A:%.*]], 0 +; CHECK-NEXT: br i1 [[X1]], label [[FALLTHROUGH:%.*]], label [[YES1:%.*]] +; CHECK: yes1: +; CHECK-NEXT: store i32 0, i32* [[P:%.*]], align 4 +; CHECK-NEXT: br label [[FALLTHROUGH]] +; CHECK: fallthrough: +; CHECK-NEXT: [[Y1:%.*]] = load i32, i32* [[Q:%.*]], align 4 +; CHECK-NEXT: [[X2:%.*]] = icmp eq i32 [[Y1]], 0 +; CHECK-NEXT: br i1 [[X2]], label [[END:%.*]], label [[YES2:%.*]] +; CHECK: yes2: +; CHECK-NEXT: store i32 1, i32* [[P]], align 4 +; CHECK-NEXT: br label [[END]] +; CHECK: end: +; CHECK-NEXT: ret void +; entry: %x1 = icmp eq i32 %a, 0 br i1 %x1, label %fallthrough, label %yes1 @@ -164,12 +227,24 @@ end: declare void @f() -; CHECK-LABEL: @test_diamond_simple ; This should get if-converted. -; CHECK: store -; CHECK-NOT: store -; CHECK: ret define i32 @test_diamond_simple(i32* %p, i32* %q, i32 %a, i32 %b) { +; CHECK-LABEL: @test_diamond_simple( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[X1:%.*]] = icmp eq i32 [[A:%.*]], 0 +; CHECK-NEXT: [[Z1:%.*]] = add i32 [[A]], [[B:%.*]] +; CHECK-NEXT: [[Z2:%.*]] = select i1 [[X1]], i32 [[Z1]], i32 0 +; CHECK-NEXT: [[X2:%.*]] = icmp eq i32 [[B]], 0 +; CHECK-NEXT: [[Z3:%.*]] = sub i32 [[Z2]], [[B]] +; CHECK-NEXT: [[Z4:%.*]] = select i1 [[X2]], i32 [[Z3]], i32 3 +; CHECK-NEXT: [[TMP0:%.*]] = or i32 [[A]], [[B]] +; CHECK-NEXT: [[TMP1:%.*]] = icmp eq i32 [[TMP0]], 0 +; CHECK-NEXT: br i1 [[TMP1]], label [[TMP3:%.*]], label [[TMP2:%.*]] +; CHECK: [[SIMPLIFYCFG_MERGE:%.*]] = select i1 [[X2]], i32 [[Z2]], i32 1 +; CHECK-NEXT: store i32 [[SIMPLIFYCFG_MERGE]], i32* [[P:%.*]], align 4 +; CHECK-NEXT: br label [[TMP3]] +; CHECK: ret i32 [[Z4]] +; entry: %x1 = icmp eq i32 %a, 0 br i1 %x1, label %no1, label %yes1 @@ -200,14 +275,36 @@ end: ret i32 %z4 } -; CHECK-LABEL: @test_diamond_alias3 ; Now there is a call to f() in the bottom branch. The store in the first ; branch would now be reordered with respect to the call if we if-converted, ; so we must not. -; CHECK: store -; CHECK: store -; CHECK: ret define i32 @test_diamond_alias3(i32* %p, i32* %q, i32 %a, i32 %b) { +; CHECK-LABEL: @test_diamond_alias3( +; CHECK-NEXT: entry: +; CHECK-NEXT: [[X1:%.*]] = icmp eq i32 [[A:%.*]], 0 +; CHECK-NEXT: br i1 [[X1]], label [[NO1:%.*]], label [[YES1:%.*]] +; CHECK: yes1: +; CHECK-NEXT: store i32 0, i32* [[P:%.*]], align 4 +; CHECK-NEXT: br label [[FALLTHROUGH:%.*]] +; CHECK: no1: +; CHECK-NEXT: call void @f() +; CHECK-NEXT: [[Z1:%.*]] = add i32 [[A]], [[B:%.*]] +; CHECK-NEXT: br label [[FALLTHROUGH]] +; CHECK: fallthrough: +; CHECK-NEXT: [[Z2:%.*]] = phi i32 [ [[Z1]], [[NO1]] ], [ 0, [[YES1]] ] +; CHECK-NEXT: [[X2:%.*]] = icmp eq i32 [[B]], 0 +; CHECK-NEXT: br i1 [[X2]], label [[NO2:%.*]], label [[YES2:%.*]] +; CHECK: yes2: +; CHECK-NEXT: store i32 1, i32* [[P]], align 4 +; CHECK-NEXT: br label [[END:%.*]] +; CHECK: no2: +; CHECK-NEXT: call void @f() +; CHECK-NEXT: [[Z3:%.*]] = sub i32 [[Z2]], [[B]] +; CHECK-NEXT: br label [[END]] +; CHECK: end: +; CHECK-NEXT: [[Z4:%.*]] = phi i32 [ [[Z3]], [[NO2]] ], [ 3, [[YES2]] ] +; CHECK-NEXT: ret i32 [[Z4]] +; entry: %x1 = icmp eq i32 %a, 0 br i1 %x1, label %no1, label %yes1 -- 2.7.4