Home | History | Annotate | Download | only in SimplifyCFG
      1 ; RUN: opt < %s -simplifycfg -S > %t
      2 ; RUN: not grep {^BB.tomerge} %t
      3 ; RUN: grep {^BB.nomerge} %t | count 2
      4 
      5 ; ModuleID = '<stdin>' 
      6 declare i1 @foo()
      7 
      8 declare i1 @bar(i32)
      9 
     10 ; This function can't be merged
     11 define void @a() {
     12 entry:
     13 	br label %BB.nomerge
     14 
     15 BB.nomerge:		; preds = %Common, %entry
     16         ; This phi has a conflicting value (0) with below phi (2), so blocks
     17         ; can't be merged.
     18 	%a = phi i32 [ 1, %entry ], [ 0, %Common ]		; <i32> [#uses=1]
     19 	br label %Succ
     20 
     21 Succ:		; preds = %Common, %BB.nomerge
     22 	%b = phi i32 [ %a, %BB.nomerge ], [ 2, %Common ]		; <i32> [#uses=0]
     23 	%conde = call i1 @foo( )		; <i1> [#uses=1]
     24 	br i1 %conde, label %Common, label %Exit
     25 
     26 Common:		; preds = %Succ
     27 	%cond = call i1 @foo( )		; <i1> [#uses=1]
     28 	br i1 %cond, label %BB.nomerge, label %Succ
     29 
     30 Exit:		; preds = %Succ
     31 	ret void
     32 }
     33 
     34 ; This function can't be merged
     35 define void @b() {
     36 entry:
     37 	br label %BB.nomerge
     38 
     39 BB.nomerge:		; preds = %Common, %entry
     40 	br label %Succ
     41 
     42 Succ:		; preds = %Common, %BB.nomerge
     43         ; This phi has confliction values for Common and (through BB) Common,
     44         ; blocks can't be merged
     45 	%b = phi i32 [ 1, %BB.nomerge ], [ 2, %Common ]		; <i32> [#uses=0]
     46 	%conde = call i1 @foo( )		; <i1> [#uses=1]
     47 	br i1 %conde, label %Common, label %Exit
     48 
     49 Common:		; preds = %Succ
     50 	%cond = call i1 @foo( )		; <i1> [#uses=1]
     51 	br i1 %cond, label %BB.nomerge, label %Succ
     52 
     53 Exit:		; preds = %Succ
     54 	ret void
     55 }
     56 
     57 ; This function can be merged
     58 define void @c() {
     59 entry:
     60 	br label %BB.tomerge
     61 
     62 BB.tomerge:		; preds = %Common, %entry
     63 	br label %Succ
     64 
     65 Succ:		; preds = %Common, %BB.tomerge, %Pre-Exit
     66         ; This phi has identical values for Common and (through BB) Common,
     67         ; blocks can't be merged
     68 	%b = phi i32 [ 1, %BB.tomerge ], [ 1, %Common ], [ 2, %Pre-Exit ]
     69 	%conde = call i1 @foo( )		; <i1> [#uses=1]
     70 	br i1 %conde, label %Common, label %Pre-Exit
     71 
     72 Common:		; preds = %Succ
     73 	%cond = call i1 @foo( )		; <i1> [#uses=1]
     74 	br i1 %cond, label %BB.tomerge, label %Succ
     75 
     76 Pre-Exit:       ; preds = %Succ
     77         ; This adds a backedge, so the %b phi node gets a third branch and is
     78         ; not completely trivial
     79 	%cond2 = call i1 @foo( )		; <i1> [#uses=1]
     80 	br i1 %cond2, label %Succ, label %Exit
     81         
     82 Exit:		; preds = %Pre-Exit
     83 	ret void
     84 }
     85 
     86 ; This function can be merged
     87 define void @d() {
     88 entry:
     89 	br label %BB.tomerge
     90 
     91 BB.tomerge:		; preds = %Common, %entry
     92         ; This phi has a matching value (0) with below phi (0), so blocks
     93         ; can be merged.
     94 	%a = phi i32 [ 1, %entry ], [ 0, %Common ]		; <i32> [#uses=1]
     95 	br label %Succ
     96 
     97 Succ:		; preds = %Common, %BB.tomerge
     98 	%b = phi i32 [ %a, %BB.tomerge ], [ 0, %Common ]		; <i32> [#uses=0]
     99 	%conde = call i1 @foo( )		; <i1> [#uses=1]
    100 	br i1 %conde, label %Common, label %Exit
    101 
    102 Common:		; preds = %Succ
    103 	%cond = call i1 @foo( )		; <i1> [#uses=1]
    104 	br i1 %cond, label %BB.tomerge, label %Succ
    105 
    106 Exit:		; preds = %Succ
    107 	ret void
    108 }
    109 
    110 ; This function can be merged
    111 define void @e() {
    112 entry:
    113 	br label %BB.tomerge
    114 
    115 BB.tomerge:		; preds = %Use, %entry
    116         ; This phi is used somewhere else than Succ, but this should not prevent
    117         ; merging this block
    118 	%a = phi i32 [ 1, %entry ], [ 0, %Use ]		; <i32> [#uses=1]
    119 	br label %Succ
    120 
    121 Succ:		; preds = %BB.tomerge
    122 	%conde = call i1 @foo( )		; <i1> [#uses=1]
    123 	br i1 %conde, label %Use, label %Exit
    124 
    125 Use:		; preds = %Succ
    126 	%cond = call i1 @bar( i32 %a )		; <i1> [#uses=1]
    127 	br i1 %cond, label %BB.tomerge, label %Exit
    128 
    129 Exit:		; preds = %Use, %Succ
    130 	ret void
    131 }
    132