481 lines · plain
1# NOTE: Assertions have been autogenerated by utils/update_mir_test_checks.py2# RUN: llc -mtriple=aarch64-unknown-unknown -run-pass=instruction-select -verify-machineinstrs %s -o - | FileCheck %s3...4---5name: shl_gep_sext_ldrwrow6alignment: 47legalized: true8regBankSelected: true9tracksRegLiveness: true10frameInfo:11 maxAlignment: 112machineFunctionInfo: {}13body: |14 bb.0:15 liveins: $w1, $x016 17 ; We should be able to fold a shift + extend into the pattern.18 ; In this case, we should get a roW load with two 1s, representing a shift19 ; plus sign extend.20 21 ; CHECK-LABEL: name: shl_gep_sext_ldrwrow22 ; CHECK: liveins: $w1, $x023 ; CHECK-NEXT: {{ $}}24 ; CHECK-NEXT: %base:gpr64sp = COPY $x025 ; CHECK-NEXT: %foo:gpr32 = COPY $w126 ; CHECK-NEXT: %load:gpr32 = LDRWroW %base, %foo, 1, 1 :: (load (s32))27 ; CHECK-NEXT: $w0 = COPY %load28 ; CHECK-NEXT: RET_ReallyLR implicit $w029 %base:gpr(p0) = COPY $x030 %foo:gpr(s32) = COPY $w131 %ext:gpr(s64) = G_SEXT %foo(s32)32 %c:gpr(s64) = G_CONSTANT i64 233 %offset:gpr(s64) = G_SHL %ext, %c34 %ptr:gpr(p0) = G_PTR_ADD %base, %offset(s64)35 %load:gpr(s32) = G_LOAD %ptr(p0) :: (load (s32))36 $w0 = COPY %load(s32)37 RET_ReallyLR implicit $w038...39---40name: shl_gep_zext_ldrwrow41alignment: 442legalized: true43regBankSelected: true44tracksRegLiveness: true45frameInfo:46 maxAlignment: 147machineFunctionInfo: {}48body: |49 bb.0:50 liveins: $w1, $x051 52 ; We should be able to fold a shift + extend into the pattern.53 ; In this case, we should get a roW load with a 0 representing a zero-extend54 ; and a 1 representing a shift.55 56 ; CHECK-LABEL: name: shl_gep_zext_ldrwrow57 ; CHECK: liveins: $w1, $x058 ; CHECK-NEXT: {{ $}}59 ; CHECK-NEXT: %base:gpr64sp = COPY $x060 ; CHECK-NEXT: %foo:gpr32 = COPY $w161 ; CHECK-NEXT: %load:gpr32 = LDRWroW %base, %foo, 0, 1 :: (load (s32))62 ; CHECK-NEXT: $w0 = COPY %load63 ; CHECK-NEXT: RET_ReallyLR implicit $w064 %base:gpr(p0) = COPY $x065 %foo:gpr(s32) = COPY $w166 %ext:gpr(s64) = G_ZEXT %foo(s32)67 %c:gpr(s64) = G_CONSTANT i64 268 %offset:gpr(s64) = G_SHL %ext, %c69 %ptr:gpr(p0) = G_PTR_ADD %base, %offset(s64)70 %load:gpr(s32) = G_LOAD %ptr(p0) :: (load (s32))71 $w0 = COPY %load(s32)72 RET_ReallyLR implicit $w073...74---75name: shl_gep_anyext_ldrwrow76alignment: 477legalized: true78regBankSelected: true79tracksRegLiveness: true80frameInfo:81 maxAlignment: 182machineFunctionInfo: {}83body: |84 bb.0:85 liveins: $w1, $x086 87 ; We should be able to fold a shift + extend into the pattern.88 ; In this case, we should get a roW load with a 0 representing a zero-extend89 ; and a 1 representing a shift.90 91 ; CHECK-LABEL: name: shl_gep_anyext_ldrwrow92 ; CHECK: liveins: $w1, $x093 ; CHECK-NEXT: {{ $}}94 ; CHECK-NEXT: %base:gpr64sp = COPY $x095 ; CHECK-NEXT: %foo:gpr32 = COPY $w196 ; CHECK-NEXT: %load:gpr32 = LDRWroW %base, %foo, 0, 1 :: (load (s32))97 ; CHECK-NEXT: $w0 = COPY %load98 ; CHECK-NEXT: RET_ReallyLR implicit $w099 %base:gpr(p0) = COPY $x0100 %foo:gpr(s32) = COPY $w1101 %ext:gpr(s64) = G_ANYEXT %foo(s32)102 %c:gpr(s64) = G_CONSTANT i64 2103 %offset:gpr(s64) = G_SHL %ext, %c104 %ptr:gpr(p0) = G_PTR_ADD %base, %offset(s64)105 %load:gpr(s32) = G_LOAD %ptr(p0) :: (load (s32))106 $w0 = COPY %load(s32)107 RET_ReallyLR implicit $w0108...109---110name: mul_gep_sext_ldrwrow111alignment: 4112legalized: true113regBankSelected: true114tracksRegLiveness: true115frameInfo:116 maxAlignment: 1117machineFunctionInfo: {}118body: |119 bb.0:120 121 ; We should be able to do the same with multiplies as with shifts.122 123 liveins: $w1, $x0124 ; CHECK-LABEL: name: mul_gep_sext_ldrwrow125 ; CHECK: liveins: $w1, $x0126 ; CHECK-NEXT: {{ $}}127 ; CHECK-NEXT: %base:gpr64sp = COPY $x0128 ; CHECK-NEXT: %foo:gpr32 = COPY $w1129 ; CHECK-NEXT: %load:gpr32 = LDRWroW %base, %foo, 1, 1 :: (load (s32))130 ; CHECK-NEXT: $w0 = COPY %load131 ; CHECK-NEXT: RET_ReallyLR implicit $w0132 %base:gpr(p0) = COPY $x0133 %foo:gpr(s32) = COPY $w1134 %ext:gpr(s64) = G_SEXT %foo(s32)135 %c:gpr(s64) = G_CONSTANT i64 4136 %offset:gpr(s64) = G_MUL %c, %ext137 %ptr:gpr(p0) = G_PTR_ADD %base, %offset(s64)138 %load:gpr(s32) = G_LOAD %ptr(p0) :: (load (s32))139 $w0 = COPY %load(s32)140 RET_ReallyLR implicit $w0141...142---143name: mul_gep_zext_ldrwrow144alignment: 4145legalized: true146regBankSelected: true147tracksRegLiveness: true148frameInfo:149 maxAlignment: 1150machineFunctionInfo: {}151body: |152 bb.0:153 liveins: $w1, $x0154 155 ; We should be able to do the same with multiplies as with shifts.156 157 ; CHECK-LABEL: name: mul_gep_zext_ldrwrow158 ; CHECK: liveins: $w1, $x0159 ; CHECK-NEXT: {{ $}}160 ; CHECK-NEXT: %base:gpr64sp = COPY $x0161 ; CHECK-NEXT: %foo:gpr32 = COPY $w1162 ; CHECK-NEXT: %load:gpr32 = LDRWroW %base, %foo, 0, 1 :: (load (s32))163 ; CHECK-NEXT: $w0 = COPY %load164 ; CHECK-NEXT: RET_ReallyLR implicit $w0165 %base:gpr(p0) = COPY $x0166 %foo:gpr(s32) = COPY $w1167 %ext:gpr(s64) = G_ZEXT %foo(s32)168 %c:gpr(s64) = G_CONSTANT i64 4169 %offset:gpr(s64) = G_MUL %c, %ext170 %ptr:gpr(p0) = G_PTR_ADD %base, %offset(s64)171 %load:gpr(s32) = G_LOAD %ptr(p0) :: (load (s32))172 $w0 = COPY %load(s32)173 RET_ReallyLR implicit $w0174...175---176name: mul_gep_anyext_ldrwrow177alignment: 4178legalized: true179regBankSelected: true180tracksRegLiveness: true181frameInfo:182 maxAlignment: 1183machineFunctionInfo: {}184body: |185 bb.0:186 liveins: $w1, $x0187 188 ; We should be able to do the same with multiplies as with shifts.189 190 ; CHECK-LABEL: name: mul_gep_anyext_ldrwrow191 ; CHECK: liveins: $w1, $x0192 ; CHECK-NEXT: {{ $}}193 ; CHECK-NEXT: %base:gpr64sp = COPY $x0194 ; CHECK-NEXT: %foo:gpr32 = COPY $w1195 ; CHECK-NEXT: %load:gpr32 = LDRWroW %base, %foo, 0, 1 :: (load (s32))196 ; CHECK-NEXT: $w0 = COPY %load197 ; CHECK-NEXT: RET_ReallyLR implicit $w0198 %base:gpr(p0) = COPY $x0199 %foo:gpr(s32) = COPY $w1200 %ext:gpr(s64) = G_ANYEXT %foo(s32)201 %c:gpr(s64) = G_CONSTANT i64 4202 %offset:gpr(s64) = G_MUL %c, %ext203 %ptr:gpr(p0) = G_PTR_ADD %base, %offset(s64)204 %load:gpr(s32) = G_LOAD %ptr(p0) :: (load (s32))205 $w0 = COPY %load(s32)206 RET_ReallyLR implicit $w0207...208---209name: ldrdrow210alignment: 4211legalized: true212regBankSelected: true213tracksRegLiveness: true214frameInfo:215 maxAlignment: 1216machineFunctionInfo: {}217body: |218 bb.0:219 liveins: $w1, $x0, $d0220 221 ; Verify that we can select LDRDroW.222 223 ; CHECK-LABEL: name: ldrdrow224 ; CHECK: liveins: $w1, $x0, $d0225 ; CHECK-NEXT: {{ $}}226 ; CHECK-NEXT: %base:gpr64sp = COPY $x0227 ; CHECK-NEXT: %foo:gpr32 = COPY $w1228 ; CHECK-NEXT: %load:fpr64 = LDRDroW %base, %foo, 1, 1 :: (load (<2 x s32>))229 ; CHECK-NEXT: $x0 = COPY %load230 ; CHECK-NEXT: RET_ReallyLR implicit $x0231 %base:gpr(p0) = COPY $x0232 %foo:gpr(s32) = COPY $w1233 %ext:gpr(s64) = G_SEXT %foo(s32)234 %c:gpr(s64) = G_CONSTANT i64 8235 %offset:gpr(s64) = G_MUL %c, %ext236 %ptr:gpr(p0) = G_PTR_ADD %base, %offset(s64)237 %load:fpr(<2 x s32>) = G_LOAD %ptr(p0) :: (load (<2 x s32>))238 $x0 = COPY %load(<2 x s32>)239 RET_ReallyLR implicit $x0240...241---242name: ldrxrow243alignment: 4244legalized: true245regBankSelected: true246tracksRegLiveness: true247frameInfo:248 maxAlignment: 1249machineFunctionInfo: {}250body: |251 bb.0:252 liveins: $w1, $x0, $d0253 254 ; Verify that we can select LDRXroW.255 256 ; CHECK-LABEL: name: ldrxrow257 ; CHECK: liveins: $w1, $x0, $d0258 ; CHECK-NEXT: {{ $}}259 ; CHECK-NEXT: %base:gpr64sp = COPY $x0260 ; CHECK-NEXT: %foo:gpr32 = COPY $w1261 ; CHECK-NEXT: %load:gpr64 = LDRXroW %base, %foo, 1, 1 :: (load (s64))262 ; CHECK-NEXT: $x0 = COPY %load263 ; CHECK-NEXT: RET_ReallyLR implicit $x0264 %base:gpr(p0) = COPY $x0265 %foo:gpr(s32) = COPY $w1266 %ext:gpr(s64) = G_SEXT %foo(s32)267 %c:gpr(s64) = G_CONSTANT i64 8268 %offset:gpr(s64) = G_MUL %c, %ext269 %ptr:gpr(p0) = G_PTR_ADD %base, %offset(s64)270 %load:gpr(s64) = G_LOAD %ptr(p0) :: (load (s64))271 $x0 = COPY %load(s64)272 RET_ReallyLR implicit $x0273...274---275name: ldrbbrow276alignment: 4277legalized: true278regBankSelected: true279tracksRegLiveness: true280frameInfo:281 maxAlignment: 1282machineFunctionInfo: {}283body: |284 bb.1.entry:285 liveins: $x0, $w0, $w1286 287 ; Verify that we can select LDRBBroW. Note that there is no shift here,288 ; but we still fold the extend into the addressing mode.289 290 ; CHECK-LABEL: name: ldrbbrow291 ; CHECK: liveins: $x0, $w0, $w1292 ; CHECK-NEXT: {{ $}}293 ; CHECK-NEXT: %val:gpr32 = COPY $w1294 ; CHECK-NEXT: %base:gpr64sp = COPY $x0295 ; CHECK-NEXT: %load:gpr32 = LDRBBroW %base, %val, 1, 0 :: (load (s8))296 ; CHECK-NEXT: $w0 = COPY %load297 ; CHECK-NEXT: RET_ReallyLR implicit $w0298 %val:gpr(s32) = COPY $w1299 %base:gpr(p0) = COPY $x0300 %ext:gpr(s64) = G_SEXT %val(s32)301 %ptr:gpr(p0) = G_PTR_ADD %base, %ext(s64)302 %load:gpr(s32) = G_LOAD %ptr(p0) :: (load (s8))303 $w0 = COPY %load(s32)304 RET_ReallyLR implicit $w0305...306---307name: ldrhrow308alignment: 4309legalized: true310regBankSelected: true311tracksRegLiveness: true312frameInfo:313 maxAlignment: 1314machineFunctionInfo: {}315body: |316 bb.1.entry:317 liveins: $w1, $x0318 319 ; Verify that we can select ldrhrow.320 321 ; CHECK-LABEL: name: ldrhrow322 ; CHECK: liveins: $w1, $x0323 ; CHECK-NEXT: {{ $}}324 ; CHECK-NEXT: %base:gpr64sp = COPY $x0325 ; CHECK-NEXT: %foo:gpr32 = COPY $w1326 ; CHECK-NEXT: %load:fpr16 = LDRHroW %base, %foo, 1, 1 :: (load (s16))327 ; CHECK-NEXT: $h0 = COPY %load328 ; CHECK-NEXT: RET_ReallyLR implicit $h0329 %base:gpr(p0) = COPY $x0330 %foo:gpr(s32) = COPY $w1331 %ext:gpr(s64) = G_SEXT %foo(s32)332 %c:gpr(s64) = G_CONSTANT i64 2333 %offset:gpr(s64) = G_MUL %c, %ext334 %ptr:gpr(p0) = G_PTR_ADD %base, %offset(s64)335 %load:fpr(s16) = G_LOAD %ptr(p0) :: (load (s16))336 $h0 = COPY %load(s16)337 RET_ReallyLR implicit $h0338...339---340name: bad_and_mask_1341alignment: 4342legalized: true343regBankSelected: true344tracksRegLiveness: true345frameInfo:346 maxAlignment: 1347body: |348 bb.0:349 liveins: $x0350 351 ; We should get a roX load here, not a roW load. We can't use the mask in352 ; this test for an extend.353 354 ; CHECK-LABEL: name: bad_and_mask_1355 ; CHECK: liveins: $x0356 ; CHECK-NEXT: {{ $}}357 ; CHECK-NEXT: %base:gpr64sp = COPY $x0358 ; CHECK-NEXT: %imp:gpr64 = IMPLICIT_DEF359 ; CHECK-NEXT: %and:gpr64common = ANDXri %imp, 4103360 ; CHECK-NEXT: %load:gpr64 = LDRXroX %base, %and, 0, 1 :: (load (s64))361 ; CHECK-NEXT: $x1 = COPY %load362 ; CHECK-NEXT: RET_ReallyLR implicit $x1363 %base:gpr(p0) = COPY $x0364 %imp:gpr(s64) = G_IMPLICIT_DEF365 %bad_mask:gpr(s64) = G_CONSTANT i64 255366 %and:gpr(s64) = G_AND %imp, %bad_mask367 %c:gpr(s64) = G_CONSTANT i64 8368 %mul:gpr(s64) = G_MUL %c, %and369 %ptr:gpr(p0) = G_PTR_ADD %base, %mul(s64)370 %load:gpr(s64) = G_LOAD %ptr(p0) :: (load (s64))371 $x1 = COPY %load(s64)372 RET_ReallyLR implicit $x1373...374---375name: bad_and_mask_2376alignment: 4377legalized: true378regBankSelected: true379tracksRegLiveness: true380frameInfo:381 maxAlignment: 1382body: |383 bb.0:384 liveins: $x0385 386 ; We should get a roX load here, not a roW load. We can't use the mask in387 ; this test for an extend.388 389 ; CHECK-LABEL: name: bad_and_mask_2390 ; CHECK: liveins: $x0391 ; CHECK-NEXT: {{ $}}392 ; CHECK-NEXT: %base:gpr64sp = COPY $x0393 ; CHECK-NEXT: %imp:gpr64 = IMPLICIT_DEF394 ; CHECK-NEXT: %and:gpr64common = ANDXri %imp, 4111395 ; CHECK-NEXT: %load:gpr64 = LDRXroX %base, %and, 0, 1 :: (load (s64))396 ; CHECK-NEXT: $x1 = COPY %load397 ; CHECK-NEXT: RET_ReallyLR implicit $x1398 %base:gpr(p0) = COPY $x0399 %imp:gpr(s64) = G_IMPLICIT_DEF400 %bad_mask:gpr(s64) = G_CONSTANT i64 65535401 %and:gpr(s64) = G_AND %imp, %bad_mask402 %c:gpr(s64) = G_CONSTANT i64 8403 %mul:gpr(s64) = G_MUL %c, %and404 %ptr:gpr(p0) = G_PTR_ADD %base, %mul(s64)405 %load:gpr(s64) = G_LOAD %ptr(p0) :: (load (s64))406 $x1 = COPY %load(s64)407 RET_ReallyLR implicit $x1408...409---410name: and_uxtw411alignment: 4412legalized: true413regBankSelected: true414tracksRegLiveness: true415frameInfo:416 maxAlignment: 1417body: |418 bb.0:419 liveins: $x0420 421 ; The mask used for the AND here is legal for producing a roW load.422 423 ; CHECK-LABEL: name: and_uxtw424 ; CHECK: liveins: $x0425 ; CHECK-NEXT: {{ $}}426 ; CHECK-NEXT: %base:gpr64sp = COPY $x0427 ; CHECK-NEXT: %imp:gpr64 = IMPLICIT_DEF428 ; CHECK-NEXT: [[COPY:%[0-9]+]]:gpr32all = COPY %imp.sub_32429 ; CHECK-NEXT: [[COPY1:%[0-9]+]]:gpr32 = COPY [[COPY]]430 ; CHECK-NEXT: %load:gpr64 = LDRXroW %base, [[COPY1]], 0, 1 :: (load (s64))431 ; CHECK-NEXT: $x1 = COPY %load432 ; CHECK-NEXT: RET_ReallyLR implicit $x1433 %base:gpr(p0) = COPY $x0434 %imp:gpr(s64) = G_IMPLICIT_DEF435 %mask:gpr(s64) = G_CONSTANT i64 4294967295436 %and:gpr(s64) = G_AND %imp, %mask437 %c:gpr(s64) = G_CONSTANT i64 8438 %mul:gpr(s64) = G_MUL %c, %and439 %ptr:gpr(p0) = G_PTR_ADD %base, %mul(s64)440 %load:gpr(s64) = G_LOAD %ptr(p0) :: (load (s64))441 $x1 = COPY %load(s64)442 RET_ReallyLR implicit $x1443...444---445name: zext_shl_LDRWroW446alignment: 4447legalized: true448regBankSelected: true449tracksRegLiveness: true450liveins:451 - { reg: '$w0' }452 - { reg: '$x1' }453body: |454 bb.1:455 liveins: $w0, $x1456 457 ; We try to look through the G_ZEXT of the SHL here.458 459 ; CHECK-LABEL: name: zext_shl_LDRWroW460 ; CHECK: liveins: $w0, $x1461 ; CHECK-NEXT: {{ $}}462 ; CHECK-NEXT: [[COPY:%[0-9]+]]:gpr32 = COPY $w0463 ; CHECK-NEXT: [[COPY1:%[0-9]+]]:gpr64sp = COPY $x1464 ; CHECK-NEXT: [[ANDWri:%[0-9]+]]:gpr32common = ANDWri [[COPY]], 7465 ; CHECK-NEXT: [[LDRWroW:%[0-9]+]]:gpr32 = LDRWroW [[COPY1]], [[ANDWri]], 0, 1 :: (load (s32))466 ; CHECK-NEXT: $w0 = COPY [[LDRWroW]]467 ; CHECK-NEXT: RET_ReallyLR implicit $w0468 %0:gpr(s32) = COPY $w0469 %1:gpr(p0) = COPY $x1470 %2:gpr(s32) = G_CONSTANT i32 255471 %3:gpr(s32) = G_AND %0, %2472 %13:gpr(s64) = G_CONSTANT i64 2473 %12:gpr(s32) = G_SHL %3, %13(s64)474 %6:gpr(s64) = G_ZEXT %12(s32)475 %7:gpr(p0) = G_PTR_ADD %1, %6(s64)476 %9:gpr(s32) = G_LOAD %7(p0) :: (load (s32))477 $w0 = COPY %9(s32)478 RET_ReallyLR implicit $w0479 480...481