blob: c85135ef6605871a32a3c8c14525d2a5e6484a05 [file] [log] [blame]
Sander de Smalen612b0382019-08-06 13:06:40 +00001//===- TestStackOffset.cpp - StackOffset unit tests------------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
9#include "AArch64StackOffset.h"
10#include "gtest/gtest.h"
11
12using namespace llvm;
13
14TEST(StackOffset, MixedSize) {
15 StackOffset A(1, MVT::i8);
16 EXPECT_EQ(1, A.getBytes());
17
18 StackOffset B(2, MVT::i32);
19 EXPECT_EQ(8, B.getBytes());
20
21 StackOffset C(2, MVT::v4i64);
22 EXPECT_EQ(64, C.getBytes());
Sander de Smalen4f99b6f2019-10-03 11:33:50 +000023
24 StackOffset D(2, MVT::nxv4i64);
25 EXPECT_EQ(64, D.getScalableBytes());
26
27 StackOffset E(2, MVT::v4i64);
28 EXPECT_EQ(0, E.getScalableBytes());
29
30 StackOffset F(2, MVT::nxv4i64);
31 EXPECT_EQ(0, F.getBytes());
Sander de Smalen612b0382019-08-06 13:06:40 +000032}
33
34TEST(StackOffset, Add) {
35 StackOffset A(1, MVT::i64);
36 StackOffset B(1, MVT::i32);
37 StackOffset C = A + B;
38 EXPECT_EQ(12, C.getBytes());
39
40 StackOffset D(1, MVT::i32);
41 D += A;
42 EXPECT_EQ(12, D.getBytes());
Sander de Smalen4f99b6f2019-10-03 11:33:50 +000043
44 StackOffset E(1, MVT::nxv1i32);
45 StackOffset F = C + E;
46 EXPECT_EQ(12, F.getBytes());
47 EXPECT_EQ(4, F.getScalableBytes());
Sander de Smalen612b0382019-08-06 13:06:40 +000048}
49
50TEST(StackOffset, Sub) {
51 StackOffset A(1, MVT::i64);
52 StackOffset B(1, MVT::i32);
53 StackOffset C = A - B;
54 EXPECT_EQ(4, C.getBytes());
55
56 StackOffset D(1, MVT::i64);
57 D -= A;
58 EXPECT_EQ(0, D.getBytes());
Sander de Smalen4f99b6f2019-10-03 11:33:50 +000059
60 C += StackOffset(2, MVT::nxv1i32);
61 StackOffset E = StackOffset(1, MVT::nxv1i32);
62 StackOffset F = C - E;
63 EXPECT_EQ(4, F.getBytes());
64 EXPECT_EQ(4, F.getScalableBytes());
Sander de Smalen612b0382019-08-06 13:06:40 +000065}
66
67TEST(StackOffset, isZero) {
68 StackOffset A(0, MVT::i64);
69 StackOffset B(0, MVT::i32);
70 EXPECT_TRUE(!A);
71 EXPECT_TRUE(!(A + B));
Sander de Smalen4f99b6f2019-10-03 11:33:50 +000072
73 StackOffset C(0, MVT::nxv1i32);
74 EXPECT_TRUE(!(A + C));
75
76 StackOffset D(1, MVT::nxv1i32);
77 EXPECT_FALSE(!(A + D));
78}
79
80TEST(StackOffset, isValid) {
81 EXPECT_FALSE(StackOffset(1, MVT::nxv8i1).isValid());
82 EXPECT_TRUE(StackOffset(2, MVT::nxv8i1).isValid());
83
84#ifndef NDEBUG
85#ifdef GTEST_HAS_DEATH_TEST
86 EXPECT_DEATH(StackOffset(1, MVT::i1),
87 "Offset type is not a multiple of bytes");
88 EXPECT_DEATH(StackOffset(1, MVT::nxv1i1),
89 "Offset type is not a multiple of bytes");
90#endif // defined GTEST_HAS_DEATH_TEST
91#endif // not defined NDEBUG
Sander de Smalen612b0382019-08-06 13:06:40 +000092}
93
94TEST(StackOffset, getForFrameOffset) {
95 StackOffset A(1, MVT::i64);
96 StackOffset B(1, MVT::i32);
Sander de Smalen4f99b6f2019-10-03 11:33:50 +000097 StackOffset C(1, MVT::nxv4i32);
98
99 // If all offsets can be materialized with only ADDVL,
100 // make sure PLSized is 0.
101 int64_t ByteSized, VLSized, PLSized;
102 (A + B + C).getForFrameOffset(ByteSized, PLSized, VLSized);
Sander de Smalen612b0382019-08-06 13:06:40 +0000103 EXPECT_EQ(12, ByteSized);
Sander de Smalen4f99b6f2019-10-03 11:33:50 +0000104 EXPECT_EQ(1, VLSized);
105 EXPECT_EQ(0, PLSized);
106
107 // If we need an ADDPL to materialize the offset, and the number of scalable
108 // bytes fits the ADDPL immediate, fold the scalable bytes to fit in PLSized.
109 StackOffset D(1, MVT::nxv16i1);
110 (C + D).getForFrameOffset(ByteSized, PLSized, VLSized);
111 EXPECT_EQ(0, ByteSized);
112 EXPECT_EQ(0, VLSized);
113 EXPECT_EQ(9, PLSized);
114
115 StackOffset E(4, MVT::nxv4i32);
116 StackOffset F(1, MVT::nxv16i1);
117 (E + F).getForFrameOffset(ByteSized, PLSized, VLSized);
118 EXPECT_EQ(0, ByteSized);
119 EXPECT_EQ(0, VLSized);
120 EXPECT_EQ(33, PLSized);
121
122 // If the offset requires an ADDPL instruction to materialize, and would
123 // require more than two instructions, decompose it into both
124 // ADDVL (n x 16 bytes) and ADDPL (n x 2 bytes) instructions.
125 StackOffset G(8, MVT::nxv4i32);
126 StackOffset H(1, MVT::nxv16i1);
127 (G + H).getForFrameOffset(ByteSized, PLSized, VLSized);
128 EXPECT_EQ(0, ByteSized);
129 EXPECT_EQ(8, VLSized);
130 EXPECT_EQ(1, PLSized);
Sander de Smalen612b0382019-08-06 13:06:40 +0000131}