From ade4fbb004d08470398352d9040177ac087a65a7 Mon Sep 17 00:00:00 2001 From: Jens Kaiser Date: Mon, 29 Oct 2018 19:41:20 +0100 Subject: [PATCH] new supervisor handler --- cpu/instructions.go | 205 ++++++++++++++++++++++++++++------ cpu/m68k.go | 32 ++++-- main.go | 6 +- mem/addrmap.go | 22 +++- mem/ram.go | 5 +- util/disam_test.go | 2 +- util/disasm.go | 267 ++++++++++++++++++++++++++++++++++++-------- util/monitor.go | 14 --- 8 files changed, 438 insertions(+), 115 deletions(-) diff --git a/cpu/instructions.go b/cpu/instructions.go index f89fd7b..29ce3e8 100644 --- a/cpu/instructions.go +++ b/cpu/instructions.go @@ -4,43 +4,184 @@ import ( "log" ) -func set(instructions []Instruction, index int, f Instruction) { - if instructions[index] != nil { - panic("opcode already in use") - } - instructions[index] = f -} +type Instruction func() int -func registerM68KInstructions(c *M68K) { +func init68000InstructionSet(c *M68K) { log.Println("register M68K instruction set") - log.Println("\tmoveq") - moveq := func(opcode int) int { - c.D[(opcode>>9)&0x7] = Data(int8(opcode & 0xff)) + moveq := func() int { + c.D[(c.opcode>>9)&0x7] = Data(int8(c.opcode & 0xff)) return 4 } - base := 0x7000 - for reg := 0; reg < 8; reg++ { - for imm := 0; imm < 256; imm++ { - set(c.instructions, base+(reg<<9)+imm, moveq) - } - } - log.Println("\tunknown") - unknown := func(opcode int) int { - if opcode&0xf000 == 0xf000 { - c.RaiseException(LineF) - } else if opcode&0xa000 == 0xa000 { - c.RaiseException(LineA) - } else { - c.RaiseException(IllegalInstruction) - } - return 34 - } - for i := range c.instructions { - if c.instructions[i] == nil { - c.instructions[i] = unknown - } - } + or := func() int { return 0 } + and := func() int { return 0 } + btst := func() int { return 0 } // movep + bchg := func() int { return 0 } + bclr := func() int { return 0 } + bset := func() int { return 0 } + sub := func() int { return 0 } + add := func() int { return 0 } + eor := func() int { return 0 } + cmp := func() int { return 0 } + neg := func() int { return 0 } + chk := func() int { return 0 } + lea := func() int { return 0 } + not := func() int { return 0 } + clr := func() int { return 0 } + nbcd := func() int { return 0 } + swap := func() int { return 0 } + tst := func() int { return 0 } + tas := func() int { return 0 } + ext := func() int { return 0 } // movem + movem := func() int { return 0 } + move := func() int { return 0 } + link := func() int { return 0 } // unlk, move + jsr := func() int { return 0 } + jmp := func() int { return 0 } + addq := func() int { return 0 } + subq := func() int { return 0 } + dbcc := func() int { return 0 } // scc + bsr := func() int { return 0 } + bcc := func() int { return 0 } + divu := func() int { return 0 } + divs := func() int { return 0 } + mulu := func() int { return 0 } + muls := func() int { return 0 } + exg := func() int { return 0 } // and + abcd := func() int { return 0 } // and + xsr := func() int { return 0 } // ror, lsr, asr + xsl := func() int { return 0 } // rol, lsl, asl + linea := func() int { return c.RaiseException(LineA) } + linef := func() int { return c.RaiseException(LineF) } + c.instructions = []Instruction{ + or, or, or, nil, btst, bchg, bclr, bset, /* 0000 */ + and, and, and, nil, btst, bchg, bclr, bset, /* 0200 */ + sub, sub, sub, nil, btst, bchg, bclr, bset, /* 0400 */ + add, add, add, nil, btst, bchg, bclr, bset, /* 0600 */ + btst, bchg, bclr, bset, btst, bchg, bclr, bset, /* 0800 */ + eor, eor, eor, nil, btst, bchg, bclr, bset, /* 0A00 */ + cmp, cmp, cmp, nil, btst, bchg, bclr, bset, /* 0C00 */ + move, move, move, nil, btst, bchg, bclr, bset, /* 0E00 */ + move, nil, move, move, move, move, move, move, /* 1000 */ + move, nil, move, move, move, move, move, move, /* 1200 */ + move, nil, move, move, move, move, move, move, /* 1400 */ + move, nil, move, move, move, move, move, move, /* 1600 */ + move, nil, move, move, move, move, move, move, /* 1800 */ + move, nil, move, move, move, move, move, move, /* 1A00 */ + move, nil, move, move, move, move, move, move, /* 1C00 */ + move, nil, move, move, move, move, move, move, /* 1E00 */ + move, move, move, move, move, move, move, move, /* 2000 */ + move, move, move, move, move, move, move, move, /* 2200 */ + move, move, move, move, move, move, move, move, /* 2400 */ + move, move, move, move, move, move, move, move, /* 2600 */ + move, move, move, move, move, move, move, move, /* 2800 */ + move, move, move, move, move, move, move, move, /* 2A00 */ + move, move, move, move, move, move, move, move, /* 2C00 */ + move, move, move, move, move, move, move, move, /* 2E00 */ + move, move, move, move, move, move, move, move, /* 3000 */ + move, move, move, move, move, move, move, move, /* 3200 */ + move, move, move, move, move, move, move, move, /* 3400 */ + move, move, move, move, move, move, move, move, /* 3600 */ + move, move, move, move, move, move, move, move, /* 3800 */ + move, move, move, move, move, move, move, move, /* 3A00 */ + move, move, move, move, move, move, move, move, /* 3C00 */ + move, move, move, move, move, move, move, move, /* 3E00 */ + neg, neg, neg, move, nil, nil, chk, lea, /* 4000 */ + clr, clr, clr, move, nil, nil, chk, lea, /* 4200 */ + neg, neg, neg, move, nil, nil, chk, lea, /* 4400 */ + not, not, not, move, nil, nil, chk, lea, /* 4600 */ + nbcd, swap, ext, ext, nil, nil, chk, lea, /* 4800 */ + tst, tst, tst, tas, nil, nil, chk, lea, /* 4A00 */ + nil, nil, movem, movem, nil, nil, chk, lea, /* 4C00 */ + nil, link, jsr, jmp, nil, nil, chk, lea, /* 4E00 */ + addq, addq, addq, dbcc, subq, subq, subq, dbcc, /* 5000 */ + addq, addq, addq, dbcc, subq, subq, subq, dbcc, /* 5200 */ + addq, addq, addq, dbcc, subq, subq, subq, dbcc, /* 5400 */ + addq, addq, addq, dbcc, subq, subq, subq, dbcc, /* 5600 */ + addq, addq, addq, dbcc, subq, subq, subq, dbcc, /* 5800 */ + addq, addq, addq, dbcc, subq, subq, subq, dbcc, /* 5A00 */ + addq, addq, addq, dbcc, subq, subq, subq, dbcc, /* 5C00 */ + addq, addq, addq, dbcc, subq, subq, subq, dbcc, /* 5E00 */ + bcc, bcc, bcc, bcc, bsr, bsr, bsr, bsr, /* 6000 */ + bcc, bcc, bcc, bcc, bcc, bcc, bcc, bcc, /* 6200 */ + bcc, bcc, bcc, bcc, bcc, bcc, bcc, bcc, /* 6400 */ + bcc, bcc, bcc, bcc, bcc, bcc, bcc, bcc, /* 6600 */ + bcc, bcc, bcc, bcc, bcc, bcc, bcc, bcc, /* 6800 */ + bcc, bcc, bcc, bcc, bcc, bcc, bcc, bcc, /* 6A00 */ + bcc, bcc, bcc, bcc, bcc, bcc, bcc, bcc, /* 6C00 */ + bcc, bcc, bcc, bcc, bcc, bcc, bcc, bcc, /* 6E00 */ + moveq, moveq, moveq, moveq, nil, nil, nil, nil, /* 7000 */ + moveq, moveq, moveq, moveq, nil, nil, nil, nil, /* 7200 */ + moveq, moveq, moveq, moveq, nil, nil, nil, nil, /* 7400 */ + moveq, moveq, moveq, moveq, nil, nil, nil, nil, /* 7600 */ + moveq, moveq, moveq, moveq, nil, nil, nil, nil, /* 7800 */ + moveq, moveq, moveq, moveq, nil, nil, nil, nil, /* 7A00 */ + moveq, moveq, moveq, moveq, nil, nil, nil, nil, /* 7C00 */ + moveq, moveq, moveq, moveq, nil, nil, nil, nil, /* 7E00 */ + or, or, or, divu, or, or, or, divs, /* 8000 */ + or, or, or, divu, or, or, or, divs, /* 8200 */ + or, or, or, divu, or, or, or, divs, /* 8400 */ + or, or, or, divu, or, or, or, divs, /* 8600 */ + or, or, or, divu, or, or, or, divs, /* 8800 */ + or, or, or, divu, or, or, or, divs, /* 8A00 */ + or, or, or, divu, or, or, or, divs, /* 8C00 */ + or, or, or, divu, or, or, or, divs, /* 8E00 */ + sub, sub, sub, sub, sub, sub, sub, sub, /* 9000 */ + sub, sub, sub, sub, sub, sub, sub, sub, /* 9200 */ + sub, sub, sub, sub, sub, sub, sub, sub, /* 9400 */ + sub, sub, sub, sub, sub, sub, sub, sub, /* 9600 */ + sub, sub, sub, sub, sub, sub, sub, sub, /* 9800 */ + sub, sub, sub, sub, sub, sub, sub, sub, /* 9A00 */ + sub, sub, sub, sub, sub, sub, sub, sub, /* 9C00 */ + sub, sub, sub, sub, sub, sub, sub, sub, /* 9E00 */ + linea, linea, linea, linea, linea, linea, linea, linea, /* A000 */ + linea, linea, linea, linea, linea, linea, linea, linea, + linea, linea, linea, linea, linea, linea, linea, linea, + linea, linea, linea, linea, linea, linea, linea, linea, + linea, linea, linea, linea, linea, linea, linea, linea, + linea, linea, linea, linea, linea, linea, linea, linea, + linea, linea, linea, linea, linea, linea, linea, linea, + linea, linea, linea, linea, linea, linea, linea, linea, + cmp, cmp, cmp, cmp, cmp, cmp, cmp, cmp, /* B000 */ + cmp, cmp, cmp, cmp, cmp, cmp, cmp, cmp, /* B200 */ + cmp, cmp, cmp, cmp, cmp, cmp, cmp, cmp, /* B400 */ + cmp, cmp, cmp, cmp, cmp, cmp, cmp, cmp, /* B600 */ + cmp, cmp, cmp, cmp, cmp, cmp, cmp, cmp, /* B800 */ + cmp, cmp, cmp, cmp, cmp, cmp, cmp, cmp, /* BA00 */ + cmp, cmp, cmp, cmp, cmp, cmp, cmp, cmp, /* BC00 */ + cmp, cmp, cmp, cmp, cmp, cmp, cmp, cmp, /* BE00 */ + and, and, and, mulu, abcd, exg, exg, muls, /* C000 */ + and, and, and, mulu, abcd, exg, exg, muls, /* C200 */ + and, and, and, mulu, abcd, exg, exg, muls, /* C400 */ + and, and, and, mulu, abcd, exg, exg, muls, /* C600 */ + and, and, and, mulu, abcd, exg, exg, muls, /* C800 */ + and, and, and, mulu, abcd, exg, exg, muls, /* CA00 */ + and, and, and, mulu, abcd, exg, exg, muls, /* CC00 */ + and, and, and, mulu, abcd, exg, exg, muls, /* CE00 */ + add, add, add, add, add, add, add, add, /* D000 */ + add, add, add, add, add, add, add, add, /* D200 */ + add, add, add, add, add, add, add, add, /* D400 */ + add, add, add, add, add, add, add, add, /* D600 */ + add, add, add, add, add, add, add, add, /* D800 */ + add, add, add, add, add, add, add, add, /* DA00 */ + add, add, add, add, add, add, add, add, /* DC00 */ + add, add, add, add, add, add, add, add, /* DE00 */ + xsr, xsr, xsr, xsr, xsl, xsl, xsl, xsl, /* E000 */ + xsr, xsr, xsr, xsr, xsl, xsl, xsl, xsl, /* E200 */ + xsr, xsr, xsr, xsr, xsl, xsl, xsl, xsl, /* E400 */ + xsr, xsr, xsr, xsr, xsl, xsl, xsl, xsl, /* E600 */ + xsr, xsr, xsr, nil, xsl, xsl, xsl, nil, /* E800 */ + xsr, xsr, xsr, nil, xsl, xsl, xsl, nil, /* EA00 */ + xsr, xsr, xsr, nil, xsl, xsl, xsl, nil, /* EC00 */ + xsr, xsr, xsr, nil, xsl, xsl, xsl, nil, /* EE00 */ + linef, linef, linef, linef, linef, linef, linef, linef, /* F000 */ + linef, linef, linef, linef, linef, linef, linef, linef, + linef, linef, linef, linef, linef, linef, linef, linef, + linef, linef, linef, linef, linef, linef, linef, linef, + linef, linef, linef, linef, linef, linef, linef, linef, + linef, linef, linef, linef, linef, linef, linef, linef, + linef, linef, linef, linef, linef, linef, linef, linef, + linef, linef, linef, linef, linef, linef, linef, linef} } diff --git a/cpu/m68k.go b/cpu/m68k.go index 6320803..4d5a7d2 100644 --- a/cpu/m68k.go +++ b/cpu/m68k.go @@ -9,10 +9,9 @@ type ( Read(address Address, operand *Operand) (int, error) Write(address Address, operand *Operand, value int) error Reset() + SetSuperVisorFlag(*bool) } - Instruction func(opcode int) int - M68K struct { // registers A [8]Address @@ -20,8 +19,11 @@ type ( SR StatusRegister PC Address SSP, USP Address - opcode int - bus AddressBus + + opcodeAddr Address + opcode int + + bus AddressBus instructions []Instruction } @@ -30,11 +32,27 @@ type ( func NewCPU(addressBus AddressBus) M68K { result := M68K{bus: addressBus} result.instructions = make([]Instruction, 0x10000) - registerM68KInstructions(&result) + init68000InstructionSet(&result) result.Reset() return result } +func (c *M68K) Step() int { + c.opcodeAddr = c.PC + if opcode, err := c.bus.Read(c.PC, Word); err == nil { + c.opcode = opcode + c.PC += Address(Word.size) + + if instruction := c.instructions[opcode>>6]; instruction != nil { + return instruction() + } else { + return c.RaiseException(IllegalInstruction) + } + } else { + panic("bus error") + } +} + func (c *M68K) Reset() { c.SR.Set(0x2700) c.bus.Reset() @@ -47,7 +65,7 @@ func (c *M68K) Reset() { c.SSP, c.PC = sp, pc } -func (c *M68K) RaiseException(x Exception) { +func (c *M68K) RaiseException(x Exception) int { oldSR := c.SR if !c.SR.S { c.SR.S = true @@ -64,7 +82,7 @@ func (c *M68K) RaiseException(x Exception) { } else { c.PC = xaddr } - + return 34 } func (c *M68K) Halt() { diff --git a/main.go b/main.go index b2f6d8b..7aeae3f 100644 --- a/main.go +++ b/main.go @@ -53,11 +53,11 @@ func main() { } bus := mem.NewAddressBus( - mem.NewProtectedRAM(0, 1024, nil), - mem.NewRAM(1024, 1023*1024), + mem.NewProtectedRAM(0, 2048), + mem.NewRAM(2048, 1024*1024), mem.NewROM(startROM, data), ) - cpu.NewCPU(bus) + cpu.NewCPU(bus) util.Dump(bus, startROM, 128) } diff --git a/mem/addrmap.go b/mem/addrmap.go index 61f41f3..f7eec99 100644 --- a/mem/addrmap.go +++ b/mem/addrmap.go @@ -12,16 +12,18 @@ type ( ResetHandler func() AddressArea struct { - start cpu.Address - end cpu.Address - read MemoryReader - write MemoryWriter - reset ResetHandler + start cpu.Address + end cpu.Address + read MemoryReader + write MemoryWriter + reset ResetHandler + parent *addressMap } addressMap struct { areas []AddressArea cache *AddressArea + sv *bool } ) @@ -60,6 +62,10 @@ func (a *addressMap) Write(address cpu.Address, operand *cpu.Operand, value int) return BusError(address) } +func (a *addressMap) SetSuperVisorFlag(flag *bool) { + a.sv = flag +} + func (a *addressMap) Reset() { for _, area := range a.areas { if area.reset != nil { @@ -69,5 +75,9 @@ func (a *addressMap) Reset() { } func NewAddressBus(areas ...AddressArea) cpu.AddressBus { - return &addressMap{areas: areas, cache: &areas[0]} + result := &addressMap{areas: areas, cache: &areas[0]} + for _, area := range areas { + area.parent = result + } + return result } diff --git a/mem/ram.go b/mem/ram.go index d0288a2..5693938 100644 --- a/mem/ram.go +++ b/mem/ram.go @@ -18,7 +18,6 @@ func NewRAM(start cpu.Address, size uint) AddressArea { }, read: func(address cpu.Address, operand *cpu.Operand) (int, error) { if address >= start && address < end { - return operand.Read(ram[address-start:]), nil } return 0, BusError(address) @@ -26,11 +25,11 @@ func NewRAM(start cpu.Address, size uint) AddressArea { } } -func NewProtectedRAM(start cpu.Address, size uint, sr *cpu.StatusRegister) AddressArea { +func NewProtectedRAM(start cpu.Address, size uint) AddressArea { area := NewRAM(start, size) protectedWrite := area.write area.write = func(address cpu.Address, operand *cpu.Operand, value int) error { - if sr.S { + if area.parent.sv == nil || *area.parent.sv == true { return protectedWrite(address, operand, value) } return cpu.SuperVisorException(address) diff --git a/util/disam_test.go b/util/disam_test.go index 617e0bf..1437c97 100644 --- a/util/disam_test.go +++ b/util/disam_test.go @@ -28,7 +28,7 @@ func TestDisasmMoveq(t *testing.T) { panic(fmt.Sprintf("invalid read %s", err)) } - instruction := opcodes[opcode](bus, start) + instruction := opcodes[opcode>>6](bus, start) assert.Equal(t, "moveq", instruction.instruction) assert.Equal(t, 2, instruction.Size()) start += cpu.Address(instruction.Size()) diff --git a/util/disasm.go b/util/disasm.go index 8d0c205..01f0212 100644 --- a/util/disasm.go +++ b/util/disasm.go @@ -25,58 +25,20 @@ type disassemble func(bus cpu.AddressBus, address cpu.Address) *disassembledOpco var opcodes []disassemble -func readO(bus cpu.AddressBus, address cpu.Address) int { - o, err := bus.Read(address, cpu.Word) - if err != nil { - panic("invalid address") - } - return o -} - -func set(index int, d disassemble) { - if opcodes[index] != nil { - panic("opcode already in use") - } - opcodes[index] = d -} - -func init() { - log.Println("disasm init") - opcodes = make([]disassemble, 0x10000) - - log.Println("\tmoveq") - moveq := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { - opcode := readO(bus, address) - return &disassembledOpcode{ - address: address, - opcode: opcode, - instruction: "moveq", - op1: &disassembledOperand{operand: fmt.Sprintf("#%d", int8(opcode&0xff))}, - op2: &disassembledOperand{operand: fmt.Sprintf("d%d", ((opcode >> 9) & 0x07))}, - } - } - - base := 0x7000 - for reg := 0; reg < 8; reg++ { - for imm := 0; imm < 256; imm++ { - set(base+(reg<<9)+imm, moveq) +func Disassemble(bus cpu.AddressBus, start cpu.Address, size int) { + end := start + cpu.Address(size) + for start < end { + if opcode, err := bus.Read(start, cpu.Word); err == nil { + instruction := opcodes[opcode](bus, start) + fmt.Println(instruction) + start += cpu.Address(instruction.Size()) + } else { + panic(fmt.Sprintf("invalid read %s", err)) } } - - log.Println("\tunknown") - unknown := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { - return &disassembledOpcode{address: address, opcode: readO(bus, address), instruction: "????"} - } - - for i := range opcodes { - if opcodes[i] == nil { - opcodes[i] = unknown - } - } - } -func (opcode *disassembledOpcode) Size() int { +func (opcode disassembledOpcode) Size() int { size := 2 if opcode.op1 != nil { size += opcode.op1.size @@ -87,7 +49,7 @@ func (opcode *disassembledOpcode) Size() int { return size } -func (opcode *disassembledOpcode) String() string { +func (opcode disassembledOpcode) String() string { op1hex, op2hex, opstr := "", "", "" if opcode.op1 != nil { switch opcode.op1.size { @@ -110,3 +72,210 @@ func (opcode *disassembledOpcode) String() string { return fmt.Sprintf("%08x %04x %8s %8s %s %s", opcode.address, opcode.opcode, op1hex, op2hex, opcode.instruction, opstr) } + +func newDisassembleOpcode(bus cpu.AddressBus, address cpu.Address, ins string) *disassembledOpcode { + if o, err := bus.Read(address, cpu.Word); err == nil { + return &disassembledOpcode{ + address: address, + opcode: o, + instruction: ins, + } + } else { + panic("illegal address") + } +} + +func init() { + log.Println("disasm init") + + moveq := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { + result := newDisassembleOpcode(bus, address, "moveq") + opcode := result.opcode + result.op1 = &disassembledOperand{operand: fmt.Sprintf("#%d", int8(opcode&0xff))} + result.op2 = &disassembledOperand{operand: fmt.Sprintf("d%d", ((opcode >> 9) & 0x07))} + return result + } + + illegal := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { + return newDisassembleOpcode(bus, address, "????") + } + + or := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { + return newDisassembleOpcode(bus, address, "or") + } + + and := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + btst := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } // movep + bchg := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + bclr := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + bset := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + sub := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + add := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + eor := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + cmp := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + neg := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + chk := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + lea := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + not := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + clr := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + nbcd := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + swap := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + tst := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + tas := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + ext := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } // movem + movem := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + move := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + link := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } // unlk, move + jsr := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + jmp := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + addq := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + subq := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + dbcc := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } // scc + bsr := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + + bcc := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { + return nil + } + + divu := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + divs := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + mulu := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + muls := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + exg := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } // and + abcd := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } // and + xsr := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } // ror, lsr, asr + xsl := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } // rol, lsl, asl + linea := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + linef := func(bus cpu.AddressBus, address cpu.Address) *disassembledOpcode { return nil } + + opcodes = []disassemble{ + or, or, or, illegal, btst, bchg, bclr, bset, /* 0000 */ + and, and, and, illegal, btst, bchg, bclr, bset, /* 0200 */ + sub, sub, sub, illegal, btst, bchg, bclr, bset, /* 0400 */ + add, add, add, illegal, btst, bchg, bclr, bset, /* 0600 */ + btst, bchg, bclr, bset, btst, bchg, bclr, bset, /* 0800 */ + eor, eor, eor, illegal, btst, bchg, bclr, bset, /* 0A00 */ + cmp, cmp, cmp, illegal, btst, bchg, bclr, bset, /* 0C00 */ + move, move, move, illegal, btst, bchg, bclr, bset, /* 0E00 */ + move, illegal, move, move, move, move, move, move, /* 1000 */ + move, illegal, move, move, move, move, move, move, /* 1200 */ + move, illegal, move, move, move, move, move, move, /* 1400 */ + move, illegal, move, move, move, move, move, move, /* 1600 */ + move, illegal, move, move, move, move, move, move, /* 1800 */ + move, illegal, move, move, move, move, move, move, /* 1A00 */ + move, illegal, move, move, move, move, move, move, /* 1C00 */ + move, illegal, move, move, move, move, move, move, /* 1E00 */ + move, move, move, move, move, move, move, move, /* 2000 */ + move, move, move, move, move, move, move, move, /* 2200 */ + move, move, move, move, move, move, move, move, /* 2400 */ + move, move, move, move, move, move, move, move, /* 2600 */ + move, move, move, move, move, move, move, move, /* 2800 */ + move, move, move, move, move, move, move, move, /* 2A00 */ + move, move, move, move, move, move, move, move, /* 2C00 */ + move, move, move, move, move, move, move, move, /* 2E00 */ + move, move, move, move, move, move, move, move, /* 3000 */ + move, move, move, move, move, move, move, move, /* 3200 */ + move, move, move, move, move, move, move, move, /* 3400 */ + move, move, move, move, move, move, move, move, /* 3600 */ + move, move, move, move, move, move, move, move, /* 3800 */ + move, move, move, move, move, move, move, move, /* 3A00 */ + move, move, move, move, move, move, move, move, /* 3C00 */ + move, move, move, move, move, move, move, move, /* 3E00 */ + neg, neg, neg, move, illegal, illegal, chk, lea, /* 4000 */ + clr, clr, clr, move, illegal, illegal, chk, lea, /* 4200 */ + neg, neg, neg, move, illegal, illegal, chk, lea, /* 4400 */ + not, not, not, move, illegal, illegal, chk, lea, /* 4600 */ + nbcd, swap, ext, ext, illegal, illegal, chk, lea, /* 4800 */ + tst, tst, tst, tas, illegal, illegal, chk, lea, /* 4A00 */ + illegal, illegal, movem, movem, illegal, illegal, chk, lea, /* 4C00 */ + illegal, link, jsr, jmp, illegal, illegal, chk, lea, /* 4E00 */ + addq, addq, addq, dbcc, subq, subq, subq, dbcc, /* 5000 */ + addq, addq, addq, dbcc, subq, subq, subq, dbcc, /* 5200 */ + addq, addq, addq, dbcc, subq, subq, subq, dbcc, /* 5400 */ + addq, addq, addq, dbcc, subq, subq, subq, dbcc, /* 5600 */ + addq, addq, addq, dbcc, subq, subq, subq, dbcc, /* 5800 */ + addq, addq, addq, dbcc, subq, subq, subq, dbcc, /* 5A00 */ + addq, addq, addq, dbcc, subq, subq, subq, dbcc, /* 5C00 */ + addq, addq, addq, dbcc, subq, subq, subq, dbcc, /* 5E00 */ + bcc, bcc, bcc, bcc, bsr, bsr, bsr, bsr, /* 6000 */ + bcc, bcc, bcc, bcc, bcc, bcc, bcc, bcc, /* 6200 */ + bcc, bcc, bcc, bcc, bcc, bcc, bcc, bcc, /* 6400 */ + bcc, bcc, bcc, bcc, bcc, bcc, bcc, bcc, /* 6600 */ + bcc, bcc, bcc, bcc, bcc, bcc, bcc, bcc, /* 6800 */ + bcc, bcc, bcc, bcc, bcc, bcc, bcc, bcc, /* 6A00 */ + bcc, bcc, bcc, bcc, bcc, bcc, bcc, bcc, /* 6C00 */ + bcc, bcc, bcc, bcc, bcc, bcc, bcc, bcc, /* 6E00 */ + moveq, moveq, moveq, moveq, illegal, illegal, illegal, illegal, /* 7000 */ + moveq, moveq, moveq, moveq, illegal, illegal, illegal, illegal, /* 7200 */ + moveq, moveq, moveq, moveq, illegal, illegal, illegal, illegal, /* 7400 */ + moveq, moveq, moveq, moveq, illegal, illegal, illegal, illegal, /* 7600 */ + moveq, moveq, moveq, moveq, illegal, illegal, illegal, illegal, /* 7800 */ + moveq, moveq, moveq, moveq, illegal, illegal, illegal, illegal, /* 7A00 */ + moveq, moveq, moveq, moveq, illegal, illegal, illegal, illegal, /* 7C00 */ + moveq, moveq, moveq, moveq, illegal, illegal, illegal, illegal, /* 7E00 */ + or, or, or, divu, or, or, or, divs, /* 8000 */ + or, or, or, divu, or, or, or, divs, /* 8200 */ + or, or, or, divu, or, or, or, divs, /* 8400 */ + or, or, or, divu, or, or, or, divs, /* 8600 */ + or, or, or, divu, or, or, or, divs, /* 8800 */ + or, or, or, divu, or, or, or, divs, /* 8A00 */ + or, or, or, divu, or, or, or, divs, /* 8C00 */ + or, or, or, divu, or, or, or, divs, /* 8E00 */ + sub, sub, sub, sub, sub, sub, sub, sub, /* 9000 */ + sub, sub, sub, sub, sub, sub, sub, sub, /* 9200 */ + sub, sub, sub, sub, sub, sub, sub, sub, /* 9400 */ + sub, sub, sub, sub, sub, sub, sub, sub, /* 9600 */ + sub, sub, sub, sub, sub, sub, sub, sub, /* 9800 */ + sub, sub, sub, sub, sub, sub, sub, sub, /* 9A00 */ + sub, sub, sub, sub, sub, sub, sub, sub, /* 9C00 */ + sub, sub, sub, sub, sub, sub, sub, sub, /* 9E00 */ + linea, linea, linea, linea, linea, linea, linea, linea, /* A000 */ + linea, linea, linea, linea, linea, linea, linea, linea, + linea, linea, linea, linea, linea, linea, linea, linea, + linea, linea, linea, linea, linea, linea, linea, linea, + linea, linea, linea, linea, linea, linea, linea, linea, + linea, linea, linea, linea, linea, linea, linea, linea, + linea, linea, linea, linea, linea, linea, linea, linea, + linea, linea, linea, linea, linea, linea, linea, linea, + cmp, cmp, cmp, cmp, cmp, cmp, cmp, cmp, /* B000 */ + cmp, cmp, cmp, cmp, cmp, cmp, cmp, cmp, /* B200 */ + cmp, cmp, cmp, cmp, cmp, cmp, cmp, cmp, /* B400 */ + cmp, cmp, cmp, cmp, cmp, cmp, cmp, cmp, /* B600 */ + cmp, cmp, cmp, cmp, cmp, cmp, cmp, cmp, /* B800 */ + cmp, cmp, cmp, cmp, cmp, cmp, cmp, cmp, /* BA00 */ + cmp, cmp, cmp, cmp, cmp, cmp, cmp, cmp, /* BC00 */ + cmp, cmp, cmp, cmp, cmp, cmp, cmp, cmp, /* BE00 */ + and, and, and, mulu, abcd, exg, exg, muls, /* C000 */ + and, and, and, mulu, abcd, exg, exg, muls, /* C200 */ + and, and, and, mulu, abcd, exg, exg, muls, /* C400 */ + and, and, and, mulu, abcd, exg, exg, muls, /* C600 */ + and, and, and, mulu, abcd, exg, exg, muls, /* C800 */ + and, and, and, mulu, abcd, exg, exg, muls, /* CA00 */ + and, and, and, mulu, abcd, exg, exg, muls, /* CC00 */ + and, and, and, mulu, abcd, exg, exg, muls, /* CE00 */ + add, add, add, add, add, add, add, add, /* D000 */ + add, add, add, add, add, add, add, add, /* D200 */ + add, add, add, add, add, add, add, add, /* D400 */ + add, add, add, add, add, add, add, add, /* D600 */ + add, add, add, add, add, add, add, add, /* D800 */ + add, add, add, add, add, add, add, add, /* DA00 */ + add, add, add, add, add, add, add, add, /* DC00 */ + add, add, add, add, add, add, add, add, /* DE00 */ + xsr, xsr, xsr, xsr, xsl, xsl, xsl, xsl, /* E000 */ + xsr, xsr, xsr, xsr, xsl, xsl, xsl, xsl, /* E200 */ + xsr, xsr, xsr, xsr, xsl, xsl, xsl, xsl, /* E400 */ + xsr, xsr, xsr, xsr, xsl, xsl, xsl, xsl, /* E600 */ + xsr, xsr, xsr, illegal, xsl, xsl, xsl, illegal, /* E800 */ + xsr, xsr, xsr, illegal, xsl, xsl, xsl, illegal, /* EA00 */ + xsr, xsr, xsr, illegal, xsl, xsl, xsl, illegal, /* EC00 */ + xsr, xsr, xsr, illegal, xsl, xsl, xsl, illegal, /* EE00 */ + linef, linef, linef, linef, linef, linef, linef, linef, /* F000 */ + linef, linef, linef, linef, linef, linef, linef, linef, + linef, linef, linef, linef, linef, linef, linef, linef, + linef, linef, linef, linef, linef, linef, linef, linef, + linef, linef, linef, linef, linef, linef, linef, linef, + linef, linef, linef, linef, linef, linef, linef, linef, + linef, linef, linef, linef, linef, linef, linef, linef, + linef, linef, linef, linef, linef, linef, linef, linef, + } +} diff --git a/util/monitor.go b/util/monitor.go index a68ffa9..9181cb9 100644 --- a/util/monitor.go +++ b/util/monitor.go @@ -22,17 +22,3 @@ func Dump(bus cpu.AddressBus, start cpu.Address, size int) { } } - -func Disassemble(bus cpu.AddressBus, start cpu.Address, size int) { - end := start + cpu.Address(size) - for start < end { - opcode, err := bus.Read(start, cpu.Word) - if err != nil { - panic(fmt.Sprintf("invalid read %s", err)) - } - - instruction := opcodes[opcode](bus, start) - fmt.Println(instruction) - start += cpu.Address(instruction.Size()) - } -}