609 lines
20 KiB
Plaintext
609 lines
20 KiB
Plaintext
|
# NOTE: Assertions have been autogenerated by utils/update_mir_test_checks.py
|
||
|
# RUN: llc -O0 -mtriple=aarch64-apple-ios -run-pass=localizer -verify-machineinstrs %s -o - | FileCheck %s -check-prefix=CHECK
|
||
|
|
||
|
# Test the localizer.
|
||
|
|
||
|
--- |
|
||
|
target datalayout = "e-m:o-i64:64-i128:128-n32:64-S128"
|
||
|
|
||
|
define void @local_use() { ret void }
|
||
|
define void @non_local_1use() { ret void }
|
||
|
define void @non_local_2uses() { ret void }
|
||
|
define void @non_local_phi_use() { ret void }
|
||
|
define void @non_local_phi_use_followed_by_use() { ret void }
|
||
|
define void @non_local_phi_use_followed_by_use_fi() { ret void }
|
||
|
define void @float_non_local_phi_use_followed_by_use_fi() { ret void }
|
||
|
define void @non_local_phi() { ret void }
|
||
|
define void @non_local_label() { ret void }
|
||
|
|
||
|
@var1 = common global i32 0, align 4
|
||
|
@var2 = common global i32 0, align 4
|
||
|
@var3 = common global i32 0, align 4
|
||
|
@var4 = common global i32 0, align 4
|
||
|
|
||
|
define i32 @intrablock_with_globalvalue() {
|
||
|
entry:
|
||
|
%0 = load i32, i32* @var1, align 4
|
||
|
%cmp = icmp eq i32 %0, 1
|
||
|
br i1 %cmp, label %if.then, label %if.end
|
||
|
|
||
|
if.then:
|
||
|
store i32 2, i32* @var2, align 4
|
||
|
store i32 3, i32* @var1, align 4
|
||
|
store i32 2, i32* @var3, align 4
|
||
|
store i32 3, i32* @var1, align 4
|
||
|
br label %if.end
|
||
|
|
||
|
if.end:
|
||
|
ret i32 0
|
||
|
}
|
||
|
define i32 @adrp_add() {
|
||
|
entry:
|
||
|
%0 = load i32, i32* @var1, align 4
|
||
|
%cmp = icmp eq i32 %0, 1
|
||
|
br i1 %cmp, label %if.then, label %if.end
|
||
|
|
||
|
if.then:
|
||
|
store i32 2, i32* @var2, align 4
|
||
|
store i32 3, i32* @var1, align 4
|
||
|
store i32 2, i32* @var3, align 4
|
||
|
store i32 3, i32* @var1, align 4
|
||
|
br label %if.end
|
||
|
|
||
|
if.end:
|
||
|
ret i32 0
|
||
|
}
|
||
|
|
||
|
define void @test_inttoptr() { ret void }
|
||
|
define void @many_local_use_intra_block() { ret void }
|
||
|
define void @non_local_phi_use_nonunique() { ret void }
|
||
|
...
|
||
|
|
||
|
---
|
||
|
name: local_use
|
||
|
legalized: true
|
||
|
regBankSelected: true
|
||
|
body: |
|
||
|
bb.0:
|
||
|
; CHECK-LABEL: name: local_use
|
||
|
; CHECK: [[C:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 1
|
||
|
; CHECK: [[ADD:%[0-9]+]]:gpr(s32) = G_ADD [[C]], [[C]]
|
||
|
%0:gpr(s32) = G_CONSTANT i32 1
|
||
|
%1:gpr(s32) = G_ADD %0, %0
|
||
|
...
|
||
|
|
||
|
---
|
||
|
name: non_local_1use
|
||
|
legalized: true
|
||
|
regBankSelected: true
|
||
|
body: |
|
||
|
; CHECK-LABEL: name: non_local_1use
|
||
|
; CHECK: bb.0:
|
||
|
; CHECK: successors: %bb.1(0x80000000)
|
||
|
; CHECK: [[C:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 1
|
||
|
; CHECK: [[ADD:%[0-9]+]]:gpr(s32) = G_ADD [[C]], [[C]]
|
||
|
; CHECK: bb.1:
|
||
|
; CHECK: [[C1:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 1
|
||
|
; CHECK: [[ADD1:%[0-9]+]]:gpr(s32) = G_ADD [[C1]], [[ADD]]
|
||
|
|
||
|
; Existing registers should be left untouched
|
||
|
; The newly created reg should be on the same regbank/regclass as its origin.
|
||
|
|
||
|
bb.0:
|
||
|
successors: %bb.1
|
||
|
|
||
|
%0:gpr(s32) = G_CONSTANT i32 1
|
||
|
%1:gpr(s32) = G_ADD %0, %0
|
||
|
|
||
|
bb.1:
|
||
|
%2:gpr(s32) = G_ADD %0, %1
|
||
|
...
|
||
|
|
||
|
---
|
||
|
name: non_local_2uses
|
||
|
legalized: true
|
||
|
regBankSelected: true
|
||
|
body: |
|
||
|
; CHECK-LABEL: name: non_local_2uses
|
||
|
; CHECK: bb.0:
|
||
|
; CHECK: successors: %bb.1(0x80000000)
|
||
|
; CHECK: [[C:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 1
|
||
|
; CHECK: [[ADD:%[0-9]+]]:gpr(s32) = G_ADD [[C]], [[C]]
|
||
|
; CHECK: bb.1:
|
||
|
; CHECK: [[C1:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 1
|
||
|
; CHECK: [[ADD1:%[0-9]+]]:gpr(s32) = G_ADD [[C1]], [[C1]]
|
||
|
|
||
|
; Existing registers should be left untouched
|
||
|
; The newly created reg should be on the same regbank/regclass as its origin.
|
||
|
|
||
|
bb.0:
|
||
|
successors: %bb.1
|
||
|
|
||
|
%0:gpr(s32) = G_CONSTANT i32 1
|
||
|
%1:gpr(s32) = G_ADD %0, %0
|
||
|
|
||
|
bb.1:
|
||
|
%2:gpr(s32) = G_ADD %0, %0
|
||
|
...
|
||
|
|
||
|
---
|
||
|
name: non_local_phi_use
|
||
|
legalized: true
|
||
|
regBankSelected: true
|
||
|
tracksRegLiveness: true
|
||
|
body: |
|
||
|
; CHECK-LABEL: name: non_local_phi_use
|
||
|
; CHECK: bb.0:
|
||
|
; CHECK: successors: %bb.1(0x80000000)
|
||
|
; CHECK: [[C:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 1
|
||
|
; CHECK: [[ADD:%[0-9]+]]:gpr(s32) = G_ADD [[C]], [[C]]
|
||
|
; CHECK: bb.1:
|
||
|
; CHECK: successors: %bb.2(0x80000000)
|
||
|
; CHECK: [[C1:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 1
|
||
|
; CHECK: bb.2:
|
||
|
; CHECK: [[PHI:%[0-9]+]]:gpr(s32) = PHI [[C1]](s32), %bb.1
|
||
|
; CHECK: [[ADD1:%[0-9]+]]:gpr(s32) = G_ADD [[PHI]], [[PHI]]
|
||
|
|
||
|
; Existing registers should be left untouched
|
||
|
; The newly created reg should be on the same regbank/regclass as its origin.
|
||
|
|
||
|
bb.0:
|
||
|
successors: %bb.1
|
||
|
|
||
|
%0:gpr(s32) = G_CONSTANT i32 1
|
||
|
%1:gpr(s32) = G_ADD %0, %0
|
||
|
|
||
|
bb.1:
|
||
|
successors: %bb.2
|
||
|
|
||
|
bb.2:
|
||
|
%3:gpr(s32) = PHI %0(s32), %bb.1
|
||
|
%2:gpr(s32) = G_ADD %3, %3
|
||
|
...
|
||
|
|
||
|
---
|
||
|
name: non_local_phi_use_followed_by_use
|
||
|
legalized: true
|
||
|
regBankSelected: true
|
||
|
tracksRegLiveness: true
|
||
|
body: |
|
||
|
; CHECK-LABEL: name: non_local_phi_use_followed_by_use
|
||
|
; CHECK: bb.0:
|
||
|
; CHECK: successors: %bb.1(0x80000000)
|
||
|
; CHECK: [[C:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 1
|
||
|
; CHECK: [[ADD:%[0-9]+]]:gpr(s32) = G_ADD [[C]], [[C]]
|
||
|
; CHECK: bb.1:
|
||
|
; CHECK: successors: %bb.2(0x80000000)
|
||
|
; CHECK: [[C1:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 1
|
||
|
; CHECK: bb.2:
|
||
|
; CHECK: [[PHI:%[0-9]+]]:gpr(s32) = PHI [[C1]](s32), %bb.1
|
||
|
; CHECK: [[C2:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 1
|
||
|
; CHECK: [[ADD1:%[0-9]+]]:gpr(s32) = G_ADD [[PHI]], [[C2]]
|
||
|
|
||
|
; Existing registers should be left untouched
|
||
|
; The newly created reg should be on the same regbank/regclass as its origin.
|
||
|
|
||
|
bb.0:
|
||
|
successors: %bb.1
|
||
|
|
||
|
%0:gpr(s32) = G_CONSTANT i32 1
|
||
|
%1:gpr(s32) = G_ADD %0, %0
|
||
|
|
||
|
bb.1:
|
||
|
successors: %bb.2
|
||
|
|
||
|
bb.2:
|
||
|
%3:gpr(s32) = PHI %0(s32), %bb.1
|
||
|
%2:gpr(s32) = G_ADD %3, %0
|
||
|
...
|
||
|
|
||
|
---
|
||
|
name: non_local_phi_use_followed_by_use_fi
|
||
|
legalized: true
|
||
|
regBankSelected: true
|
||
|
tracksRegLiveness: true
|
||
|
body: |
|
||
|
; CHECK-LABEL: name: non_local_phi_use_followed_by_use_fi
|
||
|
; CHECK: bb.0:
|
||
|
; CHECK: successors: %bb.1(0x80000000)
|
||
|
; CHECK: [[FRAME_INDEX:%[0-9]+]]:gpr(s32) = G_FRAME_INDEX 1
|
||
|
; CHECK: [[ADD:%[0-9]+]]:gpr(s32) = G_ADD [[FRAME_INDEX]], [[FRAME_INDEX]]
|
||
|
; CHECK: bb.1:
|
||
|
; CHECK: successors: %bb.2(0x80000000)
|
||
|
; CHECK: [[FRAME_INDEX1:%[0-9]+]]:gpr(s32) = G_FRAME_INDEX 1
|
||
|
; CHECK: bb.2:
|
||
|
; CHECK: [[PHI:%[0-9]+]]:gpr(s32) = PHI [[FRAME_INDEX1]](s32), %bb.1
|
||
|
; CHECK: [[FRAME_INDEX2:%[0-9]+]]:gpr(s32) = G_FRAME_INDEX 1
|
||
|
; CHECK: [[ADD1:%[0-9]+]]:gpr(s32) = G_ADD [[PHI]], [[FRAME_INDEX2]]
|
||
|
|
||
|
; Existing registers should be left untouched
|
||
|
; The newly created reg should be on the same regbank/regclass as its origin.
|
||
|
|
||
|
bb.0:
|
||
|
successors: %bb.1
|
||
|
|
||
|
%0:gpr(s32) = G_FRAME_INDEX 1
|
||
|
%1:gpr(s32) = G_ADD %0, %0
|
||
|
|
||
|
bb.1:
|
||
|
successors: %bb.2
|
||
|
|
||
|
bb.2:
|
||
|
%3:gpr(s32) = PHI %0(s32), %bb.1
|
||
|
%2:gpr(s32) = G_ADD %3, %0
|
||
|
...
|
||
|
|
||
|
---
|
||
|
name: float_non_local_phi_use_followed_by_use_fi
|
||
|
legalized: true
|
||
|
regBankSelected: true
|
||
|
tracksRegLiveness: true
|
||
|
body: |
|
||
|
; CHECK-LABEL: name: float_non_local_phi_use_followed_by_use_fi
|
||
|
; CHECK: bb.0:
|
||
|
; CHECK: successors: %bb.1(0x80000000)
|
||
|
; CHECK: [[C:%[0-9]+]]:fpr(s32) = G_FCONSTANT float 1.000000e+00
|
||
|
; CHECK: [[FADD:%[0-9]+]]:fpr(s32) = G_FADD [[C]], [[C]]
|
||
|
; CHECK: bb.1:
|
||
|
; CHECK: successors: %bb.2(0x80000000)
|
||
|
; CHECK: [[C1:%[0-9]+]]:fpr(s32) = G_FCONSTANT float 1.000000e+00
|
||
|
; CHECK: bb.2:
|
||
|
; CHECK: [[PHI:%[0-9]+]]:fpr(s32) = PHI [[C1]](s32), %bb.1
|
||
|
; CHECK: [[C2:%[0-9]+]]:fpr(s32) = G_FCONSTANT float 1.000000e+00
|
||
|
; CHECK: [[FADD1:%[0-9]+]]:fpr(s32) = G_FADD [[PHI]], [[C2]]
|
||
|
|
||
|
; Existing registers should be left untouched
|
||
|
; The newly created reg should be on the same regbank/regclass as its origin.
|
||
|
|
||
|
bb.0:
|
||
|
successors: %bb.1
|
||
|
|
||
|
%0:fpr(s32) = G_FCONSTANT float 1.0
|
||
|
%1:fpr(s32) = G_FADD %0, %0
|
||
|
|
||
|
bb.1:
|
||
|
successors: %bb.2
|
||
|
|
||
|
bb.2:
|
||
|
%3:fpr(s32) = PHI %0(s32), %bb.1
|
||
|
%2:fpr(s32) = G_FADD %3, %0
|
||
|
...
|
||
|
|
||
|
---
|
||
|
# Make sure we don't insert a constant before PHIs.
|
||
|
# This used to happen for loops of one basic block.
|
||
|
name: non_local_phi
|
||
|
legalized: true
|
||
|
regBankSelected: true
|
||
|
tracksRegLiveness: true
|
||
|
body: |
|
||
|
; CHECK-LABEL: name: non_local_phi
|
||
|
; CHECK: bb.0:
|
||
|
; CHECK: successors: %bb.1(0x80000000)
|
||
|
; CHECK: [[C:%[0-9]+]]:fpr(s32) = G_FCONSTANT float 1.000000e+00
|
||
|
; CHECK: [[FADD:%[0-9]+]]:fpr(s32) = G_FADD [[C]], [[C]]
|
||
|
; CHECK: bb.1:
|
||
|
; CHECK: successors: %bb.1(0x80000000)
|
||
|
; CHECK: [[PHI:%[0-9]+]]:fpr(s32) = PHI [[FADD]](s32), %bb.0, %4(s32), %bb.1
|
||
|
; CHECK: [[C1:%[0-9]+]]:fpr(s32) = G_FCONSTANT float 1.000000e+00
|
||
|
; CHECK: [[FADD1:%[0-9]+]]:fpr(s32) = G_FADD [[PHI]], [[FADD]]
|
||
|
; CHECK: G_BR %bb.1
|
||
|
|
||
|
; Existing registers should be left untouched
|
||
|
; The newly created reg should be on the same regbank/regclass as its origin.
|
||
|
|
||
|
bb.0:
|
||
|
successors: %bb.1
|
||
|
|
||
|
%0:fpr(s32) = G_FCONSTANT float 1.0
|
||
|
%1:fpr(s32) = G_FADD %0, %0
|
||
|
|
||
|
bb.1:
|
||
|
successors: %bb.1
|
||
|
|
||
|
%3:fpr(s32) = PHI %1(s32), %bb.0, %0(s32), %bb.1
|
||
|
%2:fpr(s32) = G_FADD %3, %1
|
||
|
G_BR %bb.1
|
||
|
...
|
||
|
|
||
|
---
|
||
|
# Make sure we don't insert a constant before EH_LABELs.
|
||
|
name: non_local_label
|
||
|
legalized: true
|
||
|
regBankSelected: true
|
||
|
tracksRegLiveness: true
|
||
|
body: |
|
||
|
; CHECK-LABEL: name: non_local_label
|
||
|
; CHECK: bb.0:
|
||
|
; CHECK: successors: %bb.1(0x80000000)
|
||
|
; CHECK: liveins: $s0
|
||
|
; CHECK: [[COPY:%[0-9]+]]:fpr(s32) = COPY $s0
|
||
|
; CHECK: [[C:%[0-9]+]]:fpr(s32) = G_FCONSTANT float 1.000000e+00
|
||
|
; CHECK: bb.1:
|
||
|
; CHECK: successors: %bb.1(0x80000000)
|
||
|
; CHECK: EH_LABEL 1
|
||
|
; CHECK: [[C1:%[0-9]+]]:fpr(s32) = G_FCONSTANT float 1.000000e+00
|
||
|
; CHECK: [[FADD:%[0-9]+]]:fpr(s32) = G_FADD [[COPY]], [[C1]]
|
||
|
; CHECK: G_BR %bb.1
|
||
|
|
||
|
; Existing registers should be left untouched
|
||
|
; The newly created reg should be on the same regbank/regclass as its origin.
|
||
|
|
||
|
bb.0:
|
||
|
liveins: $s0
|
||
|
successors: %bb.1
|
||
|
|
||
|
%0:fpr(s32) = COPY $s0
|
||
|
%1:fpr(s32) = G_FCONSTANT float 1.0
|
||
|
|
||
|
bb.1:
|
||
|
successors: %bb.1
|
||
|
|
||
|
EH_LABEL 1
|
||
|
%2:fpr(s32) = G_FADD %0, %1
|
||
|
G_BR %bb.1
|
||
|
...
|
||
|
---
|
||
|
name: intrablock_with_globalvalue
|
||
|
legalized: true
|
||
|
regBankSelected: true
|
||
|
tracksRegLiveness: true
|
||
|
body: |
|
||
|
; CHECK-LABEL: name: intrablock_with_globalvalue
|
||
|
; CHECK: bb.0.entry:
|
||
|
; CHECK: successors: %bb.1(0x40000000), %bb.2(0x40000000)
|
||
|
; CHECK: [[C:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 2
|
||
|
; CHECK: [[GV:%[0-9]+]]:gpr(p0) = G_GLOBAL_VALUE @var2
|
||
|
; CHECK: [[C1:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 3
|
||
|
; CHECK: [[GV1:%[0-9]+]]:gpr(p0) = G_GLOBAL_VALUE @var3
|
||
|
; CHECK: [[C2:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 0
|
||
|
; CHECK: [[GV2:%[0-9]+]]:gpr(p0) = G_GLOBAL_VALUE @var1
|
||
|
; CHECK: [[LOAD:%[0-9]+]]:gpr(s32) = G_LOAD [[GV2]](p0) :: (load 4 from @var1)
|
||
|
; CHECK: [[C3:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 1
|
||
|
; CHECK: [[ICMP:%[0-9]+]]:gpr(s32) = G_ICMP intpred(eq), [[LOAD]](s32), [[C3]]
|
||
|
; CHECK: [[TRUNC:%[0-9]+]]:gpr(s1) = G_TRUNC [[ICMP]](s32)
|
||
|
; CHECK: G_BRCOND [[TRUNC]](s1), %bb.1
|
||
|
; CHECK: G_BR %bb.2
|
||
|
; CHECK: bb.1.if.then:
|
||
|
; CHECK: successors: %bb.2(0x80000000)
|
||
|
; CHECK: [[GV3:%[0-9]+]]:gpr(p0) = G_GLOBAL_VALUE @var2
|
||
|
; CHECK: [[C4:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 2
|
||
|
; CHECK: G_STORE [[C4]](s32), [[GV3]](p0) :: (store 4 into @var2)
|
||
|
; CHECK: [[C5:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 3
|
||
|
; CHECK: [[GV4:%[0-9]+]]:gpr(p0) = G_GLOBAL_VALUE @var1
|
||
|
; CHECK: G_STORE [[C5]](s32), [[GV4]](p0) :: (store 4 into @var1)
|
||
|
; CHECK: [[GV5:%[0-9]+]]:gpr(p0) = G_GLOBAL_VALUE @var3
|
||
|
; CHECK: G_STORE [[C4]](s32), [[GV5]](p0) :: (store 4 into @var3)
|
||
|
; CHECK: G_STORE [[C5]](s32), [[GV4]](p0) :: (store 4 into @var1)
|
||
|
; CHECK: bb.2.if.end:
|
||
|
; CHECK: [[C6:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 0
|
||
|
; CHECK: $w0 = COPY [[C6]](s32)
|
||
|
; CHECK: RET_ReallyLR implicit $w0
|
||
|
|
||
|
; Some of these instructions are dead. We're checking that the other instructions are
|
||
|
; sunk immediately before their first user in the if.then block or as close as possible.
|
||
|
bb.1.entry:
|
||
|
%1:gpr(p0) = G_GLOBAL_VALUE @var1
|
||
|
%2:gpr(s32) = G_CONSTANT i32 1
|
||
|
%4:gpr(s32) = G_CONSTANT i32 2
|
||
|
%5:gpr(p0) = G_GLOBAL_VALUE @var2
|
||
|
%6:gpr(s32) = G_CONSTANT i32 3
|
||
|
%7:gpr(p0) = G_GLOBAL_VALUE @var3
|
||
|
%8:gpr(s32) = G_CONSTANT i32 0
|
||
|
%0:gpr(s32) = G_LOAD %1(p0) :: (load 4 from @var1)
|
||
|
%9:gpr(s32) = G_ICMP intpred(eq), %0(s32), %2
|
||
|
%3:gpr(s1) = G_TRUNC %9(s32)
|
||
|
G_BRCOND %3(s1), %bb.2
|
||
|
G_BR %bb.3
|
||
|
|
||
|
bb.2.if.then:
|
||
|
G_STORE %4(s32), %5(p0) :: (store 4 into @var2)
|
||
|
G_STORE %6(s32), %1(p0) :: (store 4 into @var1)
|
||
|
G_STORE %4(s32), %7(p0) :: (store 4 into @var3)
|
||
|
G_STORE %6(s32), %1(p0) :: (store 4 into @var1)
|
||
|
|
||
|
bb.3.if.end:
|
||
|
$w0 = COPY %8(s32)
|
||
|
RET_ReallyLR implicit $w0
|
||
|
|
||
|
...
|
||
|
---
|
||
|
name: adrp_add
|
||
|
legalized: true
|
||
|
regBankSelected: true
|
||
|
tracksRegLiveness: true
|
||
|
body: |
|
||
|
; CHECK-LABEL: name: adrp_add
|
||
|
; CHECK: bb.0.entry:
|
||
|
; CHECK: successors: %bb.1(0x40000000), %bb.2(0x40000000)
|
||
|
; CHECK: [[ADRP:%[0-9]+]]:gpr64(p0) = ADRP target-flags(aarch64-page) @var1
|
||
|
; CHECK: %addlow1:gpr(p0) = G_ADD_LOW [[ADRP]](p0), target-flags(aarch64-pageoff, aarch64-nc) @var1
|
||
|
; CHECK: [[C:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 2
|
||
|
; CHECK: [[ADRP1:%[0-9]+]]:gpr64(p0) = ADRP target-flags(aarch64-page) @var2
|
||
|
; CHECK: %addlow2:gpr(p0) = G_ADD_LOW [[ADRP1]](p0), target-flags(aarch64-pageoff, aarch64-nc) @var2
|
||
|
; CHECK: [[C1:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 3
|
||
|
; CHECK: [[ADRP2:%[0-9]+]]:gpr64(p0) = ADRP target-flags(aarch64-page) @var3
|
||
|
; CHECK: %addlow3:gpr(p0) = G_ADD_LOW [[ADRP2]](p0), target-flags(aarch64-pageoff, aarch64-nc) @var3
|
||
|
; CHECK: [[C2:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 0
|
||
|
; CHECK: [[LOAD:%[0-9]+]]:gpr(s32) = G_LOAD [[ADRP]](p0) :: (load 4 from @var1)
|
||
|
; CHECK: [[C3:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 1
|
||
|
; CHECK: [[ICMP:%[0-9]+]]:gpr(s32) = G_ICMP intpred(eq), [[LOAD]](s32), [[C3]]
|
||
|
; CHECK: [[TRUNC:%[0-9]+]]:gpr(s1) = G_TRUNC [[ICMP]](s32)
|
||
|
; CHECK: G_BRCOND [[TRUNC]](s1), %bb.1
|
||
|
; CHECK: G_BR %bb.2
|
||
|
; CHECK: bb.1.if.then:
|
||
|
; CHECK: successors: %bb.2(0x80000000)
|
||
|
; CHECK: [[ADRP3:%[0-9]+]]:gpr64(p0) = ADRP target-flags(aarch64-page) @var2
|
||
|
; CHECK: [[ADD_LOW:%[0-9]+]]:gpr(p0) = G_ADD_LOW [[ADRP3]](p0), target-flags(aarch64-pageoff, aarch64-nc) @var2
|
||
|
; CHECK: [[C4:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 2
|
||
|
; CHECK: G_STORE [[C4]](s32), [[ADD_LOW]](p0) :: (store 4 into @var2)
|
||
|
; CHECK: [[C5:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 3
|
||
|
; CHECK: [[ADRP4:%[0-9]+]]:gpr64(p0) = ADRP target-flags(aarch64-page) @var1
|
||
|
; CHECK: [[ADD_LOW1:%[0-9]+]]:gpr(p0) = G_ADD_LOW [[ADRP4]](p0), target-flags(aarch64-pageoff, aarch64-nc) @var1
|
||
|
; CHECK: G_STORE [[C5]](s32), [[ADD_LOW1]](p0) :: (store 4 into @var1)
|
||
|
; CHECK: [[ADRP5:%[0-9]+]]:gpr64(p0) = ADRP target-flags(aarch64-page) @var3
|
||
|
; CHECK: [[ADD_LOW2:%[0-9]+]]:gpr(p0) = G_ADD_LOW [[ADRP5]](p0), target-flags(aarch64-pageoff, aarch64-nc) @var3
|
||
|
; CHECK: G_STORE [[C4]](s32), [[ADD_LOW2]](p0) :: (store 4 into @var3)
|
||
|
; CHECK: G_STORE [[C5]](s32), [[ADD_LOW1]](p0) :: (store 4 into @var1)
|
||
|
; CHECK: bb.2.if.end:
|
||
|
; CHECK: [[C6:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 0
|
||
|
; CHECK: $w0 = COPY [[C6]](s32)
|
||
|
; CHECK: RET_ReallyLR implicit $w0
|
||
|
|
||
|
; Some of these instructions are dead.
|
||
|
bb.1.entry:
|
||
|
%1:gpr64(p0) = ADRP target-flags(aarch64-page) @var1
|
||
|
%addlow1:gpr(p0) = G_ADD_LOW %1(p0), target-flags(aarch64-pageoff, aarch64-nc) @var1
|
||
|
%2:gpr(s32) = G_CONSTANT i32 1
|
||
|
%4:gpr(s32) = G_CONSTANT i32 2
|
||
|
%5:gpr64(p0) = ADRP target-flags(aarch64-page) @var2
|
||
|
%addlow2:gpr(p0) = G_ADD_LOW %5(p0), target-flags(aarch64-pageoff, aarch64-nc) @var2
|
||
|
%6:gpr(s32) = G_CONSTANT i32 3
|
||
|
%7:gpr64(p0) = ADRP target-flags(aarch64-page) @var3
|
||
|
%addlow3:gpr(p0) = G_ADD_LOW %7(p0), target-flags(aarch64-pageoff, aarch64-nc) @var3
|
||
|
%8:gpr(s32) = G_CONSTANT i32 0
|
||
|
%0:gpr(s32) = G_LOAD %1(p0) :: (load 4 from @var1)
|
||
|
%9:gpr(s32) = G_ICMP intpred(eq), %0(s32), %2
|
||
|
%3:gpr(s1) = G_TRUNC %9(s32)
|
||
|
G_BRCOND %3(s1), %bb.2
|
||
|
G_BR %bb.3
|
||
|
|
||
|
bb.2.if.then:
|
||
|
G_STORE %4(s32), %addlow2(p0) :: (store 4 into @var2)
|
||
|
G_STORE %6(s32), %addlow1(p0) :: (store 4 into @var1)
|
||
|
G_STORE %4(s32), %addlow3(p0) :: (store 4 into @var3)
|
||
|
G_STORE %6(s32), %addlow1(p0) :: (store 4 into @var1)
|
||
|
|
||
|
bb.3.if.end:
|
||
|
$w0 = COPY %8(s32)
|
||
|
RET_ReallyLR implicit $w0
|
||
|
|
||
|
...
|
||
|
---
|
||
|
name: test_inttoptr
|
||
|
alignment: 4
|
||
|
legalized: true
|
||
|
regBankSelected: true
|
||
|
tracksRegLiveness: true
|
||
|
body: |
|
||
|
; CHECK-LABEL: name: test_inttoptr
|
||
|
; CHECK: bb.0:
|
||
|
; CHECK: successors: %bb.1(0x40000000), %bb.2(0x40000000)
|
||
|
; CHECK: liveins: $w0, $x1
|
||
|
; CHECK: [[COPY:%[0-9]+]]:gpr(s32) = COPY $w0
|
||
|
; CHECK: [[COPY1:%[0-9]+]]:gpr(p0) = COPY $x1
|
||
|
; CHECK: [[C:%[0-9]+]]:gpr(s64) = G_CONSTANT i64 0
|
||
|
; CHECK: [[INTTOPTR:%[0-9]+]]:gpr(p0) = G_INTTOPTR [[C]](s64)
|
||
|
; CHECK: [[C1:%[0-9]+]]:gpr(s64) = G_CONSTANT i64 128
|
||
|
; CHECK: [[INTTOPTR1:%[0-9]+]]:gpr(p0) = G_INTTOPTR [[C1]](s64)
|
||
|
; CHECK: [[C2:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 0
|
||
|
; CHECK: [[ICMP:%[0-9]+]]:gpr(s32) = G_ICMP intpred(eq), [[COPY]](s32), [[C2]]
|
||
|
; CHECK: [[TRUNC:%[0-9]+]]:gpr(s1) = G_TRUNC [[ICMP]](s32)
|
||
|
; CHECK: G_BRCOND [[TRUNC]](s1), %bb.1
|
||
|
; CHECK: G_BR %bb.2
|
||
|
; CHECK: bb.1:
|
||
|
; CHECK: [[ADD:%[0-9]+]]:gpr(s32) = G_ADD [[COPY]], [[COPY]]
|
||
|
; CHECK: G_STORE [[ADD]](s32), [[COPY1]](p0) :: (store 4)
|
||
|
; CHECK: [[C3:%[0-9]+]]:gpr(s64) = G_CONSTANT i64 128
|
||
|
; CHECK: [[INTTOPTR2:%[0-9]+]]:gpr(p0) = G_INTTOPTR [[C3]](s64)
|
||
|
; CHECK: $x0 = COPY [[INTTOPTR2]](p0)
|
||
|
; CHECK: RET_ReallyLR implicit $x0
|
||
|
; CHECK: bb.2:
|
||
|
; CHECK: [[C4:%[0-9]+]]:gpr(s64) = G_CONSTANT i64 0
|
||
|
; CHECK: [[INTTOPTR3:%[0-9]+]]:gpr(p0) = G_INTTOPTR [[C4]](s64)
|
||
|
; CHECK: $x0 = COPY [[INTTOPTR3]](p0)
|
||
|
; CHECK: RET_ReallyLR implicit $x0
|
||
|
bb.1:
|
||
|
liveins: $w0, $x1
|
||
|
|
||
|
%0:gpr(s32) = COPY $w0
|
||
|
%1:gpr(p0) = COPY $x1
|
||
|
%2:gpr(s64) = G_CONSTANT i64 128
|
||
|
%4:gpr(s32) = G_CONSTANT i32 0
|
||
|
%7:gpr(s64) = G_CONSTANT i64 0
|
||
|
%6:gpr(p0) = G_INTTOPTR %7(s64)
|
||
|
%3:gpr(p0) = G_INTTOPTR %2(s64)
|
||
|
%9:gpr(s32) = G_ICMP intpred(eq), %0(s32), %4
|
||
|
%5:gpr(s1) = G_TRUNC %9(s32)
|
||
|
G_BRCOND %5(s1), %bb.2
|
||
|
G_BR %bb.3
|
||
|
|
||
|
bb.2:
|
||
|
%8:gpr(s32) = G_ADD %0, %0
|
||
|
G_STORE %8(s32), %1(p0) :: (store 4)
|
||
|
$x0 = COPY %3(p0)
|
||
|
RET_ReallyLR implicit $x0
|
||
|
|
||
|
bb.3:
|
||
|
$x0 = COPY %6(p0)
|
||
|
RET_ReallyLR implicit $x0
|
||
|
|
||
|
...
|
||
|
|
||
|
---
|
||
|
name: many_local_use_intra_block
|
||
|
legalized: true
|
||
|
regBankSelected: true
|
||
|
body: |
|
||
|
bb.0:
|
||
|
; CHECK-LABEL: name: many_local_use_intra_block
|
||
|
; CHECK: [[C:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 1
|
||
|
; CHECK: [[ADD:%[0-9]+]]:gpr(s32) = G_ADD [[C]], [[C]]
|
||
|
; CHECK: [[ADD1:%[0-9]+]]:gpr(s32) = G_ADD [[C]], [[C]]
|
||
|
; CHECK: [[ADD2:%[0-9]+]]:gpr(s32) = G_ADD [[C]], [[C]]
|
||
|
; CHECK: [[ADD3:%[0-9]+]]:gpr(s32) = G_ADD [[C]], [[C]]
|
||
|
; CHECK: [[ADD4:%[0-9]+]]:gpr(s32) = G_ADD [[C]], [[C]]
|
||
|
; CHECK: [[C1:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 2
|
||
|
; CHECK: [[ADD5:%[0-9]+]]:gpr(s32) = G_ADD [[C1]], [[C1]]
|
||
|
%0:gpr(s32) = G_CONSTANT i32 1
|
||
|
%1:gpr(s32) = G_CONSTANT i32 2
|
||
|
%2:gpr(s32) = G_ADD %0, %0
|
||
|
%3:gpr(s32) = G_ADD %0, %0
|
||
|
%4:gpr(s32) = G_ADD %0, %0
|
||
|
%5:gpr(s32) = G_ADD %0, %0
|
||
|
%6:gpr(s32) = G_ADD %0, %0
|
||
|
%7:gpr(s32) = G_ADD %1, %1
|
||
|
...
|
||
|
|
||
|
---
|
||
|
name: non_local_phi_use_nonunique
|
||
|
legalized: true
|
||
|
regBankSelected: true
|
||
|
tracksRegLiveness: true
|
||
|
body: |
|
||
|
; CHECK-LABEL: name: non_local_phi_use_nonunique
|
||
|
; CHECK: bb.0:
|
||
|
; CHECK: successors: %bb.1(0x40000000), %bb.2(0x40000000)
|
||
|
; CHECK: [[C:%[0-9]+]]:gpr(s32) = G_CONSTANT i32 1
|
||
|
; CHECK: [[ADD:%[0-9]+]]:gpr(s32) = G_ADD [[C]], [[C]]
|
||
|
; CHECK: %cmp:gpr(s32) = G_ICMP intpred(eq), [[ADD]](s32), [[C]]
|
||
|
; CHECK: %cond:gpr(s1) = G_TRUNC %cmp(s32)
|
||
|
; CHECK: G_BRCOND %cond(s1), %bb.1
|
||
|
; CHECK: G_BR %bb.2
|
||
|
; CHECK: bb.1:
|
||
|
; CHECK: successors: %bb.2(0x80000000)
|
||
|
; CHECK: bb.2:
|
||
|
; CHECK: [[PHI:%[0-9]+]]:gpr(s32) = G_PHI [[C]](s32), %bb.1
|
||
|
; CHECK: [[ADD1:%[0-9]+]]:gpr(s32) = G_ADD [[PHI]], [[PHI]]
|
||
|
|
||
|
; Don't localize the 1 into bb.1, because there are multiple edges
|
||
|
; using that register.
|
||
|
|
||
|
bb.0:
|
||
|
successors: %bb.1, %bb.2
|
||
|
|
||
|
%0:gpr(s32) = G_CONSTANT i32 1
|
||
|
%1:gpr(s32) = G_ADD %0, %0
|
||
|
%cmp:gpr(s32) = G_ICMP intpred(eq), %1(s32), %0
|
||
|
%cond:gpr(s1) = G_TRUNC %cmp(s32)
|
||
|
G_BRCOND %cond(s1), %bb.1
|
||
|
G_BR %bb.2
|
||
|
|
||
|
bb.1:
|
||
|
successors: %bb.2
|
||
|
|
||
|
bb.2:
|
||
|
%3:gpr(s32) = G_PHI %0(s32), %bb.1, %0(s32), %bb.0
|
||
|
%2:gpr(s32) = G_ADD %3, %3
|
||
|
...
|