lib/std/arch/rv64/tests.rad 15.7 KiB raw
1
//! RV64I+M instruction encoding tests.
2
//!
3
//! These tests verify that instruction encodings match the RISC-V specification
4
//! by comparing against known-good values.
5
6
use std::testing;
7
use super::encode;
8
9
/// Helper to check encoding equals expected value.
10
fn expectEncoding(actual: u32, expected: u32) throws (testing::TestError) {
11
    try testing::expect(actual == expected);
12
}
13
14
///////////////////////
15
// R-type ALU tests  //
16
///////////////////////
17
18
@test fn testEncodeAdd() throws (testing::TestError) {
19
    let enc = encode::add(super::reg(1), super::reg(2), super::reg(3));
20
    try expectEncoding(enc, 0x003100B3);
21
}
22
23
@test fn testEncodeSub() throws (testing::TestError) {
24
    let enc = encode::sub(super::reg(5), super::reg(6), super::reg(7));
25
    try expectEncoding(enc, 0x407302B3);
26
}
27
28
@test fn testEncodeSll() throws (testing::TestError) {
29
    let enc = encode::sll(super::reg(1), super::reg(2), super::reg(3));
30
    try expectEncoding(enc, 0x003110B3);
31
}
32
33
@test fn testEncodeSlt() throws (testing::TestError) {
34
    let enc = encode::slt(super::reg(1), super::reg(2), super::reg(3));
35
    try expectEncoding(enc, 0x003120B3);
36
}
37
38
@test fn testEncodeSltu() throws (testing::TestError) {
39
    let enc = encode::sltu(super::reg(1), super::reg(2), super::reg(3));
40
    try expectEncoding(enc, 0x003130B3);
41
}
42
43
@test fn testEncodeXor() throws (testing::TestError) {
44
    let enc = encode::xor(super::reg(1), super::reg(2), super::reg(3));
45
    try expectEncoding(enc, 0x003140B3);
46
}
47
48
@test fn testEncodeSrl() throws (testing::TestError) {
49
    let enc = encode::srl(super::reg(1), super::reg(2), super::reg(3));
50
    try expectEncoding(enc, 0x003150B3);
51
}
52
53
@test fn testEncodeSra() throws (testing::TestError) {
54
    let enc = encode::sra(super::reg(1), super::reg(2), super::reg(3));
55
    try expectEncoding(enc, 0x403150B3);
56
}
57
58
@test fn testEncodeOr() throws (testing::TestError) {
59
    let enc = encode::or_(super::reg(1), super::reg(2), super::reg(3));
60
    try expectEncoding(enc, 0x003160B3);
61
}
62
63
@test fn testEncodeAnd() throws (testing::TestError) {
64
    let enc = encode::and_(super::reg(1), super::reg(2), super::reg(3));
65
    try expectEncoding(enc, 0x003170B3);
66
}
67
68
///////////////////////
69
// I-type ALU tests  //
70
///////////////////////
71
72
@test fn testEncodeAddi() throws (testing::TestError) {
73
    let enc = encode::addi(super::reg(1), super::ZERO, 42);
74
    try expectEncoding(enc, 0x02A00093);
75
}
76
77
@test fn testEncodeAddiNegative() throws (testing::TestError) {
78
    let enc = encode::addi(super::reg(1), super::ZERO, -1);
79
    try expectEncoding(enc, 0xFFF00093);
80
}
81
82
@test fn testEncodeSlti() throws (testing::TestError) {
83
    let enc = encode::slti(super::reg(1), super::reg(2), 100);
84
    try expectEncoding(enc, 0x06412093);
85
}
86
87
@test fn testEncodeSltiu() throws (testing::TestError) {
88
    let enc = encode::sltiu(super::reg(1), super::reg(2), 100);
89
    try expectEncoding(enc, 0x06413093);
90
}
91
92
@test fn testEncodeXori() throws (testing::TestError) {
93
    let enc = encode::xori(super::reg(1), super::reg(2), 0xFF);
94
    try expectEncoding(enc, 0x0FF14093);
95
}
96
97
@test fn testEncodeOri() throws (testing::TestError) {
98
    let enc = encode::ori(super::reg(1), super::reg(2), 0xFF);
99
    try expectEncoding(enc, 0x0FF16093);
100
}
101
102
@test fn testEncodeAndi() throws (testing::TestError) {
103
    let enc = encode::andi(super::reg(1), super::reg(2), 0xFF);
104
    try expectEncoding(enc, 0x0FF17093);
105
}
106
107
@test fn testEncodeSlli() throws (testing::TestError) {
108
    let enc = encode::slli(super::reg(1), super::reg(2), 5);
109
    try expectEncoding(enc, 0x00511093);
110
}
111
112
@test fn testEncodeSrli() throws (testing::TestError) {
113
    let enc = encode::srli(super::reg(1), super::reg(2), 5);
114
    try expectEncoding(enc, 0x00515093);
115
}
116
117
@test fn testEncodeSrai() throws (testing::TestError) {
118
    let enc = encode::srai(super::reg(1), super::reg(2), 5);
119
    try expectEncoding(enc, 0x40515093);
120
}
121
122
//////////////////
123
// Load tests   //
124
//////////////////
125
126
@test fn testEncodeLb() throws (testing::TestError) {
127
    let enc = encode::lb(super::reg(1), super::reg(2), 8);
128
    try expectEncoding(enc, 0x00810083);
129
}
130
131
@test fn testEncodeLh() throws (testing::TestError) {
132
    let enc = encode::lh(super::reg(1), super::reg(2), 8);
133
    try expectEncoding(enc, 0x00811083);
134
}
135
136
@test fn testEncodeLw() throws (testing::TestError) {
137
    let enc = encode::lw(super::reg(1), super::reg(2), 8);
138
    try expectEncoding(enc, 0x00812083);
139
}
140
141
@test fn testEncodeLbu() throws (testing::TestError) {
142
    let enc = encode::lbu(super::reg(1), super::reg(2), 8);
143
    try expectEncoding(enc, 0x00814083);
144
}
145
146
@test fn testEncodeLhu() throws (testing::TestError) {
147
    let enc = encode::lhu(super::reg(1), super::reg(2), 8);
148
    try expectEncoding(enc, 0x00815083);
149
}
150
151
@test fn testEncodeLwu() throws (testing::TestError) {
152
    let enc = encode::lwu(super::reg(1), super::reg(2), 8);
153
    try expectEncoding(enc, 0x00816083);
154
}
155
156
@test fn testEncodeLd() throws (testing::TestError) {
157
    let enc = encode::ld(super::reg(1), super::reg(2), 8);
158
    try expectEncoding(enc, 0x00813083);
159
}
160
161
//////////////////
162
// Store tests  //
163
//////////////////
164
165
@test fn testEncodeSb() throws (testing::TestError) {
166
    let enc = encode::sb(super::reg(3), super::reg(2), 8);
167
    try expectEncoding(enc, 0x00310423);
168
}
169
170
@test fn testEncodeSh() throws (testing::TestError) {
171
    let enc = encode::sh(super::reg(3), super::reg(2), 8);
172
    try expectEncoding(enc, 0x00311423);
173
}
174
175
@test fn testEncodeSw() throws (testing::TestError) {
176
    let enc = encode::sw(super::reg(3), super::reg(2), 8);
177
    try expectEncoding(enc, 0x00312423);
178
}
179
180
@test fn testEncodeSd() throws (testing::TestError) {
181
    let enc = encode::sd(super::reg(3), super::reg(2), 8);
182
    try expectEncoding(enc, 0x00313423);
183
}
184
185
@test fn testEncodeSwNegativeOffset() throws (testing::TestError) {
186
    let enc = encode::sw(super::reg(3), super::reg(2), -4);
187
    try expectEncoding(enc, 0xFE312E23);
188
}
189
190
//////////////////
191
// Branch tests //
192
//////////////////
193
194
@test fn testEncodeBeq() throws (testing::TestError) {
195
    let enc = encode::beq(super::reg(1), super::reg(2), 8);
196
    try expectEncoding(enc, 0x00208463);
197
}
198
199
@test fn testEncodeBne() throws (testing::TestError) {
200
    let enc = encode::bne(super::reg(1), super::reg(2), 8);
201
    try expectEncoding(enc, 0x00209463);
202
}
203
204
@test fn testEncodeBlt() throws (testing::TestError) {
205
    let enc = encode::blt(super::reg(1), super::reg(2), 8);
206
    try expectEncoding(enc, 0x0020C463);
207
}
208
209
@test fn testEncodeBge() throws (testing::TestError) {
210
    let enc = encode::bge(super::reg(1), super::reg(2), 8);
211
    try expectEncoding(enc, 0x0020D463);
212
}
213
214
@test fn testEncodeBltu() throws (testing::TestError) {
215
    let enc = encode::bltu(super::reg(1), super::reg(2), 8);
216
    try expectEncoding(enc, 0x0020E463);
217
}
218
219
@test fn testEncodeBgeu() throws (testing::TestError) {
220
    let enc = encode::bgeu(super::reg(1), super::reg(2), 8);
221
    try expectEncoding(enc, 0x0020F463);
222
}
223
224
@test fn testEncodeBranchNegative() throws (testing::TestError) {
225
    let enc = encode::beq(super::reg(1), super::reg(2), -8);
226
    try expectEncoding(enc, 0xFE208CE3);
227
}
228
229
//////////////////
230
// Jump tests   //
231
//////////////////
232
233
@test fn testEncodeJal() throws (testing::TestError) {
234
    let enc = encode::jal(super::reg(1), 8);
235
    try expectEncoding(enc, 0x008000EF);
236
}
237
238
@test fn testEncodeJalr() throws (testing::TestError) {
239
    let enc = encode::jalr(super::reg(1), super::reg(2), 8);
240
    try expectEncoding(enc, 0x008100E7);
241
}
242
243
///////////////////////////
244
// Upper immediate tests //
245
///////////////////////////
246
247
@test fn testEncodeLui() throws (testing::TestError) {
248
    let enc = encode::lui(super::reg(1), 0x12345);
249
    try expectEncoding(enc, 0x123450B7);
250
}
251
252
@test fn testEncodeAuipc() throws (testing::TestError) {
253
    let enc = encode::auipc(super::reg(1), 0x12345);
254
    try expectEncoding(enc, 0x12345097);
255
}
256
257
//////////////////
258
// System tests //
259
//////////////////
260
261
@test fn testEncodeEcall() throws (testing::TestError) {
262
    let enc = encode::ecall();
263
    try expectEncoding(enc, 0x00000073);
264
}
265
266
@test fn testEncodeEbreak() throws (testing::TestError) {
267
    let enc = encode::ebreak();
268
    try expectEncoding(enc, 0x00100073);
269
}
270
271
/////////////////////
272
// M extension tests
273
/////////////////////
274
275
@test fn testEncodeMul() throws (testing::TestError) {
276
    let enc = encode::mul(super::reg(1), super::reg(2), super::reg(3));
277
    try expectEncoding(enc, 0x023100B3);
278
}
279
280
@test fn testEncodeMulh() throws (testing::TestError) {
281
    let enc = encode::mulh(super::reg(1), super::reg(2), super::reg(3));
282
    try expectEncoding(enc, 0x023110B3);
283
}
284
285
@test fn testEncodeMulhsu() throws (testing::TestError) {
286
    let enc = encode::mulhsu(super::reg(1), super::reg(2), super::reg(3));
287
    try expectEncoding(enc, 0x023120B3);
288
}
289
290
@test fn testEncodeMulhu() throws (testing::TestError) {
291
    let enc = encode::mulhu(super::reg(1), super::reg(2), super::reg(3));
292
    try expectEncoding(enc, 0x023130B3);
293
}
294
295
@test fn testEncodeDiv() throws (testing::TestError) {
296
    let enc = encode::div(super::reg(1), super::reg(2), super::reg(3));
297
    try expectEncoding(enc, 0x023140B3);
298
}
299
300
@test fn testEncodeDivu() throws (testing::TestError) {
301
    let enc = encode::divu(super::reg(1), super::reg(2), super::reg(3));
302
    try expectEncoding(enc, 0x023150B3);
303
}
304
305
@test fn testEncodeRem() throws (testing::TestError) {
306
    let enc = encode::rem(super::reg(1), super::reg(2), super::reg(3));
307
    try expectEncoding(enc, 0x023160B3);
308
}
309
310
@test fn testEncodeRemu() throws (testing::TestError) {
311
    let enc = encode::remu(super::reg(1), super::reg(2), super::reg(3));
312
    try expectEncoding(enc, 0x023170B3);
313
}
314
315
////////////////////////////
316
// RV64 Word operation tests
317
////////////////////////////
318
319
@test fn testEncodeAddiw() throws (testing::TestError) {
320
    let enc = encode::addiw(super::reg(1), super::reg(2), 42);
321
    try expectEncoding(enc, 0x02A1009B);
322
}
323
324
@test fn testEncodeSlliw() throws (testing::TestError) {
325
    let enc = encode::slliw(super::reg(1), super::reg(2), 5);
326
    try expectEncoding(enc, 0x0051109B);
327
}
328
329
@test fn testEncodeSrliw() throws (testing::TestError) {
330
    let enc = encode::srliw(super::reg(1), super::reg(2), 5);
331
    try expectEncoding(enc, 0x0051509B);
332
}
333
334
@test fn testEncodeSraiw() throws (testing::TestError) {
335
    let enc = encode::sraiw(super::reg(1), super::reg(2), 5);
336
    try expectEncoding(enc, 0x4051509B);
337
}
338
339
@test fn testEncodeAddw() throws (testing::TestError) {
340
    let enc = encode::addw(super::reg(1), super::reg(2), super::reg(3));
341
    try expectEncoding(enc, 0x003100BB);
342
}
343
344
@test fn testEncodeSubw() throws (testing::TestError) {
345
    let enc = encode::subw(super::reg(1), super::reg(2), super::reg(3));
346
    try expectEncoding(enc, 0x403100BB);
347
}
348
349
@test fn testEncodeSllw() throws (testing::TestError) {
350
    let enc = encode::sllw(super::reg(1), super::reg(2), super::reg(3));
351
    try expectEncoding(enc, 0x003110BB);
352
}
353
354
@test fn testEncodeSrlw() throws (testing::TestError) {
355
    let enc = encode::srlw(super::reg(1), super::reg(2), super::reg(3));
356
    try expectEncoding(enc, 0x003150BB);
357
}
358
359
@test fn testEncodeSraw() throws (testing::TestError) {
360
    let enc = encode::sraw(super::reg(1), super::reg(2), super::reg(3));
361
    try expectEncoding(enc, 0x403150BB);
362
}
363
364
@test fn testEncodeMulw() throws (testing::TestError) {
365
    let enc = encode::mulw(super::reg(1), super::reg(2), super::reg(3));
366
    try expectEncoding(enc, 0x023100BB);
367
}
368
369
@test fn testEncodeDivw() throws (testing::TestError) {
370
    let enc = encode::divw(super::reg(1), super::reg(2), super::reg(3));
371
    try expectEncoding(enc, 0x023140BB);
372
}
373
374
@test fn testEncodeDivuw() throws (testing::TestError) {
375
    let enc = encode::divuw(super::reg(1), super::reg(2), super::reg(3));
376
    try expectEncoding(enc, 0x023150BB);
377
}
378
379
@test fn testEncodeRemw() throws (testing::TestError) {
380
    let enc = encode::remw(super::reg(1), super::reg(2), super::reg(3));
381
    try expectEncoding(enc, 0x023160BB);
382
}
383
384
@test fn testEncodeRemuw() throws (testing::TestError) {
385
    let enc = encode::remuw(super::reg(1), super::reg(2), super::reg(3));
386
    try expectEncoding(enc, 0x023170BB);
387
}
388
389
/////////////////////////////////
390
// RV64 6-bit shift amount tests
391
/////////////////////////////////
392
393
@test fn testEncodeSlli64() throws (testing::TestError) {
394
    let enc = encode::slli(super::reg(1), super::reg(2), 32);
395
    try expectEncoding(enc, 0x02011093);
396
}
397
398
@test fn testEncodeSrli64() throws (testing::TestError) {
399
    let enc = encode::srli(super::reg(1), super::reg(2), 32);
400
    try expectEncoding(enc, 0x02015093);
401
}
402
403
@test fn testEncodeSrai64() throws (testing::TestError) {
404
    let enc = encode::srai(super::reg(1), super::reg(2), 32);
405
    try expectEncoding(enc, 0x42015093);
406
}
407
408
///////////////////////////
409
// Pseudo-instruction tests
410
///////////////////////////
411
412
@test fn testEncodeNop() throws (testing::TestError) {
413
    let enc = encode::nop();
414
    try expectEncoding(enc, 0x00000013);
415
}
416
417
@test fn testEncodeMv() throws (testing::TestError) {
418
    let enc = encode::mv(super::reg(1), super::reg(2));
419
    try expectEncoding(enc, 0x00010093);
420
}
421
422
@test fn testEncodeNot() throws (testing::TestError) {
423
    let enc = encode::not_(super::reg(1), super::reg(2));
424
    try expectEncoding(enc, 0xFFF14093);
425
}
426
427
@test fn testEncodeNeg() throws (testing::TestError) {
428
    let enc = encode::neg(super::reg(1), super::reg(2));
429
    try expectEncoding(enc, 0x402000B3);
430
}
431
432
@test fn testEncodeRet() throws (testing::TestError) {
433
    let enc = encode::ret();
434
    try expectEncoding(enc, 0x00008067);
435
}
436
437
@test fn testEncodeJ() throws (testing::TestError) {
438
    let enc = encode::j(8);
439
    try expectEncoding(enc, 0x0080006F);
440
}
441
442
@test fn testEncodeBle() throws (testing::TestError) {
443
    let enc = encode::ble(super::reg(1), super::reg(2), 8);
444
    try expectEncoding(enc, 0x00115463);
445
}
446
447
@test fn testEncodeBgt() throws (testing::TestError) {
448
    let enc = encode::bgt(super::reg(1), super::reg(2), 8);
449
    try expectEncoding(enc, 0x00114463);
450
}
451
452
@test fn testEncodeSeqz() throws (testing::TestError) {
453
    let enc = encode::seqz(super::reg(1), super::reg(2));
454
    try expectEncoding(enc, 0x00113093);
455
}
456
457
@test fn testEncodeSnez() throws (testing::TestError) {
458
    let enc = encode::snez(super::reg(1), super::reg(2));
459
    try expectEncoding(enc, 0x002030B3);
460
}
461
462
@test fn testEncodeBeqz() throws (testing::TestError) {
463
    let enc = encode::beqz(super::reg(1), 8);
464
    try expectEncoding(enc, 0x00008463);
465
}
466
467
@test fn testEncodeBnez() throws (testing::TestError) {
468
    let enc = encode::bnez(super::reg(1), 8);
469
    try expectEncoding(enc, 0x00009463);
470
}
471
472
@test fn testEncodeCall() throws (testing::TestError) {
473
    let enc = encode::call(8);
474
    try expectEncoding(enc, 0x008000EF);
475
}
476
477
/////////////////////////////
478
// Validation helper tests //
479
/////////////////////////////
480
481
@test fn testIsSmallImm() throws (testing::TestError) {
482
    try testing::expect(encode::isSmallImm(0));
483
    try testing::expect(encode::isSmallImm(2047));
484
    try testing::expect(encode::isSmallImm(-2048));
485
    try testing::expect(encode::isSmallImm(-1));
486
    try testing::expectNot(encode::isSmallImm(2048));
487
    try testing::expectNot(encode::isSmallImm(-2049));
488
}
489
490
@test fn testIsBranchImm() throws (testing::TestError) {
491
    try testing::expect(encode::isBranchImm(0));
492
    try testing::expect(encode::isBranchImm(8));
493
    try testing::expect(encode::isBranchImm(-8));
494
    try testing::expect(encode::isBranchImm(4094));
495
    try testing::expect(encode::isBranchImm(-4096));
496
    try testing::expectNot(encode::isBranchImm(1));     // Must be even
497
    try testing::expectNot(encode::isBranchImm(4096));  // Out of range
498
}
499
500
@test fn testIsJumpImm() throws (testing::TestError) {
501
    try testing::expect(encode::isJumpImm(0));
502
    try testing::expect(encode::isJumpImm(8));
503
    try testing::expect(encode::isJumpImm(-8));
504
    try testing::expect(encode::isJumpImm(1048574));    // Max positive even
505
    try testing::expect(encode::isJumpImm(-1048576));   // Min negative
506
    try testing::expectNot(encode::isJumpImm(1));       // Must be even
507
    try testing::expectNot(encode::isJumpImm(1048576)); // Out of range
508
}