1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py 2; RUN: opt < %s -reassociate -gvn -instcombine -S | FileCheck %s 3; RUN: opt < %s -passes='reassociate,gvn,instcombine' -S | FileCheck %s 4 5define i32 @test1(i32 %arg) { 6; CHECK-LABEL: @test1( 7; CHECK-NEXT: [[ARG_NEG:%.*]] = sub i32 0, [[ARG:%.*]] 8; CHECK-NEXT: ret i32 [[ARG_NEG]] 9; 10 %tmp1 = sub i32 -12, %arg 11 %tmp2 = add i32 %tmp1, 12 12 ret i32 %tmp2 13} 14 15define i32 @test2(i32 %reg109, i32 %reg1111) { 16; CHECK-LABEL: @test2( 17; CHECK-NEXT: [[REG117:%.*]] = add i32 [[REG1111:%.*]], [[REG109:%.*]] 18; CHECK-NEXT: ret i32 [[REG117]] 19; 20 %reg115 = add i32 %reg109, -30 21 %reg116 = add i32 %reg115, %reg1111 22 %reg117 = add i32 %reg116, 30 23 ret i32 %reg117 24} 25 26@e = external global i32 27@a = external global i32 28@b = external global i32 29@c = external global i32 30@f = external global i32 31 32define void @test3() { 33; CHECK-LABEL: @test3( 34; CHECK-NEXT: [[A:%.*]] = load i32, i32* @a, align 4 35; CHECK-NEXT: [[B:%.*]] = load i32, i32* @b, align 4 36; CHECK-NEXT: [[C:%.*]] = load i32, i32* @c, align 4 37; CHECK-NEXT: [[T1:%.*]] = add i32 [[B]], [[A]] 38; CHECK-NEXT: [[T2:%.*]] = add i32 [[T1]], [[C]] 39; CHECK-NEXT: store i32 [[T2]], i32* @e, align 4 40; CHECK-NEXT: store i32 [[T2]], i32* @f, align 4 41; CHECK-NEXT: ret void 42; 43 %A = load i32, i32* @a 44 %B = load i32, i32* @b 45 %C = load i32, i32* @c 46 %t1 = add i32 %A, %B 47 %t2 = add i32 %t1, %C 48 %t3 = add i32 %C, %A 49 %t4 = add i32 %t3, %B 50 ; e = (a+b)+c; 51 store i32 %t2, i32* @e 52 ; f = (a+c)+b 53 store i32 %t4, i32* @f 54 ret void 55} 56 57define void @test4() { 58; CHECK-LABEL: @test4( 59; CHECK-NEXT: [[A:%.*]] = load i32, i32* @a, align 4 60; CHECK-NEXT: [[B:%.*]] = load i32, i32* @b, align 4 61; CHECK-NEXT: [[C:%.*]] = load i32, i32* @c, align 4 62; CHECK-NEXT: [[T1:%.*]] = add i32 [[B]], [[A]] 63; CHECK-NEXT: [[T2:%.*]] = add i32 [[T1]], [[C]] 64; CHECK-NEXT: store i32 [[T2]], i32* @e, align 4 65; CHECK-NEXT: store i32 [[T2]], i32* @f, align 4 66; CHECK-NEXT: ret void 67; 68 %A = load i32, i32* @a 69 %B = load i32, i32* @b 70 %C = load i32, i32* @c 71 %t1 = add i32 %A, %B 72 %t2 = add i32 %t1, %C 73 %t3 = add i32 %C, %A 74 %t4 = add i32 %t3, %B 75 ; e = c+(a+b) 76 store i32 %t2, i32* @e 77 ; f = (c+a)+b 78 store i32 %t4, i32* @f 79 ret void 80} 81 82define void @test5() { 83; CHECK-LABEL: @test5( 84; CHECK-NEXT: [[A:%.*]] = load i32, i32* @a, align 4 85; CHECK-NEXT: [[B:%.*]] = load i32, i32* @b, align 4 86; CHECK-NEXT: [[C:%.*]] = load i32, i32* @c, align 4 87; CHECK-NEXT: [[T1:%.*]] = add i32 [[B]], [[A]] 88; CHECK-NEXT: [[T2:%.*]] = add i32 [[T1]], [[C]] 89; CHECK-NEXT: store i32 [[T2]], i32* @e, align 4 90; CHECK-NEXT: store i32 [[T2]], i32* @f, align 4 91; CHECK-NEXT: ret void 92; 93 %A = load i32, i32* @a 94 %B = load i32, i32* @b 95 %C = load i32, i32* @c 96 %t1 = add i32 %B, %A 97 %t2 = add i32 %t1, %C 98 %t3 = add i32 %C, %A 99 %t4 = add i32 %t3, %B 100 ; e = c+(b+a) 101 store i32 %t2, i32* @e 102 ; f = (c+a)+b 103 store i32 %t4, i32* @f 104 ret void 105} 106 107define i32 @test6() { 108; CHECK-LABEL: @test6( 109; CHECK-NEXT: ret i32 0 110; 111 %tmp.0 = load i32, i32* @a 112 %tmp.1 = load i32, i32* @b 113 ; (a+b) 114 %tmp.2 = add i32 %tmp.0, %tmp.1 115 %tmp.4 = load i32, i32* @c 116 ; (a+b)+c 117 %tmp.5 = add i32 %tmp.2, %tmp.4 118 ; (a+c) 119 %tmp.8 = add i32 %tmp.0, %tmp.4 120 ; (a+c)+b 121 %tmp.11 = add i32 %tmp.8, %tmp.1 122 ; X ^ X = 0 123 %RV = xor i32 %tmp.5, %tmp.11 124 ret i32 %RV 125} 126 127; This should be one add and two multiplies. 128; A*A*B + A*C*A 129 130define i32 @test7(i32 %A, i32 %B, i32 %C) { 131; CHECK-LABEL: @test7( 132; CHECK-NEXT: [[REASS_ADD1:%.*]] = add i32 [[C:%.*]], [[B:%.*]] 133; CHECK-NEXT: [[REASS_MUL2:%.*]] = mul i32 [[A:%.*]], [[A]] 134; CHECK-NEXT: [[REASS_MUL:%.*]] = mul i32 [[REASS_MUL2]], [[REASS_ADD1]] 135; CHECK-NEXT: ret i32 [[REASS_MUL]] 136; 137 %aa = mul i32 %A, %A 138 %aab = mul i32 %aa, %B 139 %ac = mul i32 %A, %C 140 %aac = mul i32 %ac, %A 141 %r = add i32 %aab, %aac 142 ret i32 %r 143} 144 145define i32 @test8(i32 %X, i32 %Y, i32 %Z) { 146; CHECK-LABEL: @test8( 147; CHECK-NEXT: [[A:%.*]] = mul i32 [[Y:%.*]], [[X:%.*]] 148; CHECK-NEXT: [[C:%.*]] = sub i32 [[Z:%.*]], [[A]] 149; CHECK-NEXT: ret i32 [[C]] 150; 151 %A = sub i32 0, %X 152 %B = mul i32 %A, %Y 153 ; (-X)*Y + Z -> Z-X*Y 154 %C = add i32 %B, %Z 155 ret i32 %C 156} 157 158; PR5458 159 160define i32 @test9(i32 %X) { 161; CHECK-LABEL: @test9( 162; CHECK-NEXT: [[FACTOR:%.*]] = mul i32 [[X:%.*]], 94 163; CHECK-NEXT: ret i32 [[FACTOR]] 164; 165 %Y = mul i32 %X, 47 166 %Z = add i32 %Y, %Y 167 ret i32 %Z 168} 169 170define i32 @test10(i32 %X) { 171; CHECK-LABEL: @test10( 172; CHECK-NEXT: [[FACTOR:%.*]] = mul i32 [[X:%.*]], 3 173; CHECK-NEXT: ret i32 [[FACTOR]] 174; 175 %Y = add i32 %X ,%X 176 %Z = add i32 %Y, %X 177 ret i32 %Z 178} 179 180define i32 @test11(i32 %W) { 181; CHECK-LABEL: @test11( 182; CHECK-NEXT: [[FACTOR:%.*]] = mul i32 [[W:%.*]], 381 183; CHECK-NEXT: ret i32 [[FACTOR]] 184; 185 %X = mul i32 %W, 127 186 %Y = add i32 %X ,%X 187 %Z = add i32 %Y, %X 188 ret i32 %Z 189} 190 191declare void @mumble(i32) 192 193define i32 @test12(i32 %X) { 194; CHECK-LABEL: @test12( 195; CHECK-NEXT: [[X_NEG:%.*]] = sub i32 0, [[X:%.*]] 196; CHECK-NEXT: call void @mumble(i32 [[X_NEG]]) 197; CHECK-NEXT: [[FACTOR:%.*]] = mul i32 [[X]], -3 198; CHECK-NEXT: [[Z:%.*]] = add i32 [[FACTOR]], 6 199; CHECK-NEXT: ret i32 [[Z]] 200; 201 %X.neg = sub nsw nuw i32 0, %X 202 call void @mumble(i32 %X.neg) 203 %A = sub i32 1, %X 204 %B = sub i32 2, %X 205 %C = sub i32 3, %X 206 %Y = add i32 %A ,%B 207 %Z = add i32 %Y, %C 208 ret i32 %Z 209} 210 211define i32 @test13(i32 %X1, i32 %X2, i32 %X3) { 212; CHECK-LABEL: @test13( 213; CHECK-NEXT: [[REASS_ADD:%.*]] = sub i32 [[X3:%.*]], [[X2:%.*]] 214; CHECK-NEXT: [[REASS_MUL:%.*]] = mul i32 [[REASS_ADD]], [[X1:%.*]] 215; CHECK-NEXT: ret i32 [[REASS_MUL]] 216; 217 %A = sub i32 0, %X1 218 %B = mul i32 %A, %X2 ; -X1*X2 219 %C = mul i32 %X1, %X3 ; X1*X3 220 %D = add i32 %B, %C ; -X1*X2 + X1*X3 -> X1*(X3-X2) 221 ret i32 %D 222} 223 224; PR5359 225 226define i32 @test14(i32 %X1, i32 %X2) { 227; CHECK-LABEL: @test14( 228; CHECK-NEXT: [[REASS_ADD:%.*]] = sub i32 [[X1:%.*]], [[X2:%.*]] 229; CHECK-NEXT: [[REASS_MUL:%.*]] = mul i32 [[REASS_ADD]], 47 230; CHECK-NEXT: ret i32 [[REASS_MUL]] 231; 232 %B = mul i32 %X1, 47 ; X1*47 233 %C = mul i32 %X2, -47 ; X2*-47 234 %D = add i32 %B, %C ; X1*47 + X2*-47 -> 47*(X1-X2) 235 ret i32 %D 236} 237 238; Do not reassociate expressions of type i1 239 240define i32 @test15(i32 %X1, i32 %X2, i32 %X3) { 241; CHECK-LABEL: @test15( 242; CHECK-NEXT: [[A:%.*]] = icmp ne i32 [[X1:%.*]], 0 243; CHECK-NEXT: [[B:%.*]] = icmp slt i32 [[X2:%.*]], [[X3:%.*]] 244; CHECK-NEXT: [[C:%.*]] = and i1 [[A]], [[B]] 245; CHECK-NEXT: [[D:%.*]] = select i1 [[C]], i32 [[X1]], i32 0 246; CHECK-NEXT: ret i32 [[D]] 247; 248 %A = icmp ne i32 %X1, 0 249 %B = icmp slt i32 %X2, %X3 250 %C = and i1 %A, %B 251 %D = select i1 %C, i32 %X1, i32 0 252 ret i32 %D 253} 254 255; PR30256 - previously this asserted. 256 257define i64 @test16(i1 %cmp, i64 %a, i64 %b) { 258; CHECK-LABEL: @test16( 259; CHECK-NEXT: entry: 260; CHECK-NEXT: br i1 [[CMP:%.*]], label [[IF_THEN:%.*]], label [[IF_END:%.*]] 261; CHECK: if.then: 262; CHECK-NEXT: [[FACTOR:%.*]] = mul i64 [[A:%.*]], -4 263; CHECK-NEXT: [[ADD2:%.*]] = add i64 [[FACTOR]], [[B:%.*]] 264; CHECK-NEXT: ret i64 [[ADD2]] 265; CHECK: if.end: 266; CHECK-NEXT: ret i64 0 267; 268entry: 269 %shl = shl i64 %a, 1 270 %shl.neg = sub i64 0, %shl 271 br i1 %cmp, label %if.then, label %if.end 272 273if.then: 274 %add1 = add i64 %shl.neg, %shl.neg 275 %add2 = add i64 %add1, %b 276 ret i64 %add2 277 278if.end: 279 ret i64 0 280} 281 282define i32 @test17(i32 %X1, i32 %X2, i32 %X3, i32 %X4) { 283; CHECK-LABEL: @test17( 284; CHECK-NEXT: [[A:%.*]] = mul i32 [[X4:%.*]], [[X3:%.*]] 285; CHECK-NEXT: [[C:%.*]] = mul i32 [[A]], [[X1:%.*]] 286; CHECK-NEXT: [[D:%.*]] = mul i32 [[A]], [[X2:%.*]] 287; CHECK-NEXT: [[E:%.*]] = xor i32 [[C]], [[D]] 288; CHECK-NEXT: ret i32 [[E]] 289; 290 %A = mul i32 %X3, %X1 291 %B = mul i32 %X3, %X2 292 %C = mul i32 %A, %X4 293 %D = mul i32 %B, %X4 294 %E = xor i32 %C, %D 295 ret i32 %E 296} 297 298