dirkwhoffmann / vAmiga

vAmiga is a user-friendly Amiga 500, 1000, 2000 emulator for macOS
https://dirkwhoffmann.github.io/vAmiga
Other
293 stars 24 forks source link

cputester (68010) #742

Closed dirkwhoffmann closed 1 year ago

dirkwhoffmann commented 1 year ago

I've started running timing tests with cputester on my latest 68010 core (file simple_010.hdf with option -cylces). It'll reveal some issues that are not covered by my color stripe tests.

DIVS is the first one to fail:

Bildschirmfoto 2022-10-16 um 13 55 07
dirkwhoffmann commented 1 year ago

Milestone reached: Passing test suite simple_010.hdf with cputest all -cycles.

Bildschirmfoto 2022-10-21 um 12 04 25

Next step: Fix loop mode timing

dirkwhoffmann commented 1 year ago

Next milestone reached: Passing test suite LOOPn_010.hdf with cputest all -cycles.

Next step: Fix address error handling. AEDST_010.hdf fails right away 🙈:

Bildschirmfoto 2022-10-22 um 15 30 43
dirkwhoffmann commented 1 year ago

My latest code writes all the relevant data to the stack correctly (SR, PC, fault address, etc.).

Bildschirmfoto 2022-10-22 um 19 29 11

However, cputester also checks the values of the undocumented stack entries (the entire stack frame comprises 29 words). Does anybody know where the 68010 address error stack frame is created in the UAE source code?

dirkwhoffmann commented 1 year ago

For reference (from the UAE source code, newcpu.cpp). Explains write order and timing:

68010 Address/Bus Error:

- [memory access causing bus/address error]
- 8 idle cycles (+4 if bus error)
- write word 28
- write word 26
- write word 27
- write word 25
- write word 23
- write word 24
- write word 22
- write word 21
- write word 20
- write word 19
- write word 18
- write word 17
- write word 16
- write word 15
- write word 13
- write word 14
- write instruction buffer
- (skipped)
- write data input buffer
- (skipped)
- write data output buffer
- (skipped)
- write fault address low word
- write fault address high word
- write special status word
- write PC low word
- write SR
- write PC high word
- write frame format
- read exception address high word
- read exception address low word
- prefetch
- 2 idle cycles
- prefetch

Creation code:

// 68010 bus/address error (partially implemented only)
uae_u16 in = regs.read_buffer;
uae_u16 out = regs.write_buffer;
uae_u16 ssw = (sv ? 4 : 0) | last_fc_for_exception_3;
ssw |= last_di_for_exception_3 > 0 ? 0x0000 : (last_di_for_exception_3 < 0 ? (0x2000 | 0x1000) : 0x2000);
ssw |= (!last_writeaccess_for_exception_3 && last_di_for_exception_3) ? 0x1000 : 0x000; // DF
ssw |= (last_op_for_exception_3 & 0x10000) ? 0x0400 : 0x0000; // HB
ssw |= last_size_for_exception_3 == 0 ? 0x0200 : 0x0000; // BY
ssw |= last_writeaccess_for_exception_3 ? 0 : 0x0100; // RW
if (last_op_for_exception_3 & 0x20000)
ssw &= 0x00ff;
m68k_areg(regs, 7) -= (29 - 4) * 2;
exception_in_exception = -1;
frame_id = 8;
for (int i = 0; i < 15; i++) {
    x_put_word(m68k_areg(regs, 7) + 20 + i * 2, ((i + 1) << 8) | ((i + 2) << 0));
}
x_put_word(m68k_areg(regs, 7) + 18, 0); // version
x_put_word(m68k_areg(regs, 7) + 16, regs.irc); // instruction input buffer
x_put_word(m68k_areg(regs, 7) + 12, in); // data input buffer
x_put_word(m68k_areg(regs, 7) + 8, out); // data output buffer
x_put_word(m68k_areg(regs, 7) + 4, last_fault_for_exception_3); // fault addr
x_put_word(m68k_areg(regs, 7) + 2, last_fault_for_exception_3 >> 16);
x_put_word(m68k_areg(regs, 7) + 0, ssw); // ssw

MC68010/MC68012 data sheet (page 5-13):

Bildschirmfoto 2022-10-23 um 15 01 26
dirkwhoffmann commented 1 year ago

Closed as completed.