OpenCores
URL https://opencores.org/ocsvn/s80186/s80186/trunk

Subversion Repositories s80186

[/] [s80186/] [trunk/] [tests/] [instructions/] [TestString.cpp] - Blame information for rev 2

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 2 jamieiles
// Copyright Jamie Iles, 2017
2
//
3
// This file is part of s80x86.
4
//
5
// s80x86 is free software: you can redistribute it and/or modify
6
// it under the terms of the GNU General Public License as published by
7
// the Free Software Foundation, either version 3 of the License, or
8
// (at your option) any later version.
9
//
10
// s80x86 is distributed in the hope that it will be useful,
11
// but WITHOUT ANY WARRANTY; without even the implied warranty of
12
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
// GNU General Public License for more details.
14
//
15
// You should have received a copy of the GNU General Public License
16
// along with s80x86.  If not, see <http://www.gnu.org/licenses/>.
17
 
18
#include <gtest/gtest.h>
19
 
20
#include "EmulateFixture.h"
21
#include "Flags.h"
22
 
23
TEST_F(EmulateFixture, ScasbNoRep)
24
{
25
    write_reg(AL, 0);
26
    write_reg(DI, 0x800);
27
    write_reg(CX, 0xff);
28
    write_cstring(0x800, "8086", ES);
29
 
30
    // repne scasb
31
    set_instruction({0xae});
32
 
33
    emulate();
34
 
35
    ASSERT_EQ(read_reg(DI), 0x801);
36
    ASSERT_PRED_FORMAT2(AssertFlagsEqual, read_flags(),
37
                        FLAGS_STUCK_BITS | CF | AF | SF);
38
}
39
 
40
TEST_F(EmulateFixture, ScasbInc)
41
{
42
    write_reg(AL, 0);
43
    write_reg(DI, 0x800);
44
    write_reg(CX, 0xff);
45
    write_cstring(0x800, "8086", ES);
46
 
47
    // repne scasb
48
    set_instruction({0xf2, 0xae});
49
 
50
    emulate();
51
 
52
    ASSERT_EQ(read_reg(DI), 0x805);
53
}
54
 
55
TEST_F(EmulateFixture, ScasbDec)
56
{
57
    write_flags(DF);
58
    write_reg(AL, '1');
59
    write_reg(DI, 0x803);
60
    write_reg(CX, 0xff);
61
    write_cstring(0x800, "1234", ES);
62
 
63
    // repne scasb
64
    set_instruction({0xf2, 0xae});
65
 
66
    emulate();
67
 
68
    ASSERT_EQ(read_reg(DI), 0x7ff);
69
}
70
 
71
TEST_F(EmulateFixture, ScasbIncRepe)
72
{
73
    write_reg(AL, 'a');
74
    write_reg(DI, 0x800);
75
    write_reg(CX, 0xff);
76
    write_cstring(0x800, "aaab", ES);
77
 
78
    // repe scasb
79
    set_instruction({0xf3, 0xae});
80
 
81
    emulate();
82
 
83
    ASSERT_EQ(read_reg(DI), 0x804);
84
}
85
 
86
TEST_F(EmulateFixture, ScasbDecRepe)
87
{
88
    write_flags(DF);
89
    write_reg(AL, 'b');
90
    write_reg(DI, 0x803);
91
    write_reg(CX, 0xff);
92
    write_cstring(0x800, "abbb", ES);
93
 
94
    // repe scasb
95
    set_instruction({0xf3, 0xae});
96
 
97
    emulate();
98
 
99
    ASSERT_EQ(read_reg(DI), 0x7ff);
100
}
101
 
102
TEST_F(EmulateFixture, ScaswNoRep)
103
{
104
    write_reg(AX, 0);
105
    write_reg(DI, 0x800);
106
    write_reg(CX, 0xff);
107
 
108
    for (int i = 0; i < 2; ++i)
109
        write_mem16(0x800 + i * 2, 0xaa55, ES);
110
    write_mem16(0x800 + 2 * 2, 0x0000, ES);
111
 
112
    // scasw
113
    set_instruction({0xaf});
114
 
115
    emulate();
116
 
117
    ASSERT_EQ(read_reg(DI), 0x802);
118
    ASSERT_PRED_FORMAT2(AssertFlagsEqual, read_flags(),
119
                        FLAGS_STUCK_BITS | CF | AF);
120
}
121
 
122
TEST_F(EmulateFixture, ScaswInc)
123
{
124
    write_reg(AX, 0);
125
    write_reg(DI, 0x800);
126
    write_reg(CX, 0xff);
127
 
128
    for (int i = 0; i < 2; ++i)
129
        write_mem16(0x800 + i * 2, 0xaa55, ES);
130
    write_mem16(0x800 + 2 * 2, 0x0000, ES);
131
 
132
    // repne scasw
133
    set_instruction({0xf2, 0xaf});
134
 
135
    emulate();
136
 
137
    ASSERT_EQ(read_reg(DI), 0x806);
138
}
139
 
140
TEST_F(EmulateFixture, ScaswDec)
141
{
142
    write_flags(DF);
143
    write_reg(AX, 0);
144
    write_reg(DI, 0x806);
145
    write_reg(CX, 0xff);
146
 
147
    for (int i = 0; i < 4; ++i)
148
        write_mem16(0x800 + i * 2, 0xaa55, ES);
149
    write_mem16(0x800 + 4 * 2, 0x0000, ES);
150
    write_mem16(0x7fe, 0x0000, ES);
151
 
152
    // repne scasw
153
    set_instruction({0xf2, 0xaf});
154
 
155
    emulate();
156
 
157
    ASSERT_EQ(read_reg(DI), 0x7fc);
158
}
159
 
160
TEST_F(EmulateFixture, ScaswIncRepe)
161
{
162
    write_reg(AX, 0xaa55);
163
    write_reg(DI, 0x800);
164
    write_reg(CX, 0xff);
165
 
166
    for (int i = 0; i < 4; ++i)
167
        write_mem16(0x800 + i * 2, 0xaa55, ES);
168
 
169
    // repe scasw
170
    set_instruction({0xf3, 0xaf});
171
 
172
    emulate();
173
 
174
    ASSERT_EQ(read_reg(DI), 0x80a);
175
}
176
 
177
TEST_F(EmulateFixture, ScaswDecRepe)
178
{
179
    write_flags(DF);
180
    write_reg(AX, 0xaa55);
181
    write_reg(DI, 0x806);
182
    write_reg(CX, 0xff);
183
 
184
    for (int i = 0; i < 4; ++i)
185
        write_mem16(0x800 + i * 2, 0xaa55, ES);
186
 
187
    // repe scasw
188
    set_instruction({0xf3, 0xaf});
189
 
190
    emulate();
191
 
192
    ASSERT_EQ(read_reg(DI), 0x7fc);
193
}
194
 
195
TEST_F(EmulateFixture, MovsbInc)
196
{
197
    write_reg(AL, 0);
198
    write_reg(SI, 0x800);
199
    write_reg(DI, 0x400);
200
    write_reg(CX, 0x4);
201
    write_cstring(0x800, "8086");
202
    write_mem8(0x404, 0, ES);
203
 
204
    // repne movsb
205
    set_instruction({0xf3, 0xa4});
206
 
207
    emulate();
208
 
209
    ASSERT_EQ(read_reg(DI), 0x404);
210
    ASSERT_EQ(read_reg(SI), 0x804);
211
    ASSERT_EQ(read_cstring(0x400, ES), "8086");
212
}
213
 
214
TEST_F(EmulateFixture, MovsbDec)
215
{
216
    write_flags(DF);
217
    write_reg(AL, 0);
218
    write_reg(SI, 0x803);
219
    write_reg(DI, 0x403);
220
    write_reg(CX, 0x4);
221
    write_cstring(0x800, "8086");
222
    write_mem8(0x404, 0, ES);
223
 
224
    // repne movsb
225
    set_instruction({0xf3, 0xa4});
226
 
227
    emulate();
228
 
229
    ASSERT_EQ(read_reg(DI), 0x3ff);
230
    ASSERT_EQ(read_reg(SI), 0x7ff);
231
    ASSERT_EQ(read_cstring(0x400, ES), "8086");
232
}
233
 
234
TEST_F(EmulateFixture, MovswInc)
235
{
236
    write_reg(AL, 0);
237
    write_reg(SI, 0x800);
238
    write_reg(DI, 0x400);
239
    write_reg(CX, 0x2);
240
    write_mem16(0x800, 0xaa55);
241
    write_mem16(0x802, 0x55aa);
242
 
243
    // repne movsw
244
    set_instruction({0xf3, 0xa5});
245
 
246
    emulate();
247
 
248
    ASSERT_EQ(read_reg(DI), 0x404);
249
    ASSERT_EQ(read_reg(SI), 0x804);
250
    ASSERT_EQ(read_mem16(0x400, ES), 0xaa55);
251
    ASSERT_EQ(read_mem16(0x402, ES), 0x55aa);
252
}
253
 
254
TEST_F(EmulateFixture, MovswDec)
255
{
256
    write_flags(DF);
257
    write_reg(AL, 0);
258
    write_reg(SI, 0x802);
259
    write_reg(DI, 0x402);
260
    write_reg(CX, 0x2);
261
    write_mem16(0x800, 0xaa55);
262
    write_mem16(0x802, 0x55aa);
263
 
264
    // repne movsw
265
    set_instruction({0xf3, 0xa5});
266
 
267
    emulate();
268
 
269
    ASSERT_EQ(read_reg(DI), 0x3fe);
270
    ASSERT_EQ(read_reg(SI), 0x7fe);
271
    ASSERT_EQ(read_mem16(0x400, ES), 0xaa55);
272
    ASSERT_EQ(read_mem16(0x402, ES), 0x55aa);
273
}
274
 
275
template <typename T>
276
struct CmpsTest {
277
    std::vector<T> src;
278
    std::vector<T> dst;
279
    uint16_t expected_flags;
280
    uint8_t prefix;
281
    uint8_t expected_length;
282
};
283
 
284
using Cmps8Test = struct CmpsTest<uint8_t>;
285
using Cmps16Test = struct CmpsTest<uint16_t>;
286
 
287
class Cmps8Fixture : public EmulateFixture,
288
                     public ::testing::WithParamInterface<Cmps8Test>
289
{
290
};
291
TEST_P(Cmps8Fixture, Flags)
292
{
293
    auto p = GetParam();
294
 
295
    write_flags(0);
296
 
297
    write_reg(SI, 0x800);
298
    write_reg(DI, 0x400);
299
    write_reg(CX, std::max(p.src.size() + 1, p.dst.size() + 1));
300
 
301
    for (auto i = 0; i < 32; ++i) {
302
        write_mem8(0x400 + i, 0, ES);
303
        write_mem8(0x800 + i, 0);
304
    }
305
    write_vector8(0x800, p.src);
306
    write_vector8(0x400, p.dst, ES);
307
 
308
    set_instruction({p.prefix, 0xa6});
309
 
310
    emulate();
311
 
312
    ASSERT_PRED_FORMAT2(AssertFlagsEqual, read_flags(),
313
                        FLAGS_STUCK_BITS | p.expected_flags);
314
    ASSERT_EQ(p.expected_length, read_reg(SI) - 0x800);
315
}
316
INSTANTIATE_TEST_CASE_P(
317
    CmpsRepe,
318
    Cmps8Fixture,
319
    ::testing::Values(Cmps8Test{std::vector<uint8_t>{'f', 'o', 'o'},
320
                                std::vector<uint8_t>{'f', 'o', 'o'}, ZF | PF,
321
                                0xf3, 4},
322
                      Cmps8Test{std::vector<uint8_t>{'a'},
323
                                std::vector<uint8_t>{'b'}, SF | PF | CF | AF,
324
                                0xf3, 1},
325
                      Cmps8Test{std::vector<uint8_t>{'b'},
326
                                std::vector<uint8_t>{'a'}, 0, 0xf3, 1},
327
                      Cmps8Test{std::vector<uint8_t>{'b'},
328
                                std::vector<uint8_t>{}, 0, 0xf3, 1}));
329
INSTANTIATE_TEST_CASE_P(
330
    CmpsRepne,
331
    Cmps8Fixture,
332
    ::testing::Values(
333
        Cmps8Test{std::vector<uint8_t>{'b', 'a', 'r'},
334
                  std::vector<uint8_t>{'b', 'a', 'r'}, ZF | PF, 0xf2, 1},
335
        Cmps8Test{std::vector<uint8_t>{'b', 'a', 'r'},
336
                  std::vector<uint8_t>{'f', 'o', 'o'}, ZF | PF, 0xf2, 4},
337
        Cmps8Test{std::vector<uint8_t>{'b', 'a', 'r'},
338
                  std::vector<uint8_t>{'f', 'o', 'r'}, ZF | PF, 0xf2, 3},
339
        Cmps8Test{std::vector<uint8_t>{'b', 'a', 'r'},
340
                  std::vector<uint8_t>{'c'}, ZF | PF, 0xf2, 4}));
341
 
342
TEST_F(EmulateFixture, CmpsbDec)
343
{
344
    write_flags(DF);
345
    write_reg(SI, 0x800);
346
    write_reg(DI, 0x400);
347
 
348
    write_mem8(0x800, 'f');
349
    write_mem8(0x400, 'g', ES);
350
 
351
    set_instruction({0xa6});
352
 
353
    emulate();
354
 
355
    ASSERT_PRED_FORMAT2(AssertFlagsEqual, read_flags(),
356
                        FLAGS_STUCK_BITS | SF | PF | CF | DF | AF);
357
    ASSERT_EQ(read_reg(SI), 0x7ff);
358
    ASSERT_EQ(read_reg(DI), 0x3ff);
359
}
360
 
361
class Cmps16Fixture : public EmulateFixture,
362
                      public ::testing::WithParamInterface<Cmps16Test>
363
{
364
};
365
TEST_P(Cmps16Fixture, Flags)
366
{
367
    auto p = GetParam();
368
 
369
    write_flags(0);
370
 
371
    write_reg(SI, 0x800);
372
    write_reg(DI, 0x400);
373
    write_reg(CX, std::max(p.src.size() + 1, p.dst.size() + 1));
374
 
375
    for (auto i = 0; i < 32; ++i) {
376
        write_mem16(0x400 + i, 0, ES);
377
        write_mem16(0x800 + i, 0);
378
    }
379
    write_vector16(0x800, p.src);
380
    write_vector16(0x400, p.dst, ES);
381
 
382
    set_instruction({p.prefix, 0xa7});
383
 
384
    emulate();
385
 
386
    ASSERT_PRED_FORMAT2(AssertFlagsEqual, read_flags(),
387
                        FLAGS_STUCK_BITS | p.expected_flags);
388
    ASSERT_EQ(p.expected_length, read_reg(SI) - 0x800);
389
}
390
INSTANTIATE_TEST_CASE_P(
391
    CmpsRepe,
392
    Cmps16Fixture,
393
    ::testing::Values(Cmps16Test{std::vector<uint16_t>{0xaa55, 0xaa56, 0xaa57},
394
                                 std::vector<uint16_t>{0xaa55, 0xaa56, 0xaa57},
395
                                 ZF | PF, 0xf3, 8},
396
                      Cmps16Test{std::vector<uint16_t>{0x1000},
397
                                 std::vector<uint16_t>{0x2000}, SF | PF | CF,
398
                                 0xf3, 2},
399
                      Cmps16Test{std::vector<uint16_t>{0x2000},
400
                                 std::vector<uint16_t>{0x1000}, PF, 0xf3, 2},
401
                      Cmps16Test{std::vector<uint16_t>{0x2000},
402
                                 std::vector<uint16_t>{}, PF, 0xf3, 2}));
403
INSTANTIATE_TEST_CASE_P(
404
    CmpsRepne,
405
    Cmps16Fixture,
406
    ::testing::Values(Cmps16Test{std::vector<uint16_t>{0xaa55, 0xaa56, 0xaa57},
407
                                 std::vector<uint16_t>{0xaa55, 0xaa56, 0xaa57},
408
                                 ZF | PF, 0xf2, 2},
409
                      Cmps16Test{std::vector<uint16_t>{0xaa55, 0xaa56, 0xaa57},
410
                                 std::vector<uint16_t>{0x55aa, 0x55ab, 0x55ac},
411
                                 ZF | PF, 0xf2, 8},
412
                      Cmps16Test{std::vector<uint16_t>{0xaa55, 0xaa56, 0xaa57},
413
                                 std::vector<uint16_t>{0x55aa, 0x55aa, 0xaa57},
414
                                 ZF | PF, 0xf2, 6},
415
                      Cmps16Test{std::vector<uint16_t>{0xaa55, 0xaa56, 0xaa57},
416
                                 std::vector<uint16_t>{0x1234}, ZF | PF, 0xf2,
417
                                 8}));
418
 
419
TEST_F(EmulateFixture, CmpswDec)
420
{
421
    write_flags(DF);
422
    write_reg(SI, 0x800);
423
    write_reg(DI, 0x400);
424
 
425
    write_mem16(0x800, 0xaa55);
426
    write_mem16(0x400, 0xaa56, ES);
427
 
428
    set_instruction({0xa7});
429
 
430
    emulate();
431
 
432
    ASSERT_PRED_FORMAT2(AssertFlagsEqual, read_flags(),
433
                        FLAGS_STUCK_BITS | SF | PF | CF | DF | AF);
434
    ASSERT_EQ(read_reg(SI), 0x7fe);
435
    ASSERT_EQ(read_reg(DI), 0x3fe);
436
}
437
 
438
TEST_F(EmulateFixture, Lodsb)
439
{
440
    write_flags(0);
441
    write_reg(SI, 0x800);
442
    write_cstring(0x800, "foo");
443
    write_reg(CX, 3);
444
 
445
    set_instruction({0xf2, 0xac});
446
 
447
    emulate();
448
 
449
    ASSERT_EQ(read_reg(AL), 'o');
450
    ASSERT_EQ(read_reg(SI), 0x803);
451
}
452
 
453
TEST_F(EmulateFixture, Lodsw)
454
{
455
    write_flags(0);
456
    write_reg(SI, 0x800);
457
    write_vector16(0x800, {0x1234, 0x5678});
458
    write_reg(CX, 2);
459
 
460
    set_instruction({0xf2, 0xad});
461
 
462
    emulate();
463
 
464
    ASSERT_EQ(read_reg(AX), 0x5678);
465
    ASSERT_EQ(read_reg(SI), 0x804);
466
}
467
 
468
TEST_F(EmulateFixture, LodsbDec)
469
{
470
    write_flags(DF);
471
    write_reg(SI, 0x802);
472
    write_cstring(0x800, "foo");
473
    write_reg(CX, 3);
474
 
475
    set_instruction({0xf2, 0xac});
476
 
477
    emulate();
478
 
479
    ASSERT_EQ(read_reg(AL), 'f');
480
    ASSERT_EQ(read_reg(SI), 0x7ff);
481
}
482
 
483
TEST_F(EmulateFixture, LodswDec)
484
{
485
    write_flags(DF);
486
    write_reg(SI, 0x802);
487
    write_vector16(0x800, {0x1234, 0x5678});
488
    write_reg(CX, 2);
489
 
490
    set_instruction({0xf2, 0xad});
491
 
492
    emulate();
493
 
494
    ASSERT_EQ(read_reg(AX), 0x1234);
495
    ASSERT_EQ(read_reg(SI), 0x7fe);
496
}
497
 
498
TEST_F(EmulateFixture, Stosb)
499
{
500
    write_flags(0);
501
    write_reg(DI, 0x800);
502
    write_mem8(0x803, 0);
503
    write_reg(AL, 'a');
504
    write_reg(CX, 3);
505
    write_vector8(0x800, {0, 0, 0, 0, 0, 0, 0, 0}, ES);
506
 
507
    set_instruction({0xf2, 0xaa});
508
 
509
    emulate();
510
 
511
    ASSERT_EQ(read_reg(DI), 0x803);
512
    ASSERT_EQ(read_cstring(0x800, ES), "aaa");
513
}
514
 
515
TEST_F(EmulateFixture, StosbDec)
516
{
517
    write_flags(DF);
518
    write_reg(DI, 0x802);
519
    write_mem8(0x803, 0);
520
    write_reg(AL, 'a');
521
    write_reg(CX, 3);
522
 
523
    set_instruction({0xf2, 0xaa});
524
    write_vector8(0x800, {0, 0, 0, 0, 0, 0, 0, 0}, ES);
525
 
526
    emulate();
527
 
528
    ASSERT_EQ(read_reg(DI), 0x7ff);
529
    ASSERT_EQ(read_cstring(0x800, ES), "aaa");
530
}
531
 
532
TEST_F(EmulateFixture, Stosw)
533
{
534
    write_flags(0);
535
    write_reg(DI, 0x800);
536
    write_reg(AX, 0x6261);
537
    write_mem16(0x806, 0x0000);
538
    write_reg(CX, 3);
539
    write_vector16(0x800, {0, 0, 0, 0, 0, 0, 0, 0}, ES);
540
 
541
    set_instruction({0xf2, 0xab});
542
 
543
    emulate();
544
 
545
    ASSERT_EQ(read_reg(DI), 0x806);
546
    ASSERT_EQ(read_cstring(0x800, ES), "ababab");
547
}
548
 
549
TEST_F(EmulateFixture, StoswDec)
550
{
551
    write_flags(DF);
552
    write_reg(DI, 0x804);
553
    write_mem16(0x806, 0x0000);
554
    write_reg(AX, 0x6261);
555
    write_reg(CX, 3);
556
    write_vector16(0x800, {0, 0, 0, 0, 0, 0, 0, 0}, ES);
557
 
558
    set_instruction({0xf2, 0xab});
559
 
560
    emulate();
561
 
562
    ASSERT_EQ(read_reg(DI), 0x7fe);
563
    ASSERT_EQ(read_cstring(0x800, ES), "ababab");
564
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.