From 3b56312d9c9652f206e6f0394ad2ce9e76eb6520 Mon Sep 17 00:00:00 2001 From: Ivan Izaguirre Date: Sat, 24 Jul 2021 19:41:53 +0200 Subject: [PATCH] Simpler approach for Applecorn trace, no reentrancy --- traceApplecorn.go | 79 +++++++++++++++++++++-------------------------- 1 file changed, 36 insertions(+), 43 deletions(-) diff --git a/traceApplecorn.go b/traceApplecorn.go index f5e932d..fb88e7b 100644 --- a/traceApplecorn.go +++ b/traceApplecorn.go @@ -2,7 +2,6 @@ package izapple2 import ( "fmt" - "strings" ) /* @@ -19,19 +18,20 @@ type traceApplecorn struct { a *Apple2 skipConsole bool osbyteNames [256]string - calls []mosCallData + call mosCallData lastDepth int + wasInKernel bool } type mosCallData struct { - caller uint16 api uint16 a, x, y uint8 + skipLog bool } const ( - applecornMosVec uint16 = 0xffb9 // Start of the MOS entry points - applecornNoCaller uint16 = 0xffff + applecornKernelStart uint16 = 0xc000 // Code above this is out of BBC territory + applecornNoCaller uint16 = 0xffff ) func newTraceApplecorn(a *Apple2, skipConsole bool) *traceApplecorn { @@ -48,16 +48,17 @@ func newTraceApplecorn(a *Apple2, skipConsole bool) *traceApplecorn { t.osbyteNames[0x85] = "top user mem for mode" t.osbyteNames[0x86] = "read cursor pos" t.osbyteNames[0xDA] = "clear VDU queue" - t.calls = make([]mosCallData, 0) return &t } func (t *traceApplecorn) inspect() { - pc, sp := t.a.cpu.GetPCAndSP() - if pc >= 0xd000 /*applecornMosVec*/ { - regA, regX, regY := t.a.cpu.GetAXY() + pc, _ := t.a.cpu.GetPCAndSP() + inKernel := pc >= applecornKernelStart - s := "" + if !t.wasInKernel && inKernel { + regA, regX, regY, _ := t.a.cpu.GetAXYP() + + s := "UNKNOWN" skip := false // Page 2 vectors @@ -123,17 +124,15 @@ func (t *traceApplecorn) inspect() { case 0xffe0: s = fmt.Sprintf("OSRDCH()") skip = t.skipConsole - /* - case 0xffe3: // This fallbacks to OSWRCH - s = "OSASCI(?)" - skip = t.skipConsole - case 0xffe7: // This fallbacks to OSWRCH - s = fmt.Sprintf("OSNEWL()") - skip = t.skipConsole - case 0xffec: // This fallbacks to OSWRCH - skip = t.skipConsole - s = fmt.Sprintf("OSNECR()") - */ + case 0xffe3: // This fallbacks to OSWRCH + s = "OSASCI(?)" + skip = t.skipConsole + case 0xffe7: // This fallbacks to OSWRCH + s = fmt.Sprintf("OSNEWL()") + skip = t.skipConsole + case 0xffec: // This fallbacks to OSWRCH + skip = t.skipConsole + s = fmt.Sprintf("OSNECR()") case 0xffee: ch := "" if regA >= 0x20 && regA < 0x7f { @@ -153,48 +152,42 @@ func (t *traceApplecorn) inspect() { } case 0xfff4: s = fmt.Sprintf("OSBYTE('%s';A=%02x,X=%02x,Y=%02x)", t.osbyteNames[regA], regA, regX, regY) - //if regA == 0xda { - // t.a.cpu.Reset() - //} case 0xfff7: s = "OSCLI(?)" } - if !skip && s != "" { - caller := t.a.mmu.peekWord(0x100+uint16(sp+1)) + 1 - t.calls = append(t.calls, mosCallData{caller, pc, regA, regX, regY}) - if len(t.calls) > t.lastDepth { - // Reentrant call, first of block - fmt.Println() - } - if len(t.calls) > 1 { - // Reentrant call - fmt.Printf("%s", strings.Repeat(" ", len(t.calls))) - } + t.call.api = pc + t.call.a = regA + t.call.x = regX + t.call.y = regY + t.call.skipLog = skip + if !skip { fmt.Printf("BBC MOS call to $%04x %s ", pc, s) - t.lastDepth = len(t.calls) } } - if len(t.calls) > 0 && pc == t.calls[len(t.calls)-1].caller { + if t.wasInKernel && !inKernel && !t.call.skipLog { // Returning from the call - regA, regX, regY := t.a.cpu.GetAXY() - call := t.calls[len(t.calls)-1] + regA, regX, regY, _ := t.a.cpu.GetAXYP() s := "" - switch call.api { + switch t.call.api { case 0xfff1: // OSWORD - cbAddress := uint16(call.x) + uint16(call.y)<<8 - switch call.a { + cbAddress := uint16(t.call.x) + uint16(t.call.y)<<8 + switch t.call.a { case 0: // Read line from input lineAddress := t.a.mmu.peekWord(cbAddress) line := t.getString(lineAddress, regY) s = fmt.Sprintf(",line='%s'", line) + + t.a.cpu.SetTrace(true) + } } fmt.Printf("=> (A=%02x,X=%02x,Y=%02x%s)\n", regA, regX, regY, s) - t.calls = t.calls[:len(t.calls)-1] } + + t.wasInKernel = inKernel } func (t *traceApplecorn) getString(address uint16, length uint8) string {