[SystemZ] Be more careful about inverting CC masks (conditional loads)
[oota-llvm.git] / test / CodeGen / SystemZ / cond-load-01.ll
1 ; Test LOC.
2 ;
3 ; RUN: llc < %s -mtriple=s390x-linux-gnu -mcpu=z196 | FileCheck %s
4
5 declare i32 @foo(i32 *)
6
7 ; Test the simple case.
8 define i32 @f1(i32 %easy, i32 *%ptr, i32 %limit) {
9 ; CHECK-LABEL: f1:
10 ; CHECK: clfi %r4, 42
11 ; CHECK: loche %r2, 0(%r3)
12 ; CHECK: br %r14
13   %cond = icmp ult i32 %limit, 42
14   %other = load i32 *%ptr
15   %res = select i1 %cond, i32 %easy, i32 %other
16   ret i32 %res
17 }
18
19 ; ...and again with the operands swapped.
20 define i32 @f2(i32 %easy, i32 *%ptr, i32 %limit) {
21 ; CHECK-LABEL: f2:
22 ; CHECK: clfi %r4, 42
23 ; CHECK: locl %r2, 0(%r3)
24 ; CHECK: br %r14
25   %cond = icmp ult i32 %limit, 42
26   %other = load i32 *%ptr
27   %res = select i1 %cond, i32 %other, i32 %easy
28   ret i32 %res
29 }
30
31 ; Check the high end of the aligned LOC range.
32 define i32 @f3(i32 %easy, i32 *%base, i32 %limit) {
33 ; CHECK-LABEL: f3:
34 ; CHECK: clfi %r4, 42
35 ; CHECK: loche %r2, 524284(%r3)
36 ; CHECK: br %r14
37   %ptr = getelementptr i32 *%base, i64 131071
38   %cond = icmp ult i32 %limit, 42
39   %other = load i32 *%ptr
40   %res = select i1 %cond, i32 %easy, i32 %other
41   ret i32 %res
42 }
43
44 ; Check the next word up.  Other sequences besides this one would be OK.
45 define i32 @f4(i32 %easy, i32 *%base, i32 %limit) {
46 ; CHECK-LABEL: f4:
47 ; CHECK: agfi %r3, 524288
48 ; CHECK: clfi %r4, 42
49 ; CHECK: loche %r2, 0(%r3)
50 ; CHECK: br %r14
51   %ptr = getelementptr i32 *%base, i64 131072
52   %cond = icmp ult i32 %limit, 42
53   %other = load i32 *%ptr
54   %res = select i1 %cond, i32 %easy, i32 %other
55   ret i32 %res
56 }
57
58 ; Check the low end of the LOC range.
59 define i32 @f5(i32 %easy, i32 *%base, i32 %limit) {
60 ; CHECK-LABEL: f5:
61 ; CHECK: clfi %r4, 42
62 ; CHECK: loche %r2, -524288(%r3)
63 ; CHECK: br %r14
64   %ptr = getelementptr i32 *%base, i64 -131072
65   %cond = icmp ult i32 %limit, 42
66   %other = load i32 *%ptr
67   %res = select i1 %cond, i32 %easy, i32 %other
68   ret i32 %res
69 }
70
71 ; Check the next word down, with the same comments as f4.
72 define i32 @f6(i32 %easy, i32 *%base, i32 %limit) {
73 ; CHECK-LABEL: f6:
74 ; CHECK: agfi %r3, -524292
75 ; CHECK: clfi %r4, 42
76 ; CHECK: loche %r2, 0(%r3)
77 ; CHECK: br %r14
78   %ptr = getelementptr i32 *%base, i64 -131073
79   %cond = icmp ult i32 %limit, 42
80   %other = load i32 *%ptr
81   %res = select i1 %cond, i32 %easy, i32 %other
82   ret i32 %res
83 }
84
85 ; Try a frame index base.
86 define i32 @f7(i32 %alt, i32 %limit) {
87 ; CHECK-LABEL: f7:
88 ; CHECK: brasl %r14, foo@PLT
89 ; CHECK: loche %r2, {{[0-9]+}}(%r15)
90 ; CHECK: br %r14
91   %ptr = alloca i32
92   %easy = call i32 @foo(i32 *%ptr)
93   %cond = icmp ult i32 %limit, 42
94   %other = load i32 *%ptr
95   %res = select i1 %cond, i32 %easy, i32 %other
96   ret i32 %res
97 }
98
99 ; Try a case when an index is involved.
100 define i32 @f8(i32 %easy, i32 %limit, i64 %base, i64 %index) {
101 ; CHECK-LABEL: f8:
102 ; CHECK: clfi %r3, 42
103 ; CHECK: loche %r2, 0({{%r[1-5]}})
104 ; CHECK: br %r14
105   %add = add i64 %base, %index
106   %ptr = inttoptr i64 %add to i32 *
107   %cond = icmp ult i32 %limit, 42
108   %other = load i32 *%ptr
109   %res = select i1 %cond, i32 %easy, i32 %other
110   ret i32 %res
111 }
112
113 ; Test that conditionally-executed loads do not use LOC, since it is allowed
114 ; to trap even when the condition is false.
115 define i32 @f9(i32 %easy, i32 %limit, i32 *%ptr) {
116 ; CHECK-LABEL: f9:
117 ; CHECK-NOT: loc
118 ; CHECK: br %r14
119 entry:
120   %cmp = icmp ule i32 %easy, %limit
121   br i1 %cmp, label %load, label %exit
122
123 load:
124   %other = load i32 *%ptr
125   br label %exit
126
127 exit:
128   %res = phi i32 [ %easy, %entry ], [ %other, %load ]
129   ret i32 %res
130 }