tests: Delete authors lists from test files.
[gem5.git] / tests / test-progs / insttest / src / riscv / rv64c.cpp
1 /*
2 * Copyright (c) 2017 The University of Virginia
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are
7 * met: redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer;
9 * redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution;
12 * neither the name of the copyright holders nor the names of its
13 * contributors may be used to endorse or promote products derived from
14 * this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
17 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
18 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
19 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
20 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
26 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 */
28
29 #include <limits>
30
31 #include "insttest.h"
32 #include "rv64c.h"
33 #include "rv64d.h"
34
35 int main()
36 {
37 using namespace insttest;
38 using namespace std;
39
40 // C.LWSP
41 expect<bool>(true, []{
42 uint64_t lw = 0, lwsp = -1;
43 int64_t i = 16;
44 asm volatile("lw %0,%2(sp);"
45 "c.lwsp %1,%2(sp);"
46 : "=r" (lw), "=r" (lwsp)
47 : "i" (i));
48 return lw == lwsp;
49 }, "c.lwsp");
50
51 // C.LDSP
52 expect<bool>(true, []{
53 uint64_t ld = 0, ldsp = -1;
54 int64_t i = 8;
55 asm volatile("ld %0,%2(sp);"
56 "c.ldsp %1,%2(sp);"
57 : "=r" (ld), "=r" (ldsp)
58 : "i" (i));
59 return ld == ldsp;
60 }, "c.ldsp");
61
62 // C.FLDSP
63 expect<bool>(true, []{
64 double fld = 0.0, fldsp = -1.0;
65 int64_t i = 32;
66 asm volatile("fld %0,%2(sp);"
67 "c.fldsp %1,%2(sp);"
68 : "=f" (fld), "=f" (fldsp)
69 : "i" (i));
70 return D::bits(fld) == D::bits(fldsp);
71 }, "c.fldsp");
72
73 // C.SWSP
74 expect<bool>(true, []{
75 int64_t value = -1, result = 0;
76 asm volatile("addi sp,sp,-8;"
77 "c.swsp %1,8(sp);"
78 "lw %0,8(sp);"
79 "addi sp,sp,8;"
80 : "=r" (result)
81 : "r" (value)
82 : "memory");
83 return value == result;
84 }, "c.swsp");
85
86 // C.SDSP
87 expect<bool>(true, []{
88 int64_t value = -1, result = 0;
89 asm volatile("addi sp,sp,-8;"
90 "c.sdsp %1,8(sp);"
91 "ld %0,8(sp);"
92 "addi sp,sp,8;"
93 : "=r" (result)
94 : "r" (value)
95 : "memory");
96 return value == result;
97 }, "c.sdsp");
98
99 // C.FSDSP
100 expect<bool>(true, []{
101 double value = 0.1, result = numeric_limits<double>::signaling_NaN();
102 asm volatile("addi sp,sp,-8;"
103 "c.fsdsp %1,8(sp);"
104 "fld %0,8(sp);"
105 "addi sp,sp,8;"
106 : "=f" (result)
107 : "f" (value)
108 : "memory");
109 return value == result;
110 }, "c.fsdsp");
111
112 // C.LW, C.LD, C.FLD
113 expect<int64_t>(458752,
114 []{return C::c_load<int32_t, int64_t>(0x00070000);},
115 "c.lw, positive");
116 expect<int64_t>(numeric_limits<int32_t>::min(),
117 []{return C::c_load<int32_t, int64_t>(0x80000000);},
118 "c.lw, negative");
119 expect<int64_t>(30064771072,
120 []{return C::c_load<int64_t, int64_t>(30064771072);}, "c.ld");
121 expect<double>(3.1415926, []{return C::c_load<double, double>(3.1415926);},
122 "c.fld");
123
124 // C.SW, C.SD, C.FSD
125 expect<uint32_t>(0xFFFFFFFF, []{return C::c_store<int32_t>(-1);}, "c.sw");
126 expect<uint64_t>(-1, []{return C::c_store<int64_t>(-1);}, "c.sd");
127 expect<double>(1.61803398875,
128 []{return C::c_store<double>(1.61803398875);}, "c.fsd");
129
130 // C.J, C.JR, C.JALR
131 expect<bool>(true, []{return C::c_j();}, "c.j");
132 expect<bool>(true, []{return C::c_jr();}, "c.jr");
133 expect<bool>(true, []{return C::c_jalr();}, "c.jalr");
134
135 // C.BEQZ
136 expect<bool>(true, []{return C::c_beqz(0);}, "c.beqz, zero");
137 expect<bool>(false, []{return C::c_beqz(7);}, "c.beqz, not zero");
138
139 // C.BNEZ
140 expect<bool>(true, []{return C::c_bnez(15);}, "c.bnez, not zero");
141 expect<bool>(false, []{return C::c_bnez(0);}, "c.bnez, zero");
142
143 // C.LI
144 expect<int64_t>(1, []{return C::c_li(1);}, "c.li");
145 expect<int64_t>(-1, []{return C::c_li(-1);}, "c.li, sign extend");
146
147 // C.LUI
148 expect<int64_t>(4096, []{return C::c_lui(1);}, "c.lui");
149 // Note that sign extension can't be tested here because apparently the
150 // compiler doesn't allow the 6th (sign) bit of the immediate to be 1
151
152 // C.ADDI
153 expect<int64_t>(15, []{return C::c_addi(7, 8);}, "c.addi");
154
155 // C.ADDIW
156 expect<int64_t>(15, []{return C::c_addiw(8, 7);}, "c.addiw");
157 expect<int64_t>(1, []{return C::c_addiw(0xFFFFFFFF, 2);},
158 "c.addiw, overflow");
159 expect<int64_t>(1, []{return C::c_addiw(0x100000001, 0);},
160 "c.addiw, truncate");
161
162 // C.ADDI16SP
163 expect<bool>(true, []{
164 uint64_t sp = 0, rd = 0;
165 const int16_t i = 4;
166 asm volatile("mv %0,sp;"
167 "c.addi16sp sp,%2;"
168 "mv %1,sp;"
169 "mv sp,%0;"
170 : "+r" (sp), "=r" (rd)
171 : "i" (i*16));
172 return rd == sp + i*16;
173 }, "c.addi16sp");
174
175 // C.ADDI4SPN
176 expect<bool>(true, []{
177 uint64_t sp = 0, rd = 0;
178 const int16_t i = 3;
179 asm volatile("mv %0,sp;"
180 "c.addi4spn %1,sp,%2;"
181 : "=r" (sp), "=r" (rd)
182 : "i" (i*4));
183 return rd == sp + i*4;
184 }, "c.addi4spn");
185
186 // C.SLLI
187 expect<uint64_t>(16, []{return C::c_slli(1, 4);}, "c.slli");
188 expect<uint64_t>(0, []{return C::c_slli(8, 61);}, "c.slli, overflow");
189
190 // C.SRLI
191 expect<uint64_t>(4, []{return C::c_srli(128, 5);}, "c.srli");
192 expect<uint64_t>(0, []{return C::c_srli(128, 8);}, "c.srli, overflow");
193 expect<uint64_t>(1, []{return C::c_srli(-1, 63);}, "c.srli, -1");
194
195 // C.SRAI
196 expect<uint64_t>(4, []{return C::c_srai(128, 5);}, "c.srai");
197 expect<uint64_t>(0, []{return C::c_srai(128, 8);}, "c.srai, overflow");
198 expect<uint64_t>(-1, []{return C::c_srai(-2, 63);}, "c.srai, -1");
199
200 // C.ANDI
201 expect<uint64_t>(0, []{return C::c_andi(-1, 0);}, "c.andi (0)");
202 expect<uint64_t>(0x1234567812345678ULL,
203 []{return C::c_andi(0x1234567812345678ULL, -1);}, "c.andi (1)");
204
205 // C.MV
206 expect<int64_t>(1024, []{return C::c_mv(1024);}, "c.mv");
207
208 // C.ADD
209 expect<int64_t>(15, []{return C::c_add(10, 5);}, "c.add");
210
211 // C.AND
212 expect<uint64_t>(0, []{return C::c_and(-1, 0);}, "c.and (0)");
213 expect<uint64_t>(0x1234567812345678ULL,
214 []{return C::c_and(0x1234567812345678ULL, -1);}, "c.and (-1)");
215
216 // C.OR
217 expect<uint64_t>(-1,
218 []{return C::c_or(0xAAAAAAAAAAAAAAAAULL,
219 0x5555555555555555ULL);},
220 "c.or (1)");
221 expect<uint64_t>(0xAAAAAAAAAAAAAAAAULL,
222 []{return C::c_or(0xAAAAAAAAAAAAAAAAULL,
223 0xAAAAAAAAAAAAAAAAULL);},
224 "c.or (A)");
225
226 // C.XOR
227 expect<uint64_t>(-1,
228 []{return C::c_xor(0xAAAAAAAAAAAAAAAAULL,
229 0x5555555555555555ULL);},
230 "c.xor (1)");
231 expect<uint64_t>(0,
232 []{return C::c_xor(0xAAAAAAAAAAAAAAAAULL,
233 0xAAAAAAAAAAAAAAAAULL);},
234 "c.xor (0)");
235
236 // C.SUB
237 expect<int64_t>(65535, []{return C::c_sub(65536, 1);}, "c.sub");
238
239 // C.ADDW
240 expect<int64_t>(1073742078, []{return C::c_addw(0x3FFFFFFF, 255);},
241 "c.addw");
242 expect<int64_t>(-1, []{return C::c_addw(0x7FFFFFFF, 0x80000000);},
243 "c.addw, overflow");
244 expect<int64_t>(65536, []{return C::c_addw(0xFFFFFFFF0000FFFFLL, 1);},
245 "c.addw, truncate");
246
247 // C.SUBW
248 expect<int64_t>(65535, []{return C::c_subw(65536, 1);}, "c.subw");
249 expect<int64_t>(-1, []{return C::c_subw(0x7FFFFFFF, 0x80000000);},
250 "c.subw, \"overflow\"");
251 expect<int64_t>(0,
252 []{return C::c_subw(0xAAAAAAAAFFFFFFFFULL,0x55555555FFFFFFFFULL);},
253 "c.subw, truncate");
254 }