267 lines · plain
1; Test if several consecutive loads/stores can be clustered(fused) by scheduler. The2; scheduler will print "Cluster ld/st SU(x) - SU(y)" if SU(x) and SU(y) are fused.3 4; REQUIRES: asserts5; RUN: llc < %s -mtriple=powerpc64le-unknown-linux-gnu -mcpu=pwr10 \6; RUN: -mattr=-paired-vector-memops,-pcrelative-memops -verify-misched \7; RUN: -debug-only=machine-scheduler 2>&1 | FileCheck %s8 9define i64 @store_i64(ptr nocapture %P, i64 %v) {10entry:11; CHECK: ********** MI Scheduling **********12; CHECK-LABEL: store_i64:%bb.013; CHECK: Cluster ld/st SU([[SU3:[0-9]+]]) - SU([[SU4:[0-9]+]])14; CHECK: Cluster ld/st SU([[SU2:[0-9]+]]) - SU([[SU5:[0-9]+]])15; CHECK: SU([[SU2]]): STD %[[REG:[0-9]+]]:g8rc, 2416; CHECK: SU([[SU3]]): STD %[[REG]]:g8rc, 1617; CHECK: SU([[SU4]]): STD %[[REG]]:g8rc, 818; CHECK: SU([[SU5]]): STD %[[REG]]:g8rc, 3219; CHECK: ********** MI Scheduling **********20; CHECK-LABEL: store_i64:%bb.021; CHECK: Cluster ld/st SU([[SU0:[0-9]+]]) - SU([[SU1:[0-9]+]])22; CHECK: Cluster ld/st SU([[SU2:[0-9]+]]) - SU([[SU3:[0-9]+]])23; CHECK: SU([[SU0]]): STD renamable $x[[REG:[0-9]+]], 1624; CHECK: SU([[SU1]]): STD renamable $x[[REG]], 825; CHECK: SU([[SU2]]): STD renamable $x[[REG]], 2426; CHECK: SU([[SU3]]): STD renamable $x[[REG]], 3227 %arrayidx = getelementptr inbounds i64, ptr %P, i64 328 store i64 %v, ptr %arrayidx29 %arrayidx1 = getelementptr inbounds i64, ptr %P, i64 230 store i64 %v, ptr %arrayidx131 %arrayidx2 = getelementptr inbounds i64, ptr %P, i64 132 store i64 %v, ptr %arrayidx233 %arrayidx3 = getelementptr inbounds i64, ptr %P, i64 434 store i64 %v, ptr %arrayidx335 ret i64 %v36}37 38define i32 @store_i32(ptr nocapture %P, i32 %v) {39entry:40; CHECK: ********** MI Scheduling **********41; CHECK-LABEL: store_i32:%bb.042; CHECK: Cluster ld/st SU([[SU3:[0-9]+]]) - SU([[SU4:[0-9]+]])43; CHECK: Cluster ld/st SU([[SU2:[0-9]+]]) - SU([[SU5:[0-9]+]])44; CHECK: SU([[SU2]]): STW %[[REG:[0-9]+]].sub_32:g8rc, 5245; CHECK: SU([[SU3]]): STW %[[REG]].sub_32:g8rc, 4846; CHECK: SU([[SU4]]): STW %[[REG]].sub_32:g8rc, 4447; CHECK: SU([[SU5]]): STW %[[REG]].sub_32:g8rc, 5648; CHECK: ********** MI Scheduling **********49; CHECK-LABEL: store_i32:%bb.050; CHECK: Cluster ld/st SU([[SU0:[0-9]+]]) - SU([[SU1:[0-9]+]])51; CHECK: Cluster ld/st SU([[SU2:[0-9]+]]) - SU([[SU3:[0-9]+]])52; CHECK: SU([[SU0]]): STW renamable $r[[REG:[0-9]+]], 4853; CHECK: SU([[SU1]]): STW renamable $r[[REG]], 4454; CHECK: SU([[SU2]]): STW renamable $r[[REG]], 5255; CHECK: SU([[SU3]]): STW renamable $r[[REG]], 5656 %arrayidx = getelementptr inbounds i32, ptr %P, i32 1357 store i32 %v, ptr %arrayidx58 %arrayidx1 = getelementptr inbounds i32, ptr %P, i32 1259 store i32 %v, ptr %arrayidx160 %arrayidx2 = getelementptr inbounds i32, ptr %P, i32 1161 store i32 %v, ptr %arrayidx262 %arrayidx3 = getelementptr inbounds i32, ptr %P, i32 1463 store i32 %v, ptr %arrayidx364 ret i32 %v65}66 67define void @store_i64_neg(ptr nocapture %P, i64 %v) #0 {68entry:69; CHECK: ********** MI Scheduling **********70; CHECK-LABEL: store_i64_neg:%bb.071; CHECK: Cluster ld/st SU([[SU2:[0-9]+]]) - SU([[SU5:[0-9]+]])72; CHECK: Cluster ld/st SU([[SU3:[0-9]+]]) - SU([[SU4:[0-9]+]])73; CHECK: SU([[SU2]]): STD %[[REG:[0-9]+]]:g8rc, -2474; CHECK: SU([[SU3]]): STD %[[REG]]:g8rc, -875; CHECK: SU([[SU4]]): STD %[[REG]]:g8rc, -1676; CHECK: SU([[SU5]]): STD %[[REG]]:g8rc, -3277; CHECK: ********** MI Scheduling **********78; CHECK-LABEL: store_i64_neg:%bb.079; CHECK: Cluster ld/st SU([[SU2:[0-9]+]]) - SU([[SU3:[0-9]+]])80; CHECK: Cluster ld/st SU([[SU0:[0-9]+]]) - SU([[SU1:[0-9]+]])81; CHECK: SU([[SU0]]): STD renamable $x[[REG:[0-9]+]], -882; CHECK: SU([[SU1]]): STD renamable $x[[REG]], -1683; CHECK: SU([[SU2]]): STD renamable $x[[REG]], -2484; CHECK: SU([[SU3]]): STD renamable $x[[REG]], -3285 %arrayidx = getelementptr inbounds i64, ptr %P, i64 -386 store i64 %v, ptr %arrayidx87 %arrayidx1 = getelementptr inbounds i64, ptr %P, i64 -188 store i64 %v, ptr %arrayidx189 %arrayidx2 = getelementptr inbounds i64, ptr %P, i64 -290 store i64 %v, ptr %arrayidx291 %arrayidx3 = getelementptr inbounds i64, ptr %P, i64 -492 store i64 %v, ptr %arrayidx393 ret void94}95 96define void @store_i32_neg(ptr nocapture %P, i32 %v) #0 {97entry:98; CHECK: ********** MI Scheduling **********99; CHECK-LABEL: store_i32_neg:%bb.0100; CHECK: Cluster ld/st SU([[SU2:[0-9]+]]) - SU([[SU5:[0-9]+]])101; CHECK: Cluster ld/st SU([[SU3:[0-9]+]]) - SU([[SU4:[0-9]+]])102; CHECK: SU([[SU2]]): STW %[[REG:[0-9]+]].sub_32:g8rc, -12103; CHECK: SU([[SU3]]): STW %[[REG]].sub_32:g8rc, -4104; CHECK: SU([[SU4]]): STW %[[REG]].sub_32:g8rc, -8105; CHECK: SU([[SU5]]): STW %[[REG]].sub_32:g8rc, -16106; CHECK: ********** MI Scheduling **********107; CHECK-LABEL: store_i32_neg:%bb.0108; CHECK: Cluster ld/st SU([[SU2:[0-9]+]]) - SU([[SU3:[0-9]+]])109; CHECK: Cluster ld/st SU([[SU0:[0-9]+]]) - SU([[SU1:[0-9]+]])110; CHECK:SU([[SU0]]): STW renamable $r[[REG:[0-9]+]], -4111; CHECK:SU([[SU1]]): STW renamable $r[[REG]], -8112; CHECK:SU([[SU2]]): STW renamable $r[[REG]], -12113; CHECK:SU([[SU3]]): STW renamable $r[[REG]], -16114 %arrayidx = getelementptr inbounds i32, ptr %P, i32 -3115 store i32 %v, ptr %arrayidx116 %arrayidx1 = getelementptr inbounds i32, ptr %P, i32 -1117 store i32 %v, ptr %arrayidx1118 %arrayidx2 = getelementptr inbounds i32, ptr %P, i32 -2119 store i32 %v, ptr %arrayidx2120 %arrayidx3 = getelementptr inbounds i32, ptr %P, i32 -4121 store i32 %v, ptr %arrayidx3122 ret void123}124 125define void @store_double(ptr nocapture %P, double %v) {126entry:127; CHECK: ********** MI Scheduling **********128; CHECK-LABEL: store_double:%bb.0129; CHECK: Cluster ld/st SU([[SU3:[0-9]+]]) - SU([[SU4:[0-9]+]])130; CHECK: Cluster ld/st SU([[SU2:[0-9]+]]) - SU([[SU5:[0-9]+]])131; CHECK: SU([[SU2]]): DFSTOREf64 %[[REG:[0-9]+]]:vsfrc, 24132; CHECK: SU([[SU3]]): DFSTOREf64 %[[REG]]:vsfrc, 8133; CHECK: SU([[SU4]]): DFSTOREf64 %[[REG]]:vsfrc, 16134; CHECK: SU([[SU5]]): DFSTOREf64 %[[REG]]:vsfrc, 32135; CHECK: ********** MI Scheduling **********136; CHECK-LABEL: store_double:%bb.0137; CHECK: Cluster ld/st SU([[SU0:[0-9]+]]) - SU([[SU1:[0-9]+]])138; CHECK: Cluster ld/st SU([[SU2:[0-9]+]]) - SU([[SU3:[0-9]+]])139; CHECK: SU([[SU0]]): STFD renamable $f[[REG:[0-9]+]], 8140; CHECK: SU([[SU1]]): STFD renamable $f[[REG]], 16141; CHECK: SU([[SU2]]): STFD renamable $f[[REG]], 24142; CHECK: SU([[SU3]]): STFD renamable $f[[REG]], 32143 %arrayidx = getelementptr inbounds double, ptr %P, i64 3144 store double %v, ptr %arrayidx145 %arrayidx1 = getelementptr inbounds double, ptr %P, i64 1146 store double %v, ptr %arrayidx1147 %arrayidx2 = getelementptr inbounds double, ptr %P, i64 2148 store double %v, ptr %arrayidx2149 %arrayidx3 = getelementptr inbounds double, ptr %P, i64 4150 store double %v, ptr %arrayidx3151 ret void152}153 154define void @store_float(ptr nocapture %P, float %v) {155entry:156; CHECK: ********** MI Scheduling **********157; CHECK-LABEL: store_float:%bb.0158; CHECK-NOT: Cluster ld/st159; CHECK-NOT: Cluster ld/st160; CHECK: SU([[SU2]]): DFSTOREf32 %[[REG:[0-9]+]]:vssrc, 12161; CHECK: SU([[SU3]]): DFSTOREf32 %[[REG]]:vssrc, 4162; CHECK: SU([[SU4]]): DFSTOREf32 %[[REG]]:vssrc, 8163; CHECK: SU([[SU5]]): DFSTOREf32 %[[REG]]:vssrc, 16164; CHECK: ********** MI Scheduling **********165; CHECK-LABEL: store_float:%bb.0166; CHECK-NOT: Cluster ld/st167; CHECK-NOT: Cluster ld/st168; CHECK: SU([[SU0]]): STFS renamable $f[[REG:[0-9]+]], 12169; CHECK: SU([[SU1]]): STFS renamable $f[[REG]], 4170; CHECK: SU([[SU2]]): STFS renamable $f[[REG]], 8171; CHECK: SU([[SU3]]): STFS renamable $f[[REG]], 16172 %arrayidx = getelementptr inbounds float, ptr %P, i64 3173 store float %v, ptr %arrayidx174 %arrayidx1 = getelementptr inbounds float, ptr %P, i64 1175 store float %v, ptr %arrayidx1176 %arrayidx2 = getelementptr inbounds float, ptr %P, i64 2177 store float %v, ptr %arrayidx2178 %arrayidx3 = getelementptr inbounds float, ptr %P, i64 4179 store float %v, ptr %arrayidx3180 ret void181}182 183; Cannot fuse the store/load if there is volatile in between184define i64 @store_volatile(ptr nocapture %P, i64 %v) {185entry:186; CHECK: ********** MI Scheduling **********187; CHECK-LABEL: store_volatile:%bb.0188; CHECK-NOT: Cluster ld/st189; CHECK: SU([[SU2]]): STD %[[REG:[0-9]+]]:g8rc, 24190; CHECK: SU([[SU3]]): STD %[[REG]]:g8rc, 16191; CHECK: SU([[SU4]]): STD %[[REG]]:g8rc, 8192; CHECK: SU([[SU5]]): STD %[[REG]]:g8rc, 32193; CHECK: ********** MI Scheduling **********194; CHECK-LABEL: store_volatile:%bb.0195; CHECK-NOT: Cluster ld/st196; CHECK: SU([[SU0]]): STD renamable $x[[REG:[0-9]+]], 24197; CHECK: SU([[SU1]]): STD renamable $x[[REG]], 16198; CHECK: SU([[SU2]]): STD renamable $x[[REG]], 8199; CHECK: SU([[SU3]]): STD renamable $x[[REG]], 32200 %arrayidx = getelementptr inbounds i64, ptr %P, i64 3201 store volatile i64 %v, ptr %arrayidx202 %arrayidx1 = getelementptr inbounds i64, ptr %P, i64 2203 store volatile i64 %v, ptr %arrayidx1204 %arrayidx2 = getelementptr inbounds i64, ptr %P, i64 1205 store volatile i64 %v, ptr %arrayidx2206 %arrayidx3 = getelementptr inbounds i64, ptr %P, i64 4207 store volatile i64 %v, ptr %arrayidx3208 ret i64 %v209}210 211@p = common local_unnamed_addr global [100 x i32] zeroinitializer, align 4212 213define void @store_i32_stw_stw8(i32 signext %m, i32 signext %n) {214entry:215; CHECK: ********** MI Scheduling **********216; CHECK-LABEL: store_i32_stw_stw8:%bb.0217; CHECK: Cluster ld/st SU([[SU5:[0-9]+]]) - SU([[SU8:[0-9]+]])218; CHECK: SU([[SU5]]): STW8 %{{[0-9]+}}:g8rc, 24219; CHECK: SU([[SU8]]): STW %{{[0-9]+}}:gprc, 20220; CHECK: ********** MI Scheduling **********221; CHECK-LABEL: store_i32_stw_stw8:%bb.0222; CHECK: Cluster ld/st SU([[SU5:[0-9]+]]) - SU([[SU6:[0-9]+]])223; CHECK: SU([[SU5]]): STW8 renamable $x{{[0-9]+}}, 24224; CHECK: SU([[SU6]]): STW renamable $r{{[0-9]+}}, 20225 store i32 9, ptr getelementptr inbounds ([100 x i32], ptr @p, i64 0, i64 6), align 4226 store i32 %n, ptr getelementptr inbounds ([100 x i32], ptr @p, i64 0, i64 7), align 4227 %add = add nsw i32 %n, %m228 store i32 %add, ptr getelementptr inbounds ([100 x i32], ptr @p, i64 0, i64 5), align 4229 ret void230}231 232define void @store_i32_stw8(i32 signext %m, i32 signext %n) {233entry:234; CHECK: ********** MI Scheduling **********235; CHECK-LABEL: store_i32_stw8:%bb.0236; CHECK: Cluster ld/st SU([[SU4:[0-9]+]]) - SU([[SU5:[0-9]+]])237; CHECK: SU([[SU4]]): STW8 %{{[0-9]+}}:g8rc, 24238; CHECK: SU([[SU5]]): STW8 %{{[0-9]+}}:g8rc, 28239; CHECK: ********** MI Scheduling **********240; CHECK-LABEL: store_i32_stw8:%bb.0241; CHECK: Cluster ld/st SU([[SU3:[0-9]+]]) - SU([[SU4:[0-9]+]])242; CHECK: SU([[SU3]]): STW8 renamable $x{{[0-9]+}}, 24243; CHECK: SU([[SU4]]): STW8 renamable $x{{[0-9]+}}, 28244 store i32 9, ptr getelementptr inbounds ([100 x i32], ptr @p, i64 0, i64 6), align 4245 store i32 %n, ptr getelementptr inbounds ([100 x i32], ptr @p, i64 0, i64 7), align 4246 ret void247}248 249declare void @bar(ptr)250 251define void @store_frame_index(i32 %a, i32 %b) {252entry:253; CHECK: ********** MI Scheduling **********254; CHECK-LABEL: store_frame_index:%bb.0255; CHECK: Cluster ld/st SU([[SU2:[0-9]+]]) - SU([[SU3:[0-9]+]])256; CHECK: SU([[SU2]]): STD %{{[0-9]+}}:g8rc, 0, %stack.0.buf257; CHECK: SU([[SU3]]): STD %{{[0-9]+}}:g8rc, 8, %stack.0.buf258 %buf = alloca [8 x i64], align 8259 %conv = zext i32 %a to i64260 store i64 %conv, ptr %buf, align 8261 %conv1 = zext i32 %b to i64262 %arrayidx2 = getelementptr inbounds [8 x i64], ptr %buf, i64 0, i64 1263 store i64 %conv1, ptr %arrayidx2, align 8264 call void @bar(ptr nonnull %buf)265 ret void266}267