1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py 2; RUN: opt -S -passes=slp-vectorizer -mtriple=x86_64-unknown-linux-gnu < %s | FileCheck %s 3 4define ptr @test() { 5; CHECK-LABEL: @test( 6; CHECK-NEXT: entry: 7; CHECK-NEXT: [[GREEN_I:%.*]] = getelementptr inbounds float, ptr null, i32 6 8; CHECK-NEXT: [[TMP0:%.*]] = load <2 x float>, ptr [[GREEN_I]], align 4 9; CHECK-NEXT: [[TMP1:%.*]] = fpext <2 x float> [[TMP0]] to <2 x double> 10; CHECK-NEXT: br label [[BODY:%.*]] 11; CHECK: body: 12; CHECK-NEXT: [[TMP2:%.*]] = phi <2 x double> [ [[TMP5:%.*]], [[BODY]] ], [ [[TMP1]], [[ENTRY:%.*]] ] 13; CHECK-NEXT: [[TMP3:%.*]] = load <2 x i16>, ptr null, align 2 14; CHECK-NEXT: [[TMP4:%.*]] = uitofp <2 x i16> [[TMP3]] to <2 x double> 15; CHECK-NEXT: [[SHUFFLE:%.*]] = shufflevector <2 x double> [[TMP4]], <2 x double> poison, <2 x i32> <i32 1, i32 0> 16; CHECK-NEXT: [[TMP5]] = call <2 x double> @llvm.fmuladd.v2f64(<2 x double> zeroinitializer, <2 x double> [[SHUFFLE]], <2 x double> [[TMP2]]) 17; CHECK-NEXT: br label [[BODY]] 18; 19entry: 20 %green.i = getelementptr inbounds float, ptr null, i32 6 21 %blue.i = getelementptr inbounds float, ptr null, i32 7 22 %0 = load float, ptr %green.i, align 4 23 %conv197 = fpext float %0 to double 24 %1 = load float, ptr %blue.i, align 8 25 %conv199 = fpext float %1 to double 26 br label %body 27 28body: 29 %phi1 = phi double [ %3, %body ], [ %conv197, %entry ] 30 %phi2 = phi double [ %5, %body ], [ %conv199, %entry ] 31 %green = getelementptr inbounds i16, ptr null, i32 1 32 %2 = load i16, ptr %green, align 2 33 %conv1 = uitofp i16 %2 to double 34 %3 = call double @llvm.fmuladd.f64(double 0.000000e+00, double %conv1, double %phi1) 35 %4 = load i16, ptr null, align 2 36 %conv2 = uitofp i16 %4 to double 37 %5 = call double @llvm.fmuladd.f64(double 0.000000e+00, double %conv2, double %phi2) 38 br label %body 39} 40 41declare double @llvm.fmuladd.f64(double, double, double) 42 43define void @test1(ptr %agg.result, ptr %this) { 44; CHECK-LABEL: @test1( 45; CHECK-NEXT: entry: 46; CHECK-NEXT: br i1 false, label [[RETURN:%.*]], label [[LOR_LHS_FALSE:%.*]] 47; CHECK: lor.lhs.false: 48; CHECK-NEXT: br i1 false, label [[RETURN]], label [[IF_END:%.*]] 49; CHECK: if.end: 50; CHECK-NEXT: [[B_I:%.*]] = getelementptr inbounds float, ptr [[THIS:%.*]], i32 1 51; CHECK-NEXT: [[TMP0:%.*]] = load <2 x float>, ptr [[B_I]], align 4 52; CHECK-NEXT: [[TMP1:%.*]] = fadd <2 x float> [[TMP0]], zeroinitializer 53; CHECK-NEXT: br label [[RETURN]] 54; CHECK: return: 55; CHECK-NEXT: [[TMP2:%.*]] = phi <2 x float> [ [[TMP1]], [[IF_END]] ], [ <float 1.000000e+00, float 0.000000e+00>, [[LOR_LHS_FALSE]] ], [ <float 1.000000e+00, float 0.000000e+00>, [[ENTRY:%.*]] ] 56; CHECK-NEXT: [[C_I_I_I:%.*]] = getelementptr inbounds float, ptr [[AGG_RESULT:%.*]], i32 2 57; CHECK-NEXT: [[SHUFFLE:%.*]] = shufflevector <2 x float> [[TMP2]], <2 x float> poison, <2 x i32> <i32 1, i32 0> 58; CHECK-NEXT: store <2 x float> [[SHUFFLE]], ptr [[C_I_I_I]], align 4 59; CHECK-NEXT: ret void 60; 61entry: 62 br i1 false, label %return, label %lor.lhs.false 63 64lor.lhs.false: 65 br i1 false, label %return, label %if.end 66 67if.end: 68 %c.i = getelementptr inbounds float, ptr %this, i32 2 69 %0 = load float, ptr %c.i, align 4 70 %add.i = fadd float %0, 0.000000e+00 71 %b.i = getelementptr inbounds float, ptr %this, i32 1 72 %1 = load float, ptr %b.i, align 4 73 %add2.i = fadd float %1, 0.000000e+00 74 br label %return 75 76return: 77 %add.i.sink = phi float [ %add.i, %if.end ], [ 0.000000e+00, %lor.lhs.false ], [ 0.000000e+00, %entry ] 78 %add2.i.sink = phi float [ %add2.i, %if.end ], [ 1.000000e+00, %lor.lhs.false ], [ 1.000000e+00, %entry ] 79 %c.i.i.i = getelementptr inbounds float, ptr %agg.result, i32 2 80 store float %add.i.sink, ptr %c.i.i.i, align 4 81 %d.i.i.i = getelementptr inbounds float, ptr %agg.result, i32 3 82 store float %add2.i.sink, ptr %d.i.i.i, align 4 83 ret void 84} 85 86; Here PHIs have mutual uses of each other. Reordering one requires reordering the other. 87define void @test2(ptr %p1, ptr %p2) { 88; CHECK-LABEL: @test2( 89; CHECK-NEXT: entry: 90; CHECK-NEXT: [[A1:%.*]] = getelementptr inbounds ptr, ptr [[P1:%.*]], i32 0 91; CHECK-NEXT: [[B1:%.*]] = getelementptr inbounds ptr, ptr [[P1]], i32 4 92; CHECK-NEXT: [[TMP0:%.*]] = load <2 x double>, ptr [[A1]], align 8 93; CHECK-NEXT: [[TMP1:%.*]] = load <2 x double>, ptr [[B1]], align 8 94; CHECK-NEXT: [[TMP2:%.*]] = fmul fast <2 x double> <double 1.000000e+01, double 1.000000e-01>, [[TMP0]] 95; CHECK-NEXT: [[TMP3:%.*]] = fmul fast <2 x double> <double 1.100000e+01, double 1.100000e+00>, [[TMP1]] 96; CHECK-NEXT: [[TMP4:%.*]] = fsub fast <2 x double> <double 1.000000e+01, double 1.000000e-01>, [[TMP3]] 97; CHECK-NEXT: [[TMP5:%.*]] = fmul fast <2 x double> [[TMP4]], <double 2.000000e+00, double 2.100000e+00> 98; CHECK-NEXT: [[TMP6:%.*]] = fadd fast <2 x double> [[TMP2]], <double 1.000000e+01, double 1.000000e-01> 99; CHECK-NEXT: [[TMP7:%.*]] = fadd fast <2 x double> [[TMP6]], [[TMP5]] 100; CHECK-NEXT: [[TMP8:%.*]] = fmul fast <2 x double> [[TMP7]], <double 3.000000e+00, double 3.100000e+00> 101; CHECK-NEXT: br label [[BB1:%.*]] 102; CHECK: bb1: 103; CHECK-NEXT: [[TMP9:%.*]] = fadd fast <2 x double> <double 4.000000e+00, double 4.100000e+00>, [[TMP8]] 104; CHECK-NEXT: [[TMP10:%.*]] = fadd fast <2 x double> [[TMP9]], <double 2.000000e+00, double 2.100000e+00> 105; CHECK-NEXT: [[TMP11:%.*]] = fadd fast <2 x double> [[TMP10]], <double 3.000000e+00, double 3.100000e+00> 106; CHECK-NEXT: br label [[BB2:%.*]] 107; CHECK: bb2: 108; CHECK-NEXT: [[TMP12:%.*]] = phi <2 x double> [ [[TMP11]], [[BB1]] ], [ [[TMP16:%.*]], [[BB6:%.*]] ] 109; CHECK-NEXT: [[TMP13:%.*]] = shufflevector <2 x double> [[TMP12]], <2 x double> poison, <2 x i32> <i32 1, i32 0> 110; CHECK-NEXT: [[X0:%.*]] = getelementptr inbounds double, ptr [[P2:%.*]], i32 0 111; CHECK-NEXT: [[TMP14:%.*]] = load <2 x double>, ptr [[X0]], align 8 112; CHECK-NEXT: br i1 poison, label [[BB3:%.*]], label [[BB6]] 113; CHECK: bb3: 114; CHECK-NEXT: br i1 poison, label [[BB5:%.*]], label [[BB4:%.*]] 115; CHECK: bb4: 116; CHECK-NEXT: br label [[BB6]] 117; CHECK: bb5: 118; CHECK-NEXT: br label [[BB6]] 119; CHECK: bb6: 120; CHECK-NEXT: [[TMP15:%.*]] = phi <2 x double> [ [[TMP13]], [[BB2]] ], [ [[TMP14]], [[BB4]] ], [ [[TMP14]], [[BB5]] ] 121; CHECK-NEXT: [[TMP16]] = shufflevector <2 x double> [[TMP15]], <2 x double> poison, <2 x i32> <i32 1, i32 0> 122; CHECK-NEXT: br label [[BB2]] 123; 124entry: 125 %a1 = getelementptr inbounds ptr, ptr %p1, i32 0 126 %a2 = getelementptr inbounds ptr, ptr %p1, i32 1 127 %b2 = getelementptr inbounds ptr, ptr %p1, i32 5 128 %lda1 = load double, ptr %a1, align 8 129 %lda2 = load double, ptr %a2, align 8 130 %b1 = getelementptr inbounds ptr, ptr %p1, i32 4 131 %ldb1 = load double, ptr %b1, align 8 132 %ldb2 = load double, ptr %b2, align 8 133 %mul0.1 = fmul fast double 0.1, %lda2 134 %mul1.1 = fmul fast double 1.1, %ldb2 135 %sub0.1 = fsub fast double 0.1, %mul1.1 136 %mul2.1 = fmul fast double %sub0.1, 2.1 137 %add0.1 = fadd fast double %mul0.1, 0.1 138 %add1.1 = fadd fast double %add0.1, %mul2.1 139 %mul3.1 = fmul fast double %add1.1, 3.1 140 %mul0.0 = fmul fast double 10.0, %lda1 141 %mul1.0 = fmul fast double 11.0, %ldb1 142 %sub0.0 = fsub fast double 10.0, %mul1.0 143 %mul2.0 = fmul fast double %sub0.0, 2.0 144 %add0.0 = fadd fast double %mul0.0, 10.0 145 %add1.0 = fadd fast double %add0.0, %mul2.0 146 %mul3.0 = fmul fast double 3.0, %add1.0 147 br label %bb1 148 149bb1: 150 %add4.1 = fadd fast double 4.1, %mul3.1 151 %add2.1 = fadd fast double %add4.1, 2.1 152 %add3.1 = fadd fast double %add2.1, 3.1 153 %add4.0 = fadd fast double 4.0, %mul3.0 154 %add2.0 = fadd fast double %add4.0, 2.0 155 %add3.0 = fadd fast double %add2.0, 3.0 156 br label %bb2 157 158bb2: ; preds = %bb6, %bb1 159 %phi0.0 = phi double [ %add3.1, %bb1 ], [ %phi1.0, %bb6 ] 160 %phi0.1 = phi double [ %add3.0, %bb1 ], [ %phi1.1, %bb6 ] 161 %x0 = getelementptr inbounds double, ptr %p2, i32 0 162 %i0 = load double, ptr %x0, align 8 163 %x1 = getelementptr inbounds double, ptr %p2, i32 1 164 %i1 = load double, ptr %x1, align 8 165 br i1 poison, label %bb3, label %bb6 166 167bb3: ; preds = %bb2 168 br i1 poison, label %bb5, label %bb4 169 170bb4: ; preds = %bb3 171 br label %bb6 172 173bb5: ; preds = %bb3 174 br label %bb6 175 176bb6: ; preds = %bb5, %bb4, %bb3 177 %phi1.0 = phi double [ %phi0.0, %bb2 ], [ %i0, %bb4 ], [ %i0, %bb5 ] 178 %phi1.1 = phi double [ %phi0.1, %bb2 ], [ %i1, %bb4 ], [ %i1, %bb5 ] 179 br label %bb2 180} 181