MOS return values

This commit is contained in:
Ivan Izaguirre 2021-07-23 17:52:08 +02:00
parent 95b9d3ef05
commit b270c1c55b
3 changed files with 87 additions and 13 deletions

View File

@ -211,6 +211,15 @@ func (mmu *memoryManager) accessWrite(address uint16) memoryHandler {
return mmu.physicalROM[mmu.romPage] return mmu.physicalROM[mmu.romPage]
} }
func (mmu *memoryManager) peekWord(address uint16) uint16 {
return uint16(mmu.Peek(address)) +
uint16(mmu.Peek(address+1))<<8
//return uint16(mmu.Peek(address)) +
// 0x100*uint16(mmu.Peek(address+1))
}
// Peek returns the data on the given address // Peek returns the data on the given address
func (mmu *memoryManager) Peek(address uint16) uint8 { func (mmu *memoryManager) Peek(address uint16) uint8 {
mh := mmu.accessRead(address) mh := mmu.accessRead(address)

View File

@ -1,10 +1,14 @@
package izapple2 package izapple2
import "fmt" import (
"fmt"
"strings"
)
/* /*
See: See:
https://github.com/bobbimanners/Applecorn https://github.com/bobbimanners/Applecorn
Chapter 45 https://raw.githubusercontent.com/bobbimanners/Applecorn/main/Manuals/Acorn%20BBC%20Micro%20User%20Guide.pdf
http://beebwiki.mdfs.net/Category:MOS_API http://beebwiki.mdfs.net/Category:MOS_API
http://beebwiki.mdfs.net/OSBYTEs http://beebwiki.mdfs.net/OSBYTEs
http://mdfs.net/Docs/Comp/BBC/Osbyte00 http://mdfs.net/Docs/Comp/BBC/Osbyte00
@ -15,10 +19,18 @@ type traceApplecorn struct {
a *Apple2 a *Apple2
skipConsole bool skipConsole bool
osbyteNames [256]string osbyteNames [256]string
calls []mosCallData
}
type mosCallData struct {
caller uint16
api uint16
a, x, y uint8
} }
const ( const (
applecornMosVec uint16 = 0xffb9 // Start of the MOS entry points applecornMosVec uint16 = 0xffb9 // Start of the MOS entry points
applecornNoCaller uint16 = 0xffff
) )
func newTraceApplecorn(a *Apple2, skipConsole bool) *traceApplecorn { func newTraceApplecorn(a *Apple2, skipConsole bool) *traceApplecorn {
@ -35,20 +47,17 @@ func newTraceApplecorn(a *Apple2, skipConsole bool) *traceApplecorn {
t.osbyteNames[0x85] = "top user mem for mode" t.osbyteNames[0x85] = "top user mem for mode"
t.osbyteNames[0x86] = "read cursor pos" t.osbyteNames[0x86] = "read cursor pos"
t.osbyteNames[0xDA] = "clear VDU queue" t.osbyteNames[0xDA] = "clear VDU queue"
t.calls = make([]mosCallData, 0)
return &t return &t
} }
func (t *traceApplecorn) inspect() { func (t *traceApplecorn) inspect() {
pc, _ := t.a.cpu.GetPCAndSP() pc, sp := t.a.cpu.GetPCAndSP()
if pc >= applecornMosVec { if pc >= applecornMosVec {
regA, regX, regY := t.a.cpu.GetAXY() regA, regX, regY := t.a.cpu.GetAXY()
s := "" s := ""
if !t.skipConsole { if !t.skipConsole {
switch pc { switch pc {
case 0xffe0:
s = fmt.Sprintf("OSNEWL()")
case 0xffc8: case 0xffc8:
ch := "" ch := ""
if regA >= 0x20 && regA < 0x7f { if regA >= 0x20 && regA < 0x7f {
@ -57,8 +66,14 @@ func (t *traceApplecorn) inspect() {
s = fmt.Sprintf("OSNWRCH(A=%02x, '%v')", regA, ch) s = fmt.Sprintf("OSNWRCH(A=%02x, '%v')", regA, ch)
case 0xffcb: case 0xffcb:
s = fmt.Sprintf("OSNRDCH()") s = fmt.Sprintf("OSNRDCH()")
case 0xffe7: case 0xffe0:
s = fmt.Sprintf("OSRDCH()") s = fmt.Sprintf("OSRDCH()")
//case 0xffe3: // This fallbacks to OSWRCH
// s = "OSASCI(?)"
//case 0xffe7: // This fallbacks to OSWRCH
// s = fmt.Sprintf("OSNEWL()")
//case 0xffec: // This fallbacks to OSWRCH
// s = fmt.Sprintf("OSNECR()")
case 0xffee: case 0xffee:
ch := "" ch := ""
if regA >= 0x20 && regA < 0x7f { if regA >= 0x20 && regA < 0x7f {
@ -72,6 +87,8 @@ func (t *traceApplecorn) inspect() {
switch pc { switch pc {
case 0xffb9: case 0xffb9:
s = "OSDRM(?)" s = "OSDRM(?)"
case 0xffbc:
s = "VDUCHR(?)"
case 0xffbf: case 0xffbf:
s = "OSEVEN(?)" s = "OSEVEN(?)"
case 0xffc2: case 0xffc2:
@ -90,18 +107,66 @@ func (t *traceApplecorn) inspect() {
s = "OSARGS(?)" s = "OSARGS(?)"
case 0xffdd: case 0xffdd:
s = "OSFILE(?)" s = "OSFILE(?)"
case 0xffe3:
s = "OSASCI(?)"
case 0xfff1: case 0xfff1:
s = fmt.Sprintf("OSWORD(A=%02x,XY=%04x)", regA, uint16(regX)<<8+uint16(regY)) xy := uint16(regX) + uint16(regY)<<8
switch regA {
case 0: // Read line from input
lineAddress := t.a.mmu.peekWord(xy)
maxLength := t.a.mmu.Peek(xy + 2)
s = fmt.Sprintf("OSWORD('read line';A=%02x,XY=%04x,BUF=%04x,MAX=%02x)", regA, xy, lineAddress, maxLength)
default:
s = fmt.Sprintf("OSWORD(A=%02x,XY=%04x)", regA, xy)
}
case 0xfff4: case 0xfff4:
s = fmt.Sprintf("OSBYTE('%s';A=%02x,X=%02x,Y=%02x)", t.osbyteNames[regA], regA, regX, regY) 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: case 0xfff7:
s = "OSCLI(?)" s = "OSCLI(?)"
} }
//if s == "" && !(pc >= 0xffe3 && pc < 0xffee) {
// s = "UNKNOWN(?)"
//}
if s != "" { if s != "" {
fmt.Printf("BBC MOS call to $%04x %s\n", pc, 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) > 1 {
// Reentrant call
fmt.Printf("%s", strings.Repeat(" ", len(t.calls)))
}
fmt.Printf("BBC MOS call to $%04x %s ", pc, s)
} }
} }
if len(t.calls) > 0 && pc == t.calls[len(t.calls)-1].caller {
// Returning from the call
regA, regX, regY := t.a.cpu.GetAXY()
call := t.calls[len(t.calls)-1]
s := ""
switch call.api {
case 0xfff1: // OSWORD
cbAddress := uint16(call.x) + uint16(call.y)<<8
switch 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)
}
}
fmt.Printf("=> (A=%02x,X=%02x,Y=%02x%s)\n", regA, regX, regY, s)
t.calls = t.calls[:len(t.calls)-1]
}
}
func (t *traceApplecorn) getString(address uint16, length uint8) string {
s := ""
for i := uint8(0); i < length; i++ {
ch := t.a.mmu.Peek(address + uint16(i))
s = s + string(ch)
}
return s
} }

View File

@ -206,5 +206,5 @@ func (t *tracePascal) inspectPerArchitectureGuide() {
func (t *tracePascal) param(index uint8) uint16 { func (t *tracePascal) param(index uint8) uint16 {
_, sp := t.a.cpu.GetPCAndSP() _, sp := t.a.cpu.GetPCAndSP()
return uint16(t.a.mmu.Peek(0x100+uint16(sp+index))) + return uint16(t.a.mmu.Peek(0x100+uint16(sp+index))) +
uint16(t.a.mmu.Peek(0x100+uint16(sp+index+1)))<<8 - 2 uint16(t.a.mmu.Peek(0x100+uint16(sp+index+1)))<<8 - 2 // ??
} }