1 ; Test STOCGs that are presented as selects.
3 ; RUN: llc < %s -mtriple=s390x-linux-gnu -mcpu=z196 | FileCheck %s
5 declare void @foo(i64 *)
7 ; Test with the loaded value first.
8 define void @f1(i64 *%ptr, i64 %alt, i32 %limit) {
11 ; CHECK: stocghe %r3, 0(%r2)
13 %cond = icmp ult i32 %limit, 42
14 %orig = load i64, i64 *%ptr
15 %res = select i1 %cond, i64 %orig, i64 %alt
16 store i64 %res, i64 *%ptr
20 ; ...and with the loaded value second
21 define void @f2(i64 *%ptr, i64 %alt, i32 %limit) {
24 ; CHECK: stocgl %r3, 0(%r2)
26 %cond = icmp ult i32 %limit, 42
27 %orig = load i64, i64 *%ptr
28 %res = select i1 %cond, i64 %alt, i64 %orig
29 store i64 %res, i64 *%ptr
33 ; Check the high end of the aligned STOCG range.
34 define void @f3(i64 *%base, i64 %alt, i32 %limit) {
37 ; CHECK: stocghe %r3, 524280(%r2)
39 %ptr = getelementptr i64, i64 *%base, i64 65535
40 %cond = icmp ult i32 %limit, 42
41 %orig = load i64, i64 *%ptr
42 %res = select i1 %cond, i64 %orig, i64 %alt
43 store i64 %res, i64 *%ptr
47 ; Check the next doubleword up. Other sequences besides this one would be OK.
48 define void @f4(i64 *%base, i64 %alt, i32 %limit) {
50 ; CHECK: agfi %r2, 524288
52 ; CHECK: stocghe %r3, 0(%r2)
54 %ptr = getelementptr i64, i64 *%base, i64 65536
55 %cond = icmp ult i32 %limit, 42
56 %orig = load i64, i64 *%ptr
57 %res = select i1 %cond, i64 %orig, i64 %alt
58 store i64 %res, i64 *%ptr
62 ; Check the low end of the STOCG range.
63 define void @f5(i64 *%base, i64 %alt, i32 %limit) {
66 ; CHECK: stocghe %r3, -524288(%r2)
68 %ptr = getelementptr i64, i64 *%base, i64 -65536
69 %cond = icmp ult i32 %limit, 42
70 %orig = load i64, i64 *%ptr
71 %res = select i1 %cond, i64 %orig, i64 %alt
72 store i64 %res, i64 *%ptr
76 ; Check the next doubleword down, with the same comments as f4.
77 define void @f6(i64 *%base, i64 %alt, i32 %limit) {
79 ; CHECK: agfi %r2, -524296
81 ; CHECK: stocghe %r3, 0(%r2)
83 %ptr = getelementptr i64, i64 *%base, i64 -65537
84 %cond = icmp ult i32 %limit, 42
85 %orig = load i64, i64 *%ptr
86 %res = select i1 %cond, i64 %orig, i64 %alt
87 store i64 %res, i64 *%ptr
91 ; Try a frame index base.
92 define void @f7(i64 %alt, i32 %limit) {
94 ; CHECK: brasl %r14, foo@PLT
95 ; CHECK: stocghe {{%r[0-9]+}}, {{[0-9]+}}(%r15)
96 ; CHECK: brasl %r14, foo@PLT
99 call void @foo(i64 *%ptr)
100 %cond = icmp ult i32 %limit, 42
101 %orig = load i64, i64 *%ptr
102 %res = select i1 %cond, i64 %orig, i64 %alt
103 store i64 %res, i64 *%ptr
104 call void @foo(i64 *%ptr)
108 ; Test that conditionally-executed stores do not use STOC, since STOC
109 ; is allowed to trap even when the condition is false.
110 define void @f8(i64 %a, i64 %b, i64 *%dest) {
112 ; CHECK-NOT: stocg %r3, 0(%r4)
115 %cmp = icmp ule i64 %a, %b
116 br i1 %cmp, label %store, label %exit
119 store i64 %b, i64 *%dest