From 6caef2579a1490f05d28bcede731cbdd45fc5c65 Mon Sep 17 00:00:00 2001 From: Olivier Galibert Date: Wed, 5 Jul 2017 11:44:49 +0200 Subject: dvdisasm: Overhaul [O. Galibert] Disassemblers are now independant classes. Not only the code is cleaner, but unidasm has access to all the cpu cores again. The interface to the disassembly method has changed from byte buffers to objects that give a result to read methods. This also adds support for lfsr and/or paged PCs. --- docs/source/techspecs/device_disasm_interface.rst | 204 + docs/source/techspecs/device_memory_interface.rst | 5 +- docs/source/techspecs/index.rst | 1 + scripts/src/cpu.lua | 271 +- scripts/src/devices.lua | 8 +- scripts/src/emu.lua | 2 + scripts/src/lib.lua | 2 + src/devices/cpu/8x300/8x300.cpp | 6 +- src/devices/cpu/8x300/8x300.h | 4 +- src/devices/cpu/8x300/8x300dasm.cpp | 17 +- src/devices/cpu/8x300/8x300dasm.h | 31 + src/devices/cpu/adsp2100/2100dasm.cpp | 66 +- src/devices/cpu/adsp2100/2100dasm.h | 43 + src/devices/cpu/adsp2100/adsp2100.cpp | 31 +- src/devices/cpu/adsp2100/adsp2100.h | 4 +- src/devices/cpu/alph8201/8201dasm.cpp | 47 +- src/devices/cpu/alph8201/8201dasm.h | 51 + src/devices/cpu/alph8201/alph8201.cpp | 8 +- src/devices/cpu/alph8201/alph8201.h | 4 +- src/devices/cpu/alto2/a2ram.cpp | 4 +- src/devices/cpu/alto2/alto2cpu.cpp | 6 + src/devices/cpu/alto2/alto2cpu.h | 4 +- src/devices/cpu/alto2/alto2dsm.cpp | 54 +- src/devices/cpu/alto2/alto2dsm.h | 31 + src/devices/cpu/am29000/am29000.cpp | 7 +- src/devices/cpu/am29000/am29000.h | 4 +- src/devices/cpu/am29000/am29dasm.cpp | 27 +- src/devices/cpu/am29000/am29dasm.h | 36 + src/devices/cpu/amis2000/amis2000.cpp | 6 +- src/devices/cpu/amis2000/amis2000.h | 4 +- src/devices/cpu/amis2000/amis2000d.cpp | 41 +- src/devices/cpu/amis2000/amis2000d.h | 40 + src/devices/cpu/apexc/apexc.cpp | 7 +- src/devices/cpu/apexc/apexc.h | 4 +- src/devices/cpu/apexc/apexcdsm.cpp | 22 +- src/devices/cpu/apexc/apexcdsm.h | 37 + src/devices/cpu/arc/arc.cpp | 7 +- src/devices/cpu/arc/arc.h | 4 +- src/devices/cpu/arc/arcdasm.cpp | 22 +- src/devices/cpu/arc/arcdasm.h | 31 + src/devices/cpu/arcompact/arcompact.cpp | 9 +- src/devices/cpu/arcompact/arcompact.h | 4 +- src/devices/cpu/arcompact/arcompact_common.cpp | 527 -- src/devices/cpu/arcompact/arcompact_common.h | 24 - src/devices/cpu/arcompact/arcompact_execute.cpp | 98 +- src/devices/cpu/arcompact/arcompactdasm.cpp | 599 +- src/devices/cpu/arcompact/arcompactdasm.h | 721 +++ .../cpu/arcompact/arcompactdasm_dispatch.cpp | 1245 +++-- src/devices/cpu/arcompact/arcompactdasm_dispatch.h | 50 - src/devices/cpu/arcompact/arcompactdasm_ops.cpp | 3937 +++++++++++--- src/devices/cpu/arcompact/arcompactdasm_ops.h | 642 --- src/devices/cpu/arm/arm.cpp | 16 +- src/devices/cpu/arm/arm.h | 7 +- src/devices/cpu/arm/armdasm.cpp | 33 +- src/devices/cpu/arm/armdasm.h | 23 + src/devices/cpu/arm7/arm7.cpp | 83 +- src/devices/cpu/arm7/arm7.h | 9 +- src/devices/cpu/arm7/arm7dasm.cpp | 64 +- src/devices/cpu/arm7/arm7dasm.h | 51 + src/devices/cpu/asap/asap.cpp | 31 +- src/devices/cpu/asap/asap.h | 4 +- src/devices/cpu/asap/asapdasm.cpp | 45 +- src/devices/cpu/asap/asapdasm.h | 33 + src/devices/cpu/avr8/avr8.cpp | 30 +- src/devices/cpu/avr8/avr8.h | 6 +- src/devices/cpu/avr8/avr8dasm.cpp | 41 +- src/devices/cpu/avr8/avr8dasm.h | 24 + src/devices/cpu/capricorn/capricorn.cpp | 6 +- src/devices/cpu/capricorn/capricorn.h | 6 +- src/devices/cpu/capricorn/capricorn_dasm.cpp | 237 +- src/devices/cpu/capricorn/capricorn_dasm.h | 50 + src/devices/cpu/ccpu/ccpu.cpp | 6 +- src/devices/cpu/ccpu/ccpu.h | 4 +- src/devices/cpu/ccpu/ccpudasm.cpp | 18 +- src/devices/cpu/ccpu/ccpudasm.h | 28 + src/devices/cpu/clipper/clipper.cpp | 5 +- src/devices/cpu/clipper/clipper.h | 6 +- src/devices/cpu/clipper/clipperd.cpp | 158 +- src/devices/cpu/clipper/clipperd.h | 38 + src/devices/cpu/cop400/cop400.cpp | 19 +- src/devices/cpu/cop400/cop400.h | 4 +- src/devices/cpu/cop400/cop410ds.cpp | 22 +- src/devices/cpu/cop400/cop410ds.h | 26 + src/devices/cpu/cop400/cop420ds.cpp | 22 +- src/devices/cpu/cop400/cop420ds.h | 26 + src/devices/cpu/cop400/cop424ds.cpp | 22 +- src/devices/cpu/cop400/cop424ds.h | 26 + src/devices/cpu/cop400/cop444ds.cpp | 22 +- src/devices/cpu/cop400/cop444ds.h | 26 + src/devices/cpu/cosmac/cosdasm.cpp | 124 +- src/devices/cpu/cosmac/cosdasm.h | 43 + src/devices/cpu/cosmac/cosmac.cpp | 37 +- src/devices/cpu/cosmac/cosmac.h | 8 +- src/devices/cpu/cp1610/1610dasm.cpp | 12 +- src/devices/cpu/cp1610/1610dasm.h | 19 + src/devices/cpu/cp1610/cp1610.cpp | 8 +- src/devices/cpu/cp1610/cp1610.h | 7 +- src/devices/cpu/cubeqcpu/cubedasm.cpp | 30 +- src/devices/cpu/cubeqcpu/cubedasm.h | 54 + src/devices/cpu/cubeqcpu/cubeqcpu.cpp | 16 +- src/devices/cpu/cubeqcpu/cubeqcpu.h | 12 +- src/devices/cpu/dsp16/dsp16.cpp | 32 +- src/devices/cpu/dsp16/dsp16.h | 4 +- src/devices/cpu/dsp16/dsp16dis.cpp | 35 +- src/devices/cpu/dsp16/dsp16dis.h | 32 + src/devices/cpu/dsp32/dsp32.cpp | 31 +- src/devices/cpu/dsp32/dsp32.h | 4 +- src/devices/cpu/dsp32/dsp32dis.cpp | 87 +- src/devices/cpu/dsp32/dsp32dis.h | 45 + src/devices/cpu/dsp56k/dsp56dsm.cpp | 15 +- src/devices/cpu/dsp56k/dsp56dsm.h | 26 + src/devices/cpu/dsp56k/dsp56k.cpp | 5 +- src/devices/cpu/dsp56k/dsp56k.h | 6 +- src/devices/cpu/dsp56k/inst.h | 22 +- src/devices/cpu/e0c6200/e0c6200.cpp | 6 +- src/devices/cpu/e0c6200/e0c6200.h | 5 +- src/devices/cpu/e0c6200/e0c6200d.cpp | 93 +- src/devices/cpu/e0c6200/e0c6200d.h | 55 + src/devices/cpu/e132xs/32xsdasm.cpp | 252 +- src/devices/cpu/e132xs/32xsdasm.h | 43 + src/devices/cpu/e132xs/e132xs.cpp | 30 +- src/devices/cpu/e132xs/e132xs.h | 10 +- src/devices/cpu/es5510/es5510.cpp | 15 +- src/devices/cpu/es5510/es5510.h | 4 +- src/devices/cpu/es5510/es5510d.cpp | 20 + src/devices/cpu/es5510/es5510d.h | 25 + src/devices/cpu/esrip/esrip.cpp | 31 +- src/devices/cpu/esrip/esrip.h | 7 +- src/devices/cpu/esrip/esripdsm.cpp | 12 +- src/devices/cpu/esrip/esripdsm.h | 27 + src/devices/cpu/f8/f8.cpp | 6 +- src/devices/cpu/f8/f8.h | 4 +- src/devices/cpu/f8/f8dasm.cpp | 68 +- src/devices/cpu/f8/f8dasm.h | 21 + src/devices/cpu/g65816/g65816.cpp | 15 +- src/devices/cpu/g65816/g65816.h | 9 +- src/devices/cpu/g65816/g65816ds.cpp | 243 +- src/devices/cpu/g65816/g65816ds.h | 63 +- src/devices/cpu/h6280/6280dasm.cpp | 121 +- src/devices/cpu/h6280/6280dasm.h | 90 + src/devices/cpu/h6280/h6280.cpp | 30 +- src/devices/cpu/h6280/h6280.h | 4 +- src/devices/cpu/h8/h8.cpp | 256 +- src/devices/cpu/h8/h8.h | 76 +- src/devices/cpu/h8/h8d.cpp | 262 + src/devices/cpu/h8/h8d.h | 101 + src/devices/cpu/h8/h8h.cpp | 5 +- src/devices/cpu/h8/h8h.h | 4 +- src/devices/cpu/h8/h8hd.cpp | 17 + src/devices/cpu/h8/h8hd.h | 28 + src/devices/cpu/h8/h8make.py | 58 +- src/devices/cpu/h8/h8s2000.cpp | 5 +- src/devices/cpu/h8/h8s2000.h | 4 +- src/devices/cpu/h8/h8s2000d.cpp | 17 + src/devices/cpu/h8/h8s2000d.h | 28 + src/devices/cpu/h8/h8s2600.cpp | 5 +- src/devices/cpu/h8/h8s2600.h | 4 +- src/devices/cpu/h8/h8s2600d.cpp | 17 + src/devices/cpu/h8/h8s2600d.h | 28 + src/devices/cpu/hcd62121/hcd62121.cpp | 7 +- src/devices/cpu/hcd62121/hcd62121.h | 4 +- src/devices/cpu/hcd62121/hcd62121d.cpp | 182 +- src/devices/cpu/hcd62121/hcd62121d.h | 62 + src/devices/cpu/hd61700/hd61700.cpp | 10 +- src/devices/cpu/hd61700/hd61700.h | 4 +- src/devices/cpu/hd61700/hd61700d.cpp | 197 +- src/devices/cpu/hd61700/hd61700d.h | 70 + src/devices/cpu/hmcs40/hmcs40.cpp | 7 +- src/devices/cpu/hmcs40/hmcs40.h | 4 +- src/devices/cpu/hmcs40/hmcs40d.cpp | 80 +- src/devices/cpu/hmcs40/hmcs40d.h | 50 + src/devices/cpu/hphybrid/hphybrid.cpp | 11 +- src/devices/cpu/hphybrid/hphybrid.h | 6 +- src/devices/cpu/hphybrid/hphybrid_dasm.cpp | 250 +- src/devices/cpu/hphybrid/hphybrid_dasm.h | 59 + src/devices/cpu/i386/i386.cpp | 8 +- src/devices/cpu/i386/i386.h | 8 +- src/devices/cpu/i386/i386dasm.cpp | 543 +- src/devices/cpu/i386/i386dasm.h | 215 +- src/devices/cpu/i8008/8008dasm.cpp | 43 +- src/devices/cpu/i8008/8008dasm.h | 31 + src/devices/cpu/i8008/i8008.cpp | 28 +- src/devices/cpu/i8008/i8008.h | 5 +- src/devices/cpu/i8085/8085dasm.cpp | 420 +- src/devices/cpu/i8085/8085dasm.h | 25 + src/devices/cpu/i8085/i8085.cpp | 6 +- src/devices/cpu/i8085/i8085.h | 4 +- src/devices/cpu/i8089/i8089.cpp | 8 +- src/devices/cpu/i8089/i8089.h | 4 +- src/devices/cpu/i8089/i8089_dasm.cpp | 716 ++- src/devices/cpu/i8089/i8089_dasm.h | 71 + src/devices/cpu/i86/i86.cpp | 9 +- src/devices/cpu/i86/i86.h | 8 +- src/devices/cpu/i860/i860.cpp | 7 +- src/devices/cpu/i860/i860.h | 4 +- src/devices/cpu/i860/i860dasm.cpp | 378 -- src/devices/cpu/i860/i860dis.cpp | 497 +- src/devices/cpu/i860/i860dis.h | 77 + src/devices/cpu/i960/i960.cpp | 9 +- src/devices/cpu/i960/i960.h | 4 +- src/devices/cpu/i960/i960dis.cpp | 159 +- src/devices/cpu/i960/i960dis.h | 39 +- src/devices/cpu/ie15/ie15.cpp | 29 +- src/devices/cpu/ie15/ie15.h | 4 +- src/devices/cpu/ie15/ie15dasm.cpp | 19 +- src/devices/cpu/ie15/ie15dasm.h | 19 + src/devices/cpu/jaguar/jagdasm.cpp | 52 +- src/devices/cpu/jaguar/jagdasm.h | 37 + src/devices/cpu/jaguar/jaguar.cpp | 13 +- src/devices/cpu/jaguar/jaguar.h | 8 +- src/devices/cpu/lc8670/lc8670.cpp | 6 + src/devices/cpu/lc8670/lc8670.h | 32 +- src/devices/cpu/lc8670/lc8670dsm.cpp | 61 +- src/devices/cpu/lc8670/lc8670dsm.h | 54 + src/devices/cpu/lh5801/5801dasm.cpp | 203 +- src/devices/cpu/lh5801/5801dasm.h | 110 + src/devices/cpu/lh5801/lh5801.cpp | 6 +- src/devices/cpu/lh5801/lh5801.h | 4 +- src/devices/cpu/lr35902/lr35902.cpp | 8 +- src/devices/cpu/lr35902/lr35902.h | 4 +- src/devices/cpu/lr35902/lr35902d.cpp | 70 +- src/devices/cpu/lr35902/lr35902d.h | 48 + src/devices/cpu/m37710/m37710.cpp | 17 +- src/devices/cpu/m37710/m37710.h | 11 +- src/devices/cpu/m37710/m7700ds.cpp | 229 +- src/devices/cpu/m37710/m7700ds.h | 82 +- src/devices/cpu/m6502/deco16.cpp | 6 +- src/devices/cpu/m6502/deco16.h | 4 +- src/devices/cpu/m6502/deco16d.cpp | 16 + src/devices/cpu/m6502/deco16d.h | 28 + src/devices/cpu/m6502/m4510.cpp | 5 +- src/devices/cpu/m6502/m4510.h | 3 +- src/devices/cpu/m6502/m4510d.cpp | 16 + src/devices/cpu/m6502/m4510d.h | 28 + src/devices/cpu/m6502/m6502.cpp | 179 +- src/devices/cpu/m6502/m6502.h | 46 +- src/devices/cpu/m6502/m6502d.cpp | 192 + src/devices/cpu/m6502/m6502d.h | 81 + src/devices/cpu/m6502/m6502make.py | 66 +- src/devices/cpu/m6502/m6509.cpp | 6 +- src/devices/cpu/m6502/m6509.h | 4 +- src/devices/cpu/m6502/m6509d.cpp | 16 + src/devices/cpu/m6502/m6509d.h | 28 + src/devices/cpu/m6502/m6510.cpp | 5 +- src/devices/cpu/m6502/m6510.h | 4 +- src/devices/cpu/m6502/m6510d.cpp | 16 + src/devices/cpu/m6502/m6510d.h | 28 + src/devices/cpu/m6502/m65c02.cpp | 5 +- src/devices/cpu/m6502/m65c02.h | 4 +- src/devices/cpu/m6502/m65c02d.cpp | 17 + src/devices/cpu/m6502/m65c02d.h | 29 + src/devices/cpu/m6502/m65ce02.cpp | 5 +- src/devices/cpu/m6502/m65ce02.h | 4 +- src/devices/cpu/m6502/m65ce02d.cpp | 16 + src/devices/cpu/m6502/m65ce02d.h | 28 + src/devices/cpu/m6502/m740.cpp | 9 +- src/devices/cpu/m6502/m740.h | 10 +- src/devices/cpu/m6502/m740d.cpp | 21 + src/devices/cpu/m6502/m740d.h | 37 + src/devices/cpu/m6502/n2a03.cpp | 5 +- src/devices/cpu/m6502/n2a03.h | 3 +- src/devices/cpu/m6502/n2a03d.cpp | 16 + src/devices/cpu/m6502/n2a03d.h | 28 + src/devices/cpu/m6502/or65c02.lst | 0 src/devices/cpu/m6502/r65c02.cpp | 5 +- src/devices/cpu/m6502/r65c02.h | 4 +- src/devices/cpu/m6502/r65c02d.cpp | 16 + src/devices/cpu/m6502/r65c02d.h | 28 + src/devices/cpu/m6800/6800dasm.cpp | 149 +- src/devices/cpu/m6800/6800dasm.h | 76 + src/devices/cpu/m6800/m6800.cpp | 24 +- src/devices/cpu/m6800/m6800.h | 11 +- src/devices/cpu/m6800/m6801.cpp | 24 +- src/devices/cpu/m6800/m6801.h | 8 +- src/devices/cpu/m68000/m68000.h | 82 +- src/devices/cpu/m68000/m68kcpu.cpp | 103 +- src/devices/cpu/m68000/m68kdasm.cpp | 4140 ++++++-------- src/devices/cpu/m68000/m68kdasm.h | 454 ++ src/devices/cpu/m6805/6805dasm.cpp | 184 +- src/devices/cpu/m6805/6805dasm.h | 100 + src/devices/cpu/m6805/m6805.cpp | 29 +- src/devices/cpu/m6805/m6805.h | 8 +- src/devices/cpu/m6805/m6805defs.h | 69 - src/devices/cpu/m6805/m68705.cpp | 29 +- src/devices/cpu/m6805/m68705.h | 21 +- src/devices/cpu/m6805/m68hc05.cpp | 38 +- src/devices/cpu/m6805/m68hc05.h | 28 +- src/devices/cpu/m6809/6x09dasm.cpp | 298 +- src/devices/cpu/m6809/6x09dasm.h | 166 + src/devices/cpu/m6809/hd6309.cpp | 32 +- src/devices/cpu/m6809/hd6309.h | 4 +- src/devices/cpu/m6809/konami.cpp | 8 +- src/devices/cpu/m6809/konami.h | 2 +- src/devices/cpu/m6809/m6809.cpp | 30 +- src/devices/cpu/m6809/m6809.h | 4 +- src/devices/cpu/mb86233/mb86233.cpp | 6 +- src/devices/cpu/mb86233/mb86233.h | 4 +- src/devices/cpu/mb86233/mb86233d.cpp | 51 +- src/devices/cpu/mb86233/mb86233d.h | 26 + src/devices/cpu/mb86235/mb86235.cpp | 6 +- src/devices/cpu/mb86235/mb86235.h | 7 +- src/devices/cpu/mb86235/mb86235d.cpp | 57 +- src/devices/cpu/mb86235/mb86235d.h | 42 + src/devices/cpu/mb88xx/mb88dasm.cpp | 14 +- src/devices/cpu/mb88xx/mb88dasm.h | 28 + src/devices/cpu/mb88xx/mb88xx.cpp | 6 +- src/devices/cpu/mb88xx/mb88xx.h | 7 +- src/devices/cpu/mc68hc11/hc11dasm.cpp | 133 +- src/devices/cpu/mc68hc11/hc11dasm.h | 55 + src/devices/cpu/mc68hc11/mc68hc11.cpp | 6 +- src/devices/cpu/mc68hc11/mc68hc11.h | 4 +- src/devices/cpu/mcs40/mcs40.cpp | 36 +- src/devices/cpu/mcs40/mcs40.h | 18 +- src/devices/cpu/mcs40/mcs40dasm.cpp | 93 +- src/devices/cpu/mcs40/mcs40dasm.h | 81 + src/devices/cpu/mcs48/mcs48.cpp | 12 +- src/devices/cpu/mcs48/mcs48.h | 6 +- src/devices/cpu/mcs48/mcs48dsm.cpp | 200 +- src/devices/cpu/mcs48/mcs48dsm.h | 31 + src/devices/cpu/mcs51/mcs51.cpp | 38 +- src/devices/cpu/mcs51/mcs51.h | 14 +- src/devices/cpu/mcs51/mcs51dasm.cpp | 721 ++- src/devices/cpu/mcs51/mcs51dasm.h | 106 + src/devices/cpu/mcs96/i8x9x.cpp | 5 +- src/devices/cpu/mcs96/i8x9x.h | 3 +- src/devices/cpu/mcs96/i8x9xd.cpp | 19 + src/devices/cpu/mcs96/i8x9xd.h | 26 + src/devices/cpu/mcs96/i8xc196.cpp | 5 +- src/devices/cpu/mcs96/i8xc196.h | 3 +- src/devices/cpu/mcs96/i8xc196d.cpp | 18 + src/devices/cpu/mcs96/i8xc196d.h | 26 + src/devices/cpu/mcs96/mcs96.cpp | 270 - src/devices/cpu/mcs96/mcs96.h | 38 - src/devices/cpu/mcs96/mcs96d.cpp | 278 + src/devices/cpu/mcs96/mcs96d.h | 64 + src/devices/cpu/mcs96/mcs96make.py | 25 +- src/devices/cpu/melps4/m58846.cpp | 9 - src/devices/cpu/melps4/m58846.h | 3 - src/devices/cpu/melps4/melps4.cpp | 6 + src/devices/cpu/melps4/melps4.h | 4 +- src/devices/cpu/melps4/melps4d.cpp | 54 +- src/devices/cpu/melps4/melps4d.h | 52 + src/devices/cpu/minx/minx.cpp | 6 +- src/devices/cpu/minx/minx.h | 4 +- src/devices/cpu/minx/minxd.cpp | 127 +- src/devices/cpu/minx/minxd.h | 89 + src/devices/cpu/mips/mips3.cpp | 10 +- src/devices/cpu/mips/mips3.h | 11 +- src/devices/cpu/mips/mips3drc.cpp | 9 +- src/devices/cpu/mips/mips3dsm.cpp | 104 +- src/devices/cpu/mips/mips3dsm.h | 40 + src/devices/cpu/mips/r3000.cpp | 35 +- src/devices/cpu/mips/r3000.h | 4 +- src/devices/cpu/mips/r3kdasm.cpp | 58 +- src/devices/cpu/mips/r3kdasm.h | 36 + src/devices/cpu/mn10200/mn10200.cpp | 6 +- src/devices/cpu/mn10200/mn10200.h | 4 +- src/devices/cpu/mn10200/mn102dis.cpp | 380 +- src/devices/cpu/mn10200/mn102dis.h | 28 + src/devices/cpu/nanoprocessor/nanoprocessor.cpp | 102 +- src/devices/cpu/nanoprocessor/nanoprocessor.h | 4 +- .../cpu/nanoprocessor/nanoprocessor_dasm.cpp | 156 +- src/devices/cpu/nanoprocessor/nanoprocessor_dasm.h | 44 + src/devices/cpu/nec/nec.cpp | 10 +- src/devices/cpu/nec/nec.h | 4 +- src/devices/cpu/nec/nec_common.h | 9 - src/devices/cpu/nec/necdasm.cpp | 521 +- src/devices/cpu/nec/necdasm.h | 129 + src/devices/cpu/nec/necea.h | 34 +- src/devices/cpu/nec/necinstr.hxx | 144 +- src/devices/cpu/nec/necmacro.h | 8 +- src/devices/cpu/nec/necmodrm.h | 22 +- src/devices/cpu/nec/necpriv.h | 8 +- src/devices/cpu/nec/v25.cpp | 10 +- src/devices/cpu/nec/v25.h | 4 +- src/devices/cpu/nec/v25instr.hxx | 32 +- src/devices/cpu/nec/v25priv.h | 8 +- src/devices/cpu/patinhofeio/patinho_feio.cpp | 6 +- src/devices/cpu/patinhofeio/patinho_feio_dasm.cpp | 57 +- src/devices/cpu/patinhofeio/patinho_feio_dasm.h | 19 + src/devices/cpu/patinhofeio/patinhofeio_cpu.h | 6 +- src/devices/cpu/pdp1/pdp1.cpp | 6 +- src/devices/cpu/pdp1/pdp1.h | 4 +- src/devices/cpu/pdp1/pdp1dasm.cpp | 22 +- src/devices/cpu/pdp1/pdp1dasm.h | 22 + src/devices/cpu/pdp1/tx0.cpp | 12 +- src/devices/cpu/pdp1/tx0.h | 8 +- src/devices/cpu/pdp1/tx0dasm.cpp | 20 +- src/devices/cpu/pdp1/tx0dasm.h | 29 + src/devices/cpu/pdp8/pdp8.cpp | 32 +- src/devices/cpu/pdp8/pdp8.h | 4 +- src/devices/cpu/pdp8/pdp8dasm.cpp | 21 +- src/devices/cpu/pdp8/pdp8dasm.h | 24 + src/devices/cpu/pic16c5x/16c5xdsm.cpp | 147 +- src/devices/cpu/pic16c5x/16c5xdsm.h | 58 + src/devices/cpu/pic16c5x/dis16c5x.cpp | 136 - src/devices/cpu/pic16c5x/pic16c5x.cpp | 6 +- src/devices/cpu/pic16c5x/pic16c5x.h | 4 +- src/devices/cpu/pic16c62x/16c62xdsm.cpp | 151 +- src/devices/cpu/pic16c62x/16c62xdsm.h | 62 + src/devices/cpu/pic16c62x/dis16c62x.cpp | 138 - src/devices/cpu/pic16c62x/pic16c62x.cpp | 6 +- src/devices/cpu/pic16c62x/pic16c62x.h | 4 +- src/devices/cpu/powerpc/ppc.h | 4 +- src/devices/cpu/powerpc/ppc_dasm.cpp | 740 +-- src/devices/cpu/powerpc/ppc_dasm.h | 142 + src/devices/cpu/powerpc/ppccom.cpp | 8 +- src/devices/cpu/powerpc/ppcdrc.cpp | 10 +- src/devices/cpu/pps4/pps4.cpp | 6 +- src/devices/cpu/pps4/pps4.h | 4 +- src/devices/cpu/pps4/pps4dasm.cpp | 52 +- src/devices/cpu/pps4/pps4dasm.h | 59 + src/devices/cpu/psx/dismips.cpp | 332 -- src/devices/cpu/psx/dismips.mak | 2 - src/devices/cpu/psx/psx.cpp | 6 +- src/devices/cpu/psx/psx.h | 20 +- src/devices/cpu/psx/psxdasm.cpp | 200 +- src/devices/cpu/psx/psxdasm.h | 56 + src/devices/cpu/rsp/rsp.cpp | 24 +- src/devices/cpu/rsp/rsp.h | 7 +- src/devices/cpu/rsp/rsp_dasm.cpp | 53 +- src/devices/cpu/rsp/rsp_dasm.h | 38 + src/devices/cpu/rsp/rspcp2d.cpp | 4 +- src/devices/cpu/rsp/rspdrc.cpp | 11 +- src/devices/cpu/s2650/2650dasm.cpp | 788 +-- src/devices/cpu/s2650/2650dasm.h | 48 + src/devices/cpu/s2650/s2650.cpp | 11 +- src/devices/cpu/s2650/s2650.h | 8 +- src/devices/cpu/saturn/saturn.cpp | 11 +- src/devices/cpu/saturn/saturn.h | 8 +- src/devices/cpu/saturn/saturnds.cpp | 1006 ++-- src/devices/cpu/saturn/saturnds.h | 215 + src/devices/cpu/sc61860/sc61860.cpp | 8 +- src/devices/cpu/sc61860/sc61860.h | 4 +- src/devices/cpu/sc61860/scdasm.cpp | 49 +- src/devices/cpu/sc61860/scdasm.h | 50 + src/devices/cpu/scmp/scmp.cpp | 6 +- src/devices/cpu/scmp/scmp.h | 4 +- src/devices/cpu/scmp/scmpdasm.cpp | 13 +- src/devices/cpu/scmp/scmpdasm.h | 26 + src/devices/cpu/score/score.cpp | 6 + src/devices/cpu/score/score.h | 20 +- src/devices/cpu/score/scoredsm.cpp | 47 +- src/devices/cpu/score/scoredsm.h | 43 + src/devices/cpu/scudsp/scudsp.cpp | 6 +- src/devices/cpu/scudsp/scudsp.h | 7 +- src/devices/cpu/scudsp/scudspdasm.cpp | 144 +- src/devices/cpu/scudsp/scudspdasm.h | 33 + src/devices/cpu/se3208/se3208.cpp | 6 +- src/devices/cpu/se3208/se3208.h | 4 +- src/devices/cpu/se3208/se3208dis.cpp | 324 +- src/devices/cpu/se3208/se3208dis.h | 103 + src/devices/cpu/sh/sh.cpp | 9 +- src/devices/cpu/sh/sh.h | 2 - src/devices/cpu/sh/sh2.cpp | 8 +- src/devices/cpu/sh/sh2.h | 5 +- src/devices/cpu/sh/sh4.cpp | 28 +- src/devices/cpu/sh/sh4.h | 6 +- src/devices/cpu/sh/sh_dasm.cpp | 172 +- src/devices/cpu/sh/sh_dasm.h | 45 + src/devices/cpu/sharc/sharc.cpp | 6 +- src/devices/cpu/sharc/sharc.h | 5 +- src/devices/cpu/sharc/sharcdsm.cpp | 764 +-- src/devices/cpu/sharc/sharcdsm.h | 129 +- src/devices/cpu/sharc/sharcops.hxx | 4 - src/devices/cpu/sm510/sm500.h | 4 +- src/devices/cpu/sm510/sm500core.cpp | 6 +- src/devices/cpu/sm510/sm510.h | 8 +- src/devices/cpu/sm510/sm510core.cpp | 6 +- src/devices/cpu/sm510/sm510d.cpp | 188 +- src/devices/cpu/sm510/sm510d.h | 131 + src/devices/cpu/sm510/sm511core.cpp | 6 +- src/devices/cpu/sm510/sm590.h | 2 +- src/devices/cpu/sm510/sm590core.cpp | 7 +- src/devices/cpu/sm510/sm5acore.cpp | 7 +- src/devices/cpu/sm8500/sm8500.cpp | 6 +- src/devices/cpu/sm8500/sm8500.h | 4 +- src/devices/cpu/sm8500/sm8500d.cpp | 211 +- src/devices/cpu/sm8500/sm8500d.h | 68 + src/devices/cpu/sparc/mb86901.cpp | 32 +- src/devices/cpu/sparc/sparc.h | 15 +- src/devices/cpu/sparc/sparcdasm.cpp | 159 +- src/devices/cpu/sparc/sparcdasm.h | 36 +- src/devices/cpu/spc700/spc700.cpp | 4 +- src/devices/cpu/spc700/spc700.h | 4 +- src/devices/cpu/spc700/spc700ds.cpp | 119 +- src/devices/cpu/spc700/spc700ds.h | 43 +- src/devices/cpu/ssem/ssem.cpp | 32 +- src/devices/cpu/ssem/ssem.h | 6 +- src/devices/cpu/ssem/ssemdasm.cpp | 24 +- src/devices/cpu/ssem/ssemdasm.h | 28 + src/devices/cpu/ssp1601/ssp1601.cpp | 6 +- src/devices/cpu/ssp1601/ssp1601.h | 4 +- src/devices/cpu/ssp1601/ssp1601d.cpp | 64 +- src/devices/cpu/ssp1601/ssp1601d.h | 37 + src/devices/cpu/superfx/sfx_dasm.cpp | 20 +- src/devices/cpu/superfx/sfx_dasm.h | 36 + src/devices/cpu/superfx/superfx.cpp | 12 +- src/devices/cpu/superfx/superfx.h | 11 +- src/devices/cpu/t11/t11.cpp | 7 +- src/devices/cpu/t11/t11.h | 4 +- src/devices/cpu/t11/t11dasm.cpp | 182 +- src/devices/cpu/t11/t11dasm.h | 33 + src/devices/cpu/tlcs870/tlcs870.cpp | 149 +- src/devices/cpu/tlcs870/tlcs870.h | 6 +- src/devices/cpu/tlcs870/tlcs870d.cpp | 2263 ++++++++ src/devices/cpu/tlcs870/tlcs870d.h | 89 + src/devices/cpu/tlcs90/tlcs90.cpp | 88 +- src/devices/cpu/tlcs90/tlcs90.h | 6 +- src/devices/cpu/tlcs90/tlcs90d.cpp | 952 ++++ src/devices/cpu/tlcs90/tlcs90d.h | 65 + src/devices/cpu/tlcs900/dasm900.cpp | 386 +- src/devices/cpu/tlcs900/dasm900.h | 111 + src/devices/cpu/tlcs900/tlcs900.cpp | 6 +- src/devices/cpu/tlcs900/tlcs900.h | 4 +- src/devices/cpu/tms1000/tms0980.cpp | 8 +- src/devices/cpu/tms1000/tms0980.h | 4 +- src/devices/cpu/tms1000/tms1000.cpp | 6 +- src/devices/cpu/tms1000/tms1000.h | 3 +- src/devices/cpu/tms1000/tms1100.cpp | 7 +- src/devices/cpu/tms1000/tms1100.h | 2 +- src/devices/cpu/tms1000/tms1k_base.cpp | 2 +- src/devices/cpu/tms1000/tms1k_base.h | 4 - src/devices/cpu/tms1000/tms1k_dasm.cpp | 158 +- src/devices/cpu/tms1000/tms1k_dasm.h | 98 + src/devices/cpu/tms1000/tp0320.cpp | 6 +- src/devices/cpu/tms1000/tp0320.h | 2 +- src/devices/cpu/tms32010/32010dsm.cpp | 277 +- src/devices/cpu/tms32010/32010dsm.h | 59 + src/devices/cpu/tms32010/tms32010.cpp | 6 +- src/devices/cpu/tms32010/tms32010.h | 4 +- src/devices/cpu/tms32025/32025dsm.cpp | 576 +- src/devices/cpu/tms32025/32025dsm.h | 66 + src/devices/cpu/tms32025/dis32025.cpp | 137 - src/devices/cpu/tms32025/tms32025.cpp | 7 +- src/devices/cpu/tms32025/tms32025.h | 4 +- src/devices/cpu/tms32031/dis32031.cpp | 77 +- src/devices/cpu/tms32031/dis32031.h | 51 + src/devices/cpu/tms32031/tms32031.cpp | 30 +- src/devices/cpu/tms32031/tms32031.h | 4 +- src/devices/cpu/tms32051/dis32051.cpp | 176 +- src/devices/cpu/tms32051/dis32051.h | 32 + src/devices/cpu/tms32051/tms32051.cpp | 6 +- src/devices/cpu/tms32051/tms32051.h | 4 +- src/devices/cpu/tms32082/dis_mp.cpp | 173 +- src/devices/cpu/tms32082/dis_mp.h | 35 + src/devices/cpu/tms32082/dis_pp.cpp | 135 +- src/devices/cpu/tms32082/dis_pp.h | 33 + src/devices/cpu/tms32082/tms32082.cpp | 16 +- src/devices/cpu/tms32082/tms32082.h | 8 +- src/devices/cpu/tms34010/34010dsm.cpp | 360 +- src/devices/cpu/tms34010/34010dsm.h | 52 + src/devices/cpu/tms34010/34010gfx.hxx | 6 + src/devices/cpu/tms34010/dis34010.cpp | 115 - src/devices/cpu/tms34010/tms34010.cpp | 15 +- src/devices/cpu/tms34010/tms34010.h | 12 +- src/devices/cpu/tms57002/57002dsm.cpp | 17 +- src/devices/cpu/tms57002/57002dsm.h | 30 + src/devices/cpu/tms57002/tms57002.cpp | 21 +- src/devices/cpu/tms57002/tms57002.h | 4 +- src/devices/cpu/tms57002/tms57kdec.cpp | 9 +- src/devices/cpu/tms7000/7000dasm.cpp | 120 +- src/devices/cpu/tms7000/7000dasm.h | 42 + src/devices/cpu/tms7000/tms7000.cpp | 6 +- src/devices/cpu/tms7000/tms7000.h | 4 +- src/devices/cpu/tms9900/9900dasm.cpp | 253 +- src/devices/cpu/tms9900/9900dasm.h | 136 + src/devices/cpu/tms9900/ti990_10.cpp | 17 +- src/devices/cpu/tms9900/ti990_10.h | 4 +- src/devices/cpu/tms9900/tms9900.cpp | 15 +- src/devices/cpu/tms9900/tms9900.h | 4 +- src/devices/cpu/tms9900/tms9980a.cpp | 15 +- src/devices/cpu/tms9900/tms9980a.h | 5 +- src/devices/cpu/tms9900/tms9995.cpp | 16 +- src/devices/cpu/tms9900/tms9995.h | 4 +- src/devices/cpu/ucom4/ucom4.cpp | 7 +- src/devices/cpu/ucom4/ucom4.h | 4 +- src/devices/cpu/ucom4/ucom4d.cpp | 60 +- src/devices/cpu/ucom4/ucom4d.h | 48 + src/devices/cpu/unsp/unsp.cpp | 6 +- src/devices/cpu/unsp/unsp.h | 4 +- src/devices/cpu/unsp/unspdasm.cpp | 21 +- src/devices/cpu/unsp/unspdasm.h | 32 + src/devices/cpu/upd7725/dasm7725.cpp | 13 +- src/devices/cpu/upd7725/dasm7725.h | 27 + src/devices/cpu/upd7725/upd7725.cpp | 29 +- src/devices/cpu/upd7725/upd7725.h | 4 +- src/devices/cpu/upd7810/upd7810.cpp | 21 +- src/devices/cpu/upd7810/upd7810.h | 10 +- src/devices/cpu/upd7810/upd7810_dasm.cpp | 5738 ++++++++++---------- src/devices/cpu/upd7810/upd7810_dasm.h | 291 + src/devices/cpu/v30mz/v30mz.cpp | 6 +- src/devices/cpu/v30mz/v30mz.h | 4 +- src/devices/cpu/v60/v60.cpp | 13 +- src/devices/cpu/v60/v60.h | 7 +- src/devices/cpu/v60/v60d.cpp | 1445 +++-- src/devices/cpu/v60/v60d.h | 359 ++ src/devices/cpu/v810/v810.cpp | 6 +- src/devices/cpu/v810/v810.h | 4 +- src/devices/cpu/v810/v810dasm.cpp | 24 +- src/devices/cpu/v810/v810dasm.h | 27 + src/devices/cpu/x86log.cpp | 30 +- src/devices/cpu/z180/z180.cpp | 8 +- src/devices/cpu/z180/z180.h | 4 +- src/devices/cpu/z180/z180dasm.cpp | 87 +- src/devices/cpu/z180/z180dasm.h | 54 + src/devices/cpu/z8/z8.cpp | 8 +- src/devices/cpu/z8/z8.h | 4 +- src/devices/cpu/z8/z8dasm.cpp | 33 +- src/devices/cpu/z8/z8dasm.h | 24 + src/devices/cpu/z80/z80.cpp | 8 +- src/devices/cpu/z80/z80.h | 4 +- src/devices/cpu/z80/z80dasm.cpp | 164 +- src/devices/cpu/z80/z80dasm.h | 56 + src/devices/cpu/z8000/8000dasm.cpp | 624 ++- src/devices/cpu/z8000/8000dasm.h | 50 + src/devices/cpu/z8000/z8000.cpp | 105 +- src/devices/cpu/z8000/z8000.h | 41 +- src/devices/cpu/z8000/z8000cpu.h | 2 +- src/devices/cpu/z8000/z8000ops.hxx | 44 +- src/devices/cpu/z8000/z8000tbl.hxx | 1100 ++-- src/devices/machine/68307.h | 3 - src/devices/machine/netlist.cpp | 46 +- src/devices/machine/netlist.h | 23 +- src/emu/debug/debugbuf.cpp | 1381 +++++ src/emu/debug/debugbuf.h | 97 + src/emu/debug/debugcmd.cpp | 172 +- src/emu/debug/debugcpu.cpp | 113 +- src/emu/debug/debugcpu.h | 1 - src/emu/debug/dvdisasm.cpp | 514 +- src/emu/debug/dvdisasm.h | 59 +- src/emu/devcpu.h | 12 - src/emu/didisasm.cpp | 113 +- src/emu/didisasm.h | 83 +- src/emu/emumem.h | 2 + src/lib/util/disasmintf.cpp | 47 + src/lib/util/disasmintf.h | 69 + src/mame/drivers/palm.cpp | 2 +- src/mame/drivers/palm_dbg.hxx | 10 +- src/mame/drivers/vgmplay.cpp | 232 +- src/mame/etc/template_cpu.cpp | 4 +- src/mame/etc/template_cpu.h | 5 +- src/mame/includes/coco.h | 4 +- src/mame/includes/dgn_beta.h | 2 +- src/mame/includes/mac.h | 2 +- src/mame/machine/apollo_dbg.cpp | 28 +- src/mame/machine/coco.cpp | 10 +- src/mame/machine/deco222.cpp | 28 + src/mame/machine/deco222.h | 22 +- src/mame/machine/decocpu6.cpp | 15 + src/mame/machine/decocpu6.h | 10 +- src/mame/machine/decocpu7.cpp | 19 + src/mame/machine/decocpu7.h | 13 +- src/mame/machine/dgn_beta.cpp | 4 +- src/mame/machine/mac.cpp | 6 +- src/tools/unidasm.cpp | 1668 ++++-- 656 files changed, 36307 insertions(+), 26163 deletions(-) create mode 100644 docs/source/techspecs/device_disasm_interface.rst create mode 100644 src/devices/cpu/8x300/8x300dasm.h create mode 100644 src/devices/cpu/adsp2100/2100dasm.h create mode 100644 src/devices/cpu/alph8201/8201dasm.h create mode 100644 src/devices/cpu/alto2/alto2dsm.h create mode 100644 src/devices/cpu/am29000/am29dasm.h create mode 100644 src/devices/cpu/amis2000/amis2000d.h create mode 100644 src/devices/cpu/apexc/apexcdsm.h create mode 100644 src/devices/cpu/arc/arcdasm.h delete mode 100644 src/devices/cpu/arcompact/arcompact_common.cpp delete mode 100644 src/devices/cpu/arcompact/arcompact_common.h create mode 100644 src/devices/cpu/arcompact/arcompactdasm.h delete mode 100644 src/devices/cpu/arcompact/arcompactdasm_dispatch.h delete mode 100644 src/devices/cpu/arcompact/arcompactdasm_ops.h create mode 100644 src/devices/cpu/arm/armdasm.h create mode 100644 src/devices/cpu/arm7/arm7dasm.h create mode 100644 src/devices/cpu/asap/asapdasm.h create mode 100644 src/devices/cpu/avr8/avr8dasm.h create mode 100644 src/devices/cpu/capricorn/capricorn_dasm.h create mode 100644 src/devices/cpu/ccpu/ccpudasm.h create mode 100644 src/devices/cpu/clipper/clipperd.h create mode 100644 src/devices/cpu/cop400/cop410ds.h create mode 100644 src/devices/cpu/cop400/cop420ds.h create mode 100644 src/devices/cpu/cop400/cop424ds.h create mode 100644 src/devices/cpu/cop400/cop444ds.h create mode 100644 src/devices/cpu/cosmac/cosdasm.h create mode 100644 src/devices/cpu/cp1610/1610dasm.h create mode 100644 src/devices/cpu/cubeqcpu/cubedasm.h create mode 100644 src/devices/cpu/dsp16/dsp16dis.h create mode 100644 src/devices/cpu/dsp32/dsp32dis.h create mode 100644 src/devices/cpu/dsp56k/dsp56dsm.h create mode 100644 src/devices/cpu/e0c6200/e0c6200d.h create mode 100644 src/devices/cpu/e132xs/32xsdasm.h create mode 100644 src/devices/cpu/es5510/es5510d.cpp create mode 100644 src/devices/cpu/es5510/es5510d.h create mode 100644 src/devices/cpu/esrip/esripdsm.h create mode 100644 src/devices/cpu/f8/f8dasm.h create mode 100644 src/devices/cpu/h6280/6280dasm.h create mode 100644 src/devices/cpu/h8/h8d.cpp create mode 100644 src/devices/cpu/h8/h8d.h create mode 100644 src/devices/cpu/h8/h8hd.cpp create mode 100644 src/devices/cpu/h8/h8hd.h create mode 100644 src/devices/cpu/h8/h8s2000d.cpp create mode 100644 src/devices/cpu/h8/h8s2000d.h create mode 100644 src/devices/cpu/h8/h8s2600d.cpp create mode 100644 src/devices/cpu/h8/h8s2600d.h create mode 100644 src/devices/cpu/hcd62121/hcd62121d.h create mode 100644 src/devices/cpu/hd61700/hd61700d.h create mode 100644 src/devices/cpu/hmcs40/hmcs40d.h create mode 100644 src/devices/cpu/hphybrid/hphybrid_dasm.h create mode 100644 src/devices/cpu/i8008/8008dasm.h create mode 100644 src/devices/cpu/i8085/8085dasm.h create mode 100644 src/devices/cpu/i8089/i8089_dasm.h delete mode 100644 src/devices/cpu/i860/i860dasm.cpp create mode 100644 src/devices/cpu/i860/i860dis.h create mode 100644 src/devices/cpu/ie15/ie15dasm.h create mode 100644 src/devices/cpu/jaguar/jagdasm.h create mode 100644 src/devices/cpu/lc8670/lc8670dsm.h create mode 100644 src/devices/cpu/lh5801/5801dasm.h create mode 100644 src/devices/cpu/lr35902/lr35902d.h create mode 100644 src/devices/cpu/m6502/deco16d.cpp create mode 100644 src/devices/cpu/m6502/deco16d.h create mode 100644 src/devices/cpu/m6502/m4510d.cpp create mode 100644 src/devices/cpu/m6502/m4510d.h create mode 100644 src/devices/cpu/m6502/m6502d.cpp create mode 100644 src/devices/cpu/m6502/m6502d.h create mode 100644 src/devices/cpu/m6502/m6509d.cpp create mode 100644 src/devices/cpu/m6502/m6509d.h create mode 100644 src/devices/cpu/m6502/m6510d.cpp create mode 100644 src/devices/cpu/m6502/m6510d.h create mode 100644 src/devices/cpu/m6502/m65c02d.cpp create mode 100644 src/devices/cpu/m6502/m65c02d.h create mode 100644 src/devices/cpu/m6502/m65ce02d.cpp create mode 100644 src/devices/cpu/m6502/m65ce02d.h create mode 100644 src/devices/cpu/m6502/m740d.cpp create mode 100644 src/devices/cpu/m6502/m740d.h create mode 100644 src/devices/cpu/m6502/n2a03d.cpp create mode 100644 src/devices/cpu/m6502/n2a03d.h create mode 100644 src/devices/cpu/m6502/or65c02.lst create mode 100644 src/devices/cpu/m6502/r65c02d.cpp create mode 100644 src/devices/cpu/m6502/r65c02d.h create mode 100644 src/devices/cpu/m6800/6800dasm.h create mode 100644 src/devices/cpu/m68000/m68kdasm.h create mode 100644 src/devices/cpu/m6805/6805dasm.h create mode 100644 src/devices/cpu/m6809/6x09dasm.h create mode 100644 src/devices/cpu/mb86233/mb86233d.h create mode 100644 src/devices/cpu/mb86235/mb86235d.h create mode 100644 src/devices/cpu/mb88xx/mb88dasm.h create mode 100644 src/devices/cpu/mc68hc11/hc11dasm.h create mode 100644 src/devices/cpu/mcs40/mcs40dasm.h create mode 100644 src/devices/cpu/mcs48/mcs48dsm.h create mode 100644 src/devices/cpu/mcs51/mcs51dasm.h create mode 100644 src/devices/cpu/mcs96/i8x9xd.cpp create mode 100644 src/devices/cpu/mcs96/i8x9xd.h create mode 100644 src/devices/cpu/mcs96/i8xc196d.cpp create mode 100644 src/devices/cpu/mcs96/i8xc196d.h create mode 100644 src/devices/cpu/mcs96/mcs96d.cpp create mode 100644 src/devices/cpu/mcs96/mcs96d.h create mode 100644 src/devices/cpu/melps4/melps4d.h create mode 100644 src/devices/cpu/minx/minxd.h create mode 100644 src/devices/cpu/mips/mips3dsm.h create mode 100644 src/devices/cpu/mips/r3kdasm.h create mode 100644 src/devices/cpu/mn10200/mn102dis.h create mode 100644 src/devices/cpu/nanoprocessor/nanoprocessor_dasm.h delete mode 100644 src/devices/cpu/nec/nec_common.h create mode 100644 src/devices/cpu/nec/necdasm.h create mode 100644 src/devices/cpu/patinhofeio/patinho_feio_dasm.h create mode 100644 src/devices/cpu/pdp1/pdp1dasm.h create mode 100644 src/devices/cpu/pdp1/tx0dasm.h create mode 100644 src/devices/cpu/pdp8/pdp8dasm.h create mode 100644 src/devices/cpu/pic16c5x/16c5xdsm.h delete mode 100644 src/devices/cpu/pic16c5x/dis16c5x.cpp create mode 100644 src/devices/cpu/pic16c62x/16c62xdsm.h delete mode 100644 src/devices/cpu/pic16c62x/dis16c62x.cpp create mode 100644 src/devices/cpu/powerpc/ppc_dasm.h create mode 100644 src/devices/cpu/pps4/pps4dasm.h delete mode 100644 src/devices/cpu/psx/dismips.cpp delete mode 100644 src/devices/cpu/psx/dismips.mak create mode 100644 src/devices/cpu/psx/psxdasm.h create mode 100644 src/devices/cpu/rsp/rsp_dasm.h create mode 100644 src/devices/cpu/s2650/2650dasm.h create mode 100644 src/devices/cpu/saturn/saturnds.h create mode 100644 src/devices/cpu/sc61860/scdasm.h create mode 100644 src/devices/cpu/scmp/scmpdasm.h create mode 100644 src/devices/cpu/score/scoredsm.h create mode 100644 src/devices/cpu/scudsp/scudspdasm.h create mode 100644 src/devices/cpu/se3208/se3208dis.h create mode 100644 src/devices/cpu/sh/sh_dasm.h create mode 100644 src/devices/cpu/sm510/sm510d.h create mode 100644 src/devices/cpu/sm8500/sm8500d.h create mode 100644 src/devices/cpu/ssem/ssemdasm.h create mode 100644 src/devices/cpu/ssp1601/ssp1601d.h create mode 100644 src/devices/cpu/superfx/sfx_dasm.h create mode 100644 src/devices/cpu/t11/t11dasm.h create mode 100644 src/devices/cpu/tlcs870/tlcs870d.cpp create mode 100644 src/devices/cpu/tlcs870/tlcs870d.h create mode 100644 src/devices/cpu/tlcs90/tlcs90d.cpp create mode 100644 src/devices/cpu/tlcs90/tlcs90d.h create mode 100644 src/devices/cpu/tlcs900/dasm900.h create mode 100644 src/devices/cpu/tms1000/tms1k_dasm.h create mode 100644 src/devices/cpu/tms32010/32010dsm.h create mode 100644 src/devices/cpu/tms32025/32025dsm.h delete mode 100644 src/devices/cpu/tms32025/dis32025.cpp create mode 100644 src/devices/cpu/tms32031/dis32031.h create mode 100644 src/devices/cpu/tms32051/dis32051.h create mode 100644 src/devices/cpu/tms32082/dis_mp.h create mode 100644 src/devices/cpu/tms32082/dis_pp.h create mode 100644 src/devices/cpu/tms34010/34010dsm.h delete mode 100644 src/devices/cpu/tms34010/dis34010.cpp create mode 100644 src/devices/cpu/tms57002/57002dsm.h create mode 100644 src/devices/cpu/tms7000/7000dasm.h create mode 100644 src/devices/cpu/tms9900/9900dasm.h create mode 100644 src/devices/cpu/ucom4/ucom4d.h create mode 100644 src/devices/cpu/unsp/unspdasm.h create mode 100644 src/devices/cpu/upd7725/dasm7725.h create mode 100644 src/devices/cpu/upd7810/upd7810_dasm.h create mode 100644 src/devices/cpu/v60/v60d.h create mode 100644 src/devices/cpu/v810/v810dasm.h create mode 100644 src/devices/cpu/z180/z180dasm.h create mode 100644 src/devices/cpu/z8/z8dasm.h create mode 100644 src/devices/cpu/z80/z80dasm.h create mode 100644 src/devices/cpu/z8000/8000dasm.h create mode 100644 src/emu/debug/debugbuf.cpp create mode 100644 src/emu/debug/debugbuf.h create mode 100644 src/lib/util/disasmintf.cpp create mode 100644 src/lib/util/disasmintf.h diff --git a/docs/source/techspecs/device_disasm_interface.rst b/docs/source/techspecs/device_disasm_interface.rst new file mode 100644 index 00000000000..beacaf8e6df --- /dev/null +++ b/docs/source/techspecs/device_disasm_interface.rst @@ -0,0 +1,204 @@ +The device_disasm_interface and the disassemblers +================================================= + +1. Capabilities +--------------- + +The disassemblers are classes that provide disassembly and opcode +meta-information for the cpu cores and **unidasm**. The +**device_disasm_interface** connects a cpu core with its disassembler. + +2. The disassemblers +-------------------- + +2.1. Definition +~~~~~~~~~~~~~~~ + +A disassembler is a class that derives from +**util::disasm_interface**. It then has two required methods to +implement, **opcode_alignment** and **disassemble**, and 6 optional, +**interface_flags**, **page_address_bits**, **pc_linear_to_real**, +**pc_real_to_linear**, and one with four possible variants, +**decrypt8/16/32/64**. + + +2.2. opcode_alignment +~~~~~~~~~~~~~~~~~~~~~ + +| u32 \ **opcode_alignment**\ () const + +Returns the required alignment of opcodes by the cpu, in PC-units. In +other words, the required alignment for the PC register of the cpu. +Tends to be 1 (almost everything), 2 (68000...), 4 (mips, ppc...), +which an exceptional 8 (tms 32082 parallel processor) and 16 +(tms32010, instructions are 16-bits aligned and the PC targets bits). +It must be a power-of-two or things will break. + +Note that processors like the tms32031 which have 32-bits instructions +but where the PC targets 32-bits values have an alignment of 1. + +2.3. disassemble +~~~~~~~~~~~~~~~~ + +| offs_t \ **disassemble**\ (std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) + +This is the method where the real work is done. This method must +disassemble the instruction at address *pc* and write the result to +*stream*. The values to decode are retrieved from the *opcode* +buffer. A **data_buffer** object offers four accessor methods: + +| u8 util::disasm_interface::data_buffer::\ **r8**\ (offs_t pc) const +| u16 util::disasm_interface::data_buffer::\ **r16**\ (offs_t pc) const +| u32 util::disasm_interface::data_buffer::\ **r32**\ (offs_t pc) const +| u64 util::disasm_interface::data_buffer::\ **r64**\ (offs_t pc) const + +They read the data at a given address and take endianness and +nonlinear PCs for larger-than-bus-width accesses. The debugger +variant also caches the read data in one block, so for that reason one +should not read data too far from the base pc (e.g. stay within 16K or +so, careful when trying to follow indirect accesses). + +A number of CPUs have an external signal that splits fetches into an +opcode part and a parameter part. This is for instance the M1 signal +of the z80 or the SYNC signal of the 6502. Some systems present +different values to the cpu depending on whether that signal is +active, usually for protection purposes. On these cpus the opcode +part should be read from the *opcode* buffer, and the parameter part +from the *params* buffer. They will or will not be the same buffer +depending on the system itself. + +The method returns the size of the instruction in PC units, with a +maximum of 65535. In addition, if possible, the disassembler should +give some meta-information about the opcode by OR-ing in into the +result: + +* **STEP_OVER** for subroutine calls or auto-decrementing loops. If there is some delay slots, also OR with **step_over_extra**\ (n) where n is the number of instruction slots. +* **STEP_OUT** for the return-from-subroutine instructions + +In addition, to indicated that these flags are supported, OR the +result with **SUPPORTED**\ . An annoying number of disassemblers lies +about that support (e.g. they do a or with **SUPPORTED** without even +generating the **STEP_OVER** or **STEP_OUT** information). Don't do +that, it breaks the step over/step out functionality of the debugger. + +2.4. interface_flags +~~~~~~~~~~~~~~~~~~~~ + +| u32 **interface_flags**\ () const + +That optional method indicates specifics of the disassembler. Default +of zero is correct most of the time. Possible flags, which need to be +OR-ed together, are: + +* **NONLINEAR_PC**\ : stepping to the next opcode or the next byte of the opcode is not adding one to pc. Used for old LFSR-based PCs. +* **PAGED**\ : PC wraps at a page boundary +* **PAGED2LEVEL**\ : not only PC wraps at some kind of page boundary, but there are two levels of paging +* **INTERNAL_DECRYPTION**\ : there is some decryption tucked between reading from AS_PROGRAM and the actual disassembler +* **SPLIT_DECRYPTION**\ : there is some decryption tucked between reading from AS_PROGRAM and the actual disassembler, and that decryption is different for opcodes and parameters + +Note that in practice non-linear pc systems are also paged, that +**PAGED2LEVEL** implies **PAGED**, and that **SPLIT_DECRYPTION** +implies **DECRYPTION**. + + +2.5. pc_linear_to_real and pc_real_to_linear +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +| offs_t **pc_linear_to_real**\ (offs_t pc) const +| offs_t **pc_real_to_linear**\ (offs_t pc) const + +These methods should be present only when **NONLINEAR_PC** is set in +the interface flags. They must convert pc to and from a value to a +linear domain where the instruction parameters and next instruction +are reached by incrementing the value. **pc_real_to_linear** converts +to that domain, **pc_linear_to_real** converts back from that domain. + + +2.6. page_address_bits +~~~~~~~~~~~~~~~~~~~~~~ + +| u32 **page_address_bits**\ () const + +Present on when **PAGED** or **PAGED2LEVEL** is set, gives the number +of address bits in the lowest page. + + +2.7. page2_address_bits +~~~~~~~~~~~~~~~~~~~~~~~ + +| u32 **page2_address_bits**\ () const + +Present on when **PAGED2LEVEL** is set, gives the number +of address bits in the upper page. + +2.8. decryptnn +~~~~~~~~~~~~~~ + +| u8 **decrypt8**\ (u8 value, offs_t pc, bool opcode) const +| u16 **decrypt16**\ (u16 value, offs_t pc, bool opcode) const +| u32 **decrypt32**\ (u32 value, offs_t pc, bool opcode) const +| u64 **decrypt64**\ (u64 value, offs_t pc, bool opcode) const + +One of these must be defined when **INTERNAL_DECRYPTION** or +**SPLIT_DECRYPTION** is set. The chosen one is the one which takes +what **opcode_alignment** represents in bytes. + +That method decrypts a given value read from address pc (from +AS_PROGRAM) and gives the result which will be passed to the +disassembler. In the split decryption case, opcode indicates whether +we're in the opcode (true) or parameter (false) part of the +instruction. + + +3. Disassembler interface, device_disasm_interface +-------------------------------------------------- + +3.1. Definition +~~~~~~~~~~~~~~~ + +A CPU core derives from **device_disasm_interface** through +**cpu_device**\ . One method has to be implemented, +**create_disassembler**\ . + +3.2. create_disassembler +~~~~~~~~~~~~~~~~~~~~~~~~ + +| util::disasm_interface \*\ **create_disassembler**\ () + +That method must return a pointer to a newly allocated disassembler +object. The caller takes ownership and handles the lifetime. + +THis method will be called at most one in the lifetime of the cpu +object. + +4. Disassembler configuration and communication +----------------------------------------------- + +Some disassemblers need to be configured. Configuration can be +unchanging (static) for the duration of the run (cpu model type for +instance) or dynamic (state of a flag or a user preference). Static +configuration can be done through either (a) parameter(s) to the +disassembler constructor, or through deriving a main disassembler +class. If the information is short and its semantics obvious (like a +model name), feel free to use a parameter. Otherwise derive the +class. + +Dynamic configuration must be done by first defining a nested public +struct called "config" in the disassembler, with virtual destructor +and pure virtual methods to pull the required information. A pointer +to that struct should be passed to the disassembler constructor. The +cpu core should then add a derivation from that config struct and +implement the methods. Unidasm will have to derive a small class from +the config class to give the information. + +5. Missing stuff +---------------- + +There currently is no way for the debugger GUI to add per-core +configuration. It is needed for in particular the s2650 and the +saturn cores. It should go through the cpu core class itself, since +it's pulled from the config struct. + +There is support missing in unidasm for per-cpu configuration. That's +needed for a lot of things, see the unidasm source code for the +current list ("Configuration missing" comments). diff --git a/docs/source/techspecs/device_memory_interface.rst b/docs/source/techspecs/device_memory_interface.rst index d38faf8c996..f35a1887cee 100644 --- a/docs/source/techspecs/device_memory_interface.rst +++ b/docs/source/techspecs/device_memory_interface.rst @@ -40,12 +40,13 @@ instructions separately from the data. 2. Setup -------- -| std::vector>\ **memory_space_config**\ (int spacenum) const +| std::vector>\ **memory_space_config**\ (int spacenum) const The device must override that method to provide a vector of pairs comprising of a space number and its associated **address_space_config** describing its configuration. Some examples to look up when needed: + * Standard two-space vector: v60_device * Conditional AS_OPCODE: z80_device * Inherit config and add a space: m6801_device @@ -106,7 +107,7 @@ version tests for AS_PROGRAM/AS_0. Does a logical to physical address translation through the device's MMU. spacenum gives the space number, intention the type of the -future access (TRANSLATE_(READ|WRITE|FETCH)(|_USER|_DEBUG)) and +future access (TRANSLATE_(READ\|WRITE\|FETCH)(\|_USER\|_DEBUG)) and address is an inout parameter with the address to translate and its translated version. Should return true if the translation went correctly, false if the address is unmapped. diff --git a/docs/source/techspecs/index.rst b/docs/source/techspecs/index.rst index 5b73caffd0c..6ed4435772a 100644 --- a/docs/source/techspecs/index.rst +++ b/docs/source/techspecs/index.rst @@ -8,6 +8,7 @@ This section covers technical specifications useful to programmers working on MA device_memory_interface device_rom_interface + device_disasm_interface floppy nscsi luaengine diff --git a/scripts/src/cpu.lua b/scripts/src/cpu.lua index eee44c7ed3d..35e27b3e97f 100644 --- a/scripts/src/cpu.lua +++ b/scripts/src/cpu.lua @@ -51,6 +51,7 @@ if (CPUS["8X300"]~=null) then end if (CPUS["8X300"]~=null or _OPTIONS["with-tools"]) then + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/8x300/8x300dasm.h") table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/8x300/8x300dasm.cpp") end @@ -67,6 +68,7 @@ if (CPUS["ARC"]~=null) then end if (CPUS["ARC"]~=null or _OPTIONS["with-tools"]) then + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/arc/arcdasm.h") table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/arc/arcdasm.cpp") end @@ -80,9 +82,6 @@ if (CPUS["ARCOMPACT"]~=null) then MAME_DIR .. "src/devices/cpu/arcompact/arcompact.cpp", MAME_DIR .. "src/devices/cpu/arcompact/arcompact.h", MAME_DIR .. "src/devices/cpu/arcompact/arcompact_execute.cpp", - MAME_DIR .. "src/devices/cpu/arcompact/arcompactdasm_dispatch.h", - MAME_DIR .. "src/devices/cpu/arcompact/arcompactdasm_ops.h", - MAME_DIR .. "src/devices/cpu/arcompact/arcompact_common.h", } dependency { { MAME_DIR .. "src/devices/cpu/arcompact/arcompact.cpp", GEN_DIR .. "emu/cpu/arcompact/arcompact.hxx" }, @@ -95,10 +94,10 @@ if (CPUS["ARCOMPACT"]~=null) then end if (CPUS["ARCOMPACT"]~=null or _OPTIONS["with-tools"]) then + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/arcompact/arcompactdasm.h") table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/arcompact/arcompactdasm.cpp") table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/arcompact/arcompactdasm_dispatch.cpp") table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/arcompact/arcompactdasm_ops.cpp") - table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/arcompact/arcompact_common.cpp") end -------------------------------------------------- @@ -117,6 +116,7 @@ end if (CPUS["ARM"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/arm/armdasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/arm/armdasm.h") end if (CPUS["ARM7"]~=null) then @@ -137,6 +137,7 @@ end if (CPUS["ARM7"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/arm7/arm7dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/arm7/arm7dasm.h") end -------------------------------------------------- @@ -153,6 +154,7 @@ end if (CPUS["SE3208"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/se3208/se3208dis.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/se3208/se3208dis.h") end -------------------------------------------------- @@ -170,6 +172,7 @@ end if (CPUS["AMIS2000"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/amis2000/amis2000d.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/amis2000/amis2000d.h") end -------------------------------------------------- @@ -186,6 +189,7 @@ end if (CPUS["ALPHA8201"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/alph8201/8201dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/alph8201/8201dasm.h") end -------------------------------------------------- @@ -203,6 +207,7 @@ end if (CPUS["ADSP21XX"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/adsp2100/2100dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/adsp2100/2100dasm.h") end -------------------------------------------------- @@ -216,7 +221,6 @@ if (CPUS["ADSP21062"]~=null) then MAME_DIR .. "src/devices/cpu/sharc/sharc.h", MAME_DIR .. "src/devices/cpu/sharc/compute.hxx", MAME_DIR .. "src/devices/cpu/sharc/sharcdma.hxx", - MAME_DIR .. "src/devices/cpu/sharc/sharcdsm.h", MAME_DIR .. "src/devices/cpu/sharc/sharcmem.hxx", MAME_DIR .. "src/devices/cpu/sharc/sharcops.h", MAME_DIR .. "src/devices/cpu/sharc/sharcops.hxx", @@ -228,6 +232,7 @@ end if (CPUS["ADSP21062"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/sharc/sharcdsm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/sharc/sharcdsm.h") end -------------------------------------------------- @@ -244,6 +249,7 @@ end if (CPUS["APEXC"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/apexc/apexcdsm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/apexc/apexcdsm.h") end -------------------------------------------------- @@ -261,6 +267,7 @@ end if (CPUS["DSP16A"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/dsp16/dsp16dis.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/dsp16/dsp16dis.h") end -------------------------------------------------- @@ -278,6 +285,7 @@ end if (CPUS["DSP32C"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/dsp32/dsp32dis.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/dsp32/dsp32dis.h") end -------------------------------------------------- @@ -294,6 +302,7 @@ end if (CPUS["ASAP"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/asap/asapdasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/asap/asapdasm.h") end -------------------------------------------------- @@ -310,6 +319,7 @@ if (CPUS["AM29000"]~=null) then end if (CPUS["AM29000"]~=null or _OPTIONS["with-tools"]) then + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/am29000/am29dasm.h") table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/am29000/am29dasm.cpp") end @@ -327,6 +337,7 @@ end if (CPUS["JAGUAR"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/jaguar/jagdasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/jaguar/jagdasm.h") end -------------------------------------------------- @@ -343,6 +354,7 @@ end if (CPUS["CUBEQCPU"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/cubeqcpu/cubedasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/cubeqcpu/cubedasm.h") end -------------------------------------------------- @@ -357,6 +369,11 @@ if (CPUS["ES5510"]~=null) then } end +if (CPUS["ES5510"]~=null or _OPTIONS["with-tools"]) then + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/es5510/es5510d.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/es5510/es5510d.h") +end + -------------------------------------------------- -- Entertainment Sciences AM29116-based RIP --@src/devices/cpu/esrip/esrip.h,CPUS["ESRIP"] = true @@ -371,6 +388,7 @@ end if (CPUS["ESRIP"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/esrip/esripdsm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/esrip/esripdsm.h") end -------------------------------------------------- @@ -390,6 +408,7 @@ end if (CPUS["E0C6200"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/e0c6200/e0c6200d.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/e0c6200/e0c6200d.h") end -------------------------------------------------- @@ -406,6 +425,7 @@ end if (CPUS["COSMAC"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/cosmac/cosdasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/cosmac/cosdasm.h") end -------------------------------------------------- @@ -423,9 +443,13 @@ end if (CPUS["COP400"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/cop400/cop410ds.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/cop400/cop410ds.h") table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/cop400/cop420ds.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/cop400/cop420ds.h") table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/cop400/cop444ds.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/cop400/cop444ds.h") table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/cop400/cop424ds.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/cop400/cop424ds.h") end -------------------------------------------------- @@ -442,6 +466,7 @@ end if (CPUS["CP1610"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/cp1610/1610dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/cp1610/1610dasm.h") end -------------------------------------------------- @@ -457,6 +482,7 @@ if (CPUS["CCPU"]~=null) then end if (CPUS["CCPU"]~=null or _OPTIONS["with-tools"]) then + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/ccpu/ccpudasm.h") table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/ccpu/ccpudasm.cpp") end @@ -476,6 +502,7 @@ end if (CPUS["T11"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/t11/t11dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/t11/t11dasm.h") end -------------------------------------------------- @@ -492,6 +519,7 @@ end if (CPUS["PDP8"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/pdp8/pdp8dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/pdp8/pdp8dasm.h") end -------------------------------------------------- @@ -508,6 +536,7 @@ end if (CPUS["F8"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/f8/f8dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/f8/f8dasm.h") end -------------------------------------------------- @@ -532,6 +561,7 @@ end if (CPUS["G65816"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/g65816/g65816ds.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/g65816/g65816ds.h") end -------------------------------------------------- @@ -595,13 +625,34 @@ if (CPUS["H8"]~=null) then } custombuildtask { - { MAME_DIR .. "src/devices/cpu/h8/h8.lst" , GEN_DIR .. "emu/cpu/h8/h8.hxx", { MAME_DIR .. "src/devices/cpu/h8/h8make.py" }, {"@echo Generating H8-300 source file...", PYTHON .. " $(1) $(<) o $(@)" }}, - { MAME_DIR .. "src/devices/cpu/h8/h8.lst" , GEN_DIR .. "emu/cpu/h8/h8h.hxx", { MAME_DIR .. "src/devices/cpu/h8/h8make.py" }, {"@echo Generating H8-300H source file...", PYTHON .. " $(1) $(<) h $(@)" }}, - { MAME_DIR .. "src/devices/cpu/h8/h8.lst" , GEN_DIR .. "emu/cpu/h8/h8s2000.hxx", { MAME_DIR .. "src/devices/cpu/h8/h8make.py" }, {"@echo Generating H8S/2000 source file...", PYTHON .. " $(1) $(<) s20 $(@)" }}, - { MAME_DIR .. "src/devices/cpu/h8/h8.lst" , GEN_DIR .. "emu/cpu/h8/h8s2600.hxx", { MAME_DIR .. "src/devices/cpu/h8/h8make.py" }, {"@echo Generating H8S/2600 source file...", PYTHON .. " $(1) $(<) s26 $(@)" }}, + { MAME_DIR .. "src/devices/cpu/h8/h8.lst" , GEN_DIR .. "emu/cpu/h8/h8.hxx", { MAME_DIR .. "src/devices/cpu/h8/h8make.py" }, {"@echo Generating H8-300 source file...", PYTHON .. " $(1) $(<) s o $(@)" }}, + { MAME_DIR .. "src/devices/cpu/h8/h8.lst" , GEN_DIR .. "emu/cpu/h8/h8h.hxx", { MAME_DIR .. "src/devices/cpu/h8/h8make.py" }, {"@echo Generating H8-300H source file...", PYTHON .. " $(1) $(<) s h $(@)" }}, + { MAME_DIR .. "src/devices/cpu/h8/h8.lst" , GEN_DIR .. "emu/cpu/h8/h8s2000.hxx", { MAME_DIR .. "src/devices/cpu/h8/h8make.py" }, {"@echo Generating H8S/2000 source file...", PYTHON .. " $(1) $(<) s s20 $(@)" }}, + { MAME_DIR .. "src/devices/cpu/h8/h8.lst" , GEN_DIR .. "emu/cpu/h8/h8s2600.hxx", { MAME_DIR .. "src/devices/cpu/h8/h8make.py" }, {"@echo Generating H8S/2600 source file...", PYTHON .. " $(1) $(<) s s26 $(@)" }}, } end +if (CPUS["H8"]~=null or _OPTIONS["with-tools"]) then + table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/h8/h8.lst" , GEN_DIR .. "emu/cpu/h8/h8d.hxx", { MAME_DIR .. "src/devices/cpu/h8/h8make.py" }, {"@echo Generating H8-300 disassembler source file...", PYTHON .. " $(1) $(<) d o $(@)" }}) + table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/h8/h8.lst" , GEN_DIR .. "emu/cpu/h8/h8hd.hxx", { MAME_DIR .. "src/devices/cpu/h8/h8make.py" }, {"@echo Generating H8-300H disassembler source file...", PYTHON .. " $(1) $(<) d h $(@)" }}) + table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/h8/h8.lst" , GEN_DIR .. "emu/cpu/h8/h8s2000d.hxx", { MAME_DIR .. "src/devices/cpu/h8/h8make.py" }, {"@echo Generating H8S/2000 disassembler source file...", PYTHON .. " $(1) $(<) d s20 $(@)" }}) + table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/h8/h8.lst" , GEN_DIR .. "emu/cpu/h8/h8s2600d.hxx", { MAME_DIR .. "src/devices/cpu/h8/h8make.py" }, {"@echo Generating H8S/2600 disassembler source file...", PYTHON .. " $(1) $(<) d s26 $(@)" }}) + + table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/h8/h8d.cpp", GEN_DIR .. "emu/cpu/h8/h8d.hxx" }) + table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/h8/h8hd.cpp", GEN_DIR .. "emu/cpu/h8/h8hd.hxx" }) + table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/h8/h8s2000d.cpp", GEN_DIR .. "emu/cpu/h8/h8s2000d.hxx" }) + table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/h8/h8s2600d.cpp", GEN_DIR .. "emu/cpu/h8/h8s2600d.hxx" }) + + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/h8/h8d.cpp") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/h8/h8d.h") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/h8/h8hd.cpp") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/h8/h8hd.h") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/h8/h8s2000d.cpp") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/h8/h8s2000d.h") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/h8/h8s2600d.cpp") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/h8/h8s2600d.h") +end + -------------------------------------------------- -- Hitachi HCD62121 --@src/devices/cpu/hcd62121/hcd62121.h,CPUS["HCD62121"] = true @@ -616,6 +667,7 @@ end if (CPUS["HCD62121"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/hcd62121/hcd62121d.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/hcd62121/hcd62121d.h") end -------------------------------------------------- @@ -633,6 +685,7 @@ end if (CPUS["HMCS40"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/hmcs40/hmcs40d.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/hmcs40/hmcs40d.h") end -------------------------------------------------- @@ -674,6 +727,7 @@ end if (CPUS["SH"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/sh/sh_dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/sh/sh_dasm.h") end -------------------------------------------------- @@ -685,12 +739,13 @@ if (CPUS["HPHYBRID"]~=null) then files { MAME_DIR .. "src/devices/cpu/hphybrid/hphybrid.cpp", MAME_DIR .. "src/devices/cpu/hphybrid/hphybrid.h", - MAME_DIR .. "src/devices/cpu/hphybrid/hphybrid_defs.h", } end if (CPUS["HPHYBRID"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/hphybrid/hphybrid_dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/hphybrid/hphybrid_dasm.h") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/hphybrid/hphybrid_defs.h") end -------------------------------------------------- @@ -707,6 +762,7 @@ end if (CPUS["NANOPROCESSOR"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/nanoprocessor/nanoprocessor_dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/nanoprocessor/nanoprocessor_dasm.h") end -------------------------------------------------- @@ -723,6 +779,7 @@ end if (CPUS["CAPRICORN"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/capricorn/capricorn_dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/capricorn/capricorn_dasm.h") end -------------------------------------------------- @@ -739,6 +796,7 @@ end if (CPUS["H6280"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/h6280/6280dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/h6280/6280dasm.h") end -------------------------------------------------- @@ -757,6 +815,7 @@ end if (CPUS["E1"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/e132xs/32xsdasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/e132xs/32xsdasm.h") end -------------------------------------------------- @@ -773,6 +832,7 @@ end if (CPUS["IE15"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/ie15/ie15dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/ie15/ie15dasm.h") end -------------------------------------------------- @@ -789,6 +849,7 @@ end if (CPUS["MCS40"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mcs40/mcs40dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mcs40/mcs40dasm.h") end -------------------------------------------------- @@ -805,6 +866,7 @@ end if (CPUS["I8008"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/i8008/8008dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/i8008/8008dasm.h") end -------------------------------------------------- @@ -821,6 +883,7 @@ end if (CPUS["SCMP"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/scmp/scmpdasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/scmp/scmpdasm.h") end -------------------------------------------------- @@ -837,6 +900,7 @@ end if (CPUS["I8085"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/i8085/8085dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/i8085/8085dasm.h") end -------------------------------------------------- @@ -856,6 +920,7 @@ end if (CPUS["I8089"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/i8089/i8089_dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/i8089/i8089_dasm.h") end -------------------------------------------------- @@ -872,6 +937,7 @@ end if (CPUS["MCS48"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mcs48/mcs48dsm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mcs48/mcs48dsm.h") end -------------------------------------------------- @@ -889,6 +955,7 @@ end if (CPUS["MCS51"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mcs51/mcs51dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mcs51/mcs51dasm.h") end -------------------------------------------------- @@ -912,12 +979,24 @@ if (CPUS["MCS96"]~=null) then } custombuildtask { - { MAME_DIR .. "src/devices/cpu/mcs96/mcs96ops.lst" , GEN_DIR .. "emu/cpu/mcs96/mcs96.hxx", { MAME_DIR .. "src/devices/cpu/mcs96/mcs96make.py" }, {"@echo Generating mcs96 source file...", PYTHON .. " $(1) mcs96 $(<) $(@)" }}, - { MAME_DIR .. "src/devices/cpu/mcs96/mcs96ops.lst" , GEN_DIR .. "emu/cpu/mcs96/i8x9x.hxx", { MAME_DIR .. "src/devices/cpu/mcs96/mcs96make.py" }, {"@echo Generating i8x9x source file...", PYTHON .. " $(1) i8x9x $(<) $(@)" }}, - { MAME_DIR .. "src/devices/cpu/mcs96/mcs96ops.lst" , GEN_DIR .. "emu/cpu/mcs96/i8xc196.hxx", { MAME_DIR .. "src/devices/cpu/mcs96/mcs96make.py" }, {"@echo Generating i8xc196 source file...", PYTHON .. " $(1) i8xc196 $(<) $(@)" }}, + { MAME_DIR .. "src/devices/cpu/mcs96/mcs96ops.lst" , GEN_DIR .. "emu/cpu/mcs96/mcs96.hxx", { MAME_DIR .. "src/devices/cpu/mcs96/mcs96make.py" }, {"@echo Generating mcs96 source file...", PYTHON .. " $(1) s mcs96 $(<) $(@)" }}, + { MAME_DIR .. "src/devices/cpu/mcs96/mcs96ops.lst" , GEN_DIR .. "emu/cpu/mcs96/i8x9x.hxx", { MAME_DIR .. "src/devices/cpu/mcs96/mcs96make.py" }, {"@echo Generating i8x9x source file...", PYTHON .. " $(1) s i8x9x $(<) $(@)" }}, + { MAME_DIR .. "src/devices/cpu/mcs96/mcs96ops.lst" , GEN_DIR .. "emu/cpu/mcs96/i8xc196.hxx", { MAME_DIR .. "src/devices/cpu/mcs96/mcs96make.py" }, {"@echo Generating i8xc196 source file...", PYTHON .. " $(1) s i8xc196 $(<) $(@)" }}, } end +if (CPUS["MCS96"]~=null or _OPTIONS["with-tools"]) then + table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/mcs96/mcs96ops.lst", GEN_DIR .. "emu/cpu/mcs96/i8x9xd.hxx", { MAME_DIR .. "src/devices/cpu/mcs96/mcs96make.py" }, {"@echo Generating i8x9x disassembler source file...", PYTHON .. " $(1) d i8x9x $(<) $(2) $(@)" }}) + table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/mcs96/mcs96ops.lst", GEN_DIR .. "emu/cpu/mcs96/i8xc196d.hxx", { MAME_DIR .. "src/devices/cpu/mcs96/mcs96make.py" }, {"@echo Generating i8xc196 disassembler source file...", PYTHON .. " $(1) d i8xc196 $(<) $(2) $(@)" }}) + + table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/mcs96/i8x9xd.cpp", GEN_DIR .. "emu/cpu/mcs96/i8x9xd.hxx" }) + table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/mcs96/i8xc196d.cpp", GEN_DIR .. "emu/cpu/mcs96/i8xc196d.hxx" }) + + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/mcs96/mcs96d.cpp") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/mcs96/i8x9xd.cpp") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/mcs96/i8xc196d.cpp") + end + -------------------------------------------------- -- Intel 80x86 series (also a dynamic recompiler target) --@src/devices/cpu/i86/i86.h,CPUS["I86"] = true @@ -967,13 +1046,13 @@ if (CPUS["I860"]~=null) then files { MAME_DIR .. "src/devices/cpu/i860/i860.cpp", MAME_DIR .. "src/devices/cpu/i860/i860.h", - --MAME_DIR .. "src/devices/cpu/i860/i860dasm.cpp", MAME_DIR .. "src/devices/cpu/i860/i860dec.hxx", } end if (CPUS["I860"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/i860/i860dis.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/i860/i860dis.h") end -------------------------------------------------- @@ -1008,6 +1087,7 @@ end if (CPUS["LH5801"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/lh5801/5801dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/lh5801/5801dasm.h") end -------- ------------------------------------------ @@ -1024,6 +1104,7 @@ end if (CPUS["SSEM"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/ssem/ssemdasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/ssem/ssemdasm.h") end -------------------------------------------------- @@ -1040,6 +1121,7 @@ end if (CPUS["MB88XX"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mb88xx/mb88dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mb88xx/mb88dasm.h") end -------------------------------------------------- @@ -1056,6 +1138,7 @@ end if (CPUS["MB86233"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mb86233/mb86233d.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mb86233/mb86233d.h") end -------------------------------------------------- @@ -1075,6 +1158,7 @@ end if (CPUS["MB86235"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mb86235/mb86235d.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mb86235/mb86235d.h") end -------------------------------------------------- @@ -1086,12 +1170,12 @@ if (CPUS["PIC16C5X"]~=null) then files { MAME_DIR .. "src/devices/cpu/pic16c5x/pic16c5x.cpp", MAME_DIR .. "src/devices/cpu/pic16c5x/pic16c5x.h", - --MAME_DIR .. "src/devices/cpu/pic16c5x/dis16c5x.cpp", } end if (CPUS["PIC16C5X"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/pic16c5x/16c5xdsm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/pic16c5x/16c5xdsm.h") end -------------------------------------------------- @@ -1103,12 +1187,12 @@ if (CPUS["PIC16C62X"]~=null) then files { MAME_DIR .. "src/devices/cpu/pic16c62x/pic16c62x.cpp", MAME_DIR .. "src/devices/cpu/pic16c62x/pic16c62x.h", - --MAME_DIR .. "src/devices/cpu/pic16c62x/dis16c62x.cpp", } end if (CPUS["PIC16C62X"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/pic16c62x/16c62xdsm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/pic16c62x/16c62xdsm.h") end -------------------------------------------------- @@ -1125,6 +1209,7 @@ end if (CPUS["R3000"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mips/r3kdasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mips/r3kdasm.h") end -------------------------------------------------- @@ -1146,6 +1231,7 @@ end if (CPUS["MIPS"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mips/mips3dsm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mips/mips3dsm.h") end -------------------------------------------------- @@ -1170,12 +1256,12 @@ if (CPUS["PSX"]~=null) then MAME_DIR .. "src/devices/cpu/psx/rcnt.h", MAME_DIR .. "src/devices/cpu/psx/sio.cpp", MAME_DIR .. "src/devices/cpu/psx/sio.h", - --MAME_DIR .. "src/devices/cpu/psx/dismips.cpp", } end if (CPUS["PSX"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/psx/psxdasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/psx/psxdasm.h") end -------------------------------------------------- @@ -1195,6 +1281,7 @@ end if (CPUS["MELPS4"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/melps4/melps4d.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/melps4/melps4d.h") end -------------------------------------------------- @@ -1213,12 +1300,12 @@ if (CPUS["M37710"]~=null) then MAME_DIR .. "src/devices/cpu/m37710/m37710cm.h", MAME_DIR .. "src/devices/cpu/m37710/m37710il.h", MAME_DIR .. "src/devices/cpu/m37710/m37710op.h", - MAME_DIR .. "src/devices/cpu/m37710/m7700ds.h", } end if (CPUS["M37710"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/m37710/m7700ds.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/m37710/m7700ds.h") end -------------------------------------------------- @@ -1284,6 +1371,19 @@ if (CPUS["M6502"]~=null) then MAME_DIR .. "src/devices/cpu/m6502/m5074x.h", } + custombuildtask { + { MAME_DIR .. "src/devices/cpu/m6502/odeco16.lst", GEN_DIR .. "emu/cpu/m6502/deco16.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/ddeco16.lst" }, {"@echo Generating deco16 disassembler source file...", PYTHON .. " $(1) s deco16 $(<) $(2) $(@)" }}, + { MAME_DIR .. "src/devices/cpu/m6502/om4510.lst", GEN_DIR .. "emu/cpu/m6502/m4510.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm4510.lst" }, {"@echo Generating m4510 disassembler source file...", PYTHON .. " $(1) s m4510 $(<) $(2) $(@)" }}, + { MAME_DIR .. "src/devices/cpu/m6502/om6502.lst", GEN_DIR .. "emu/cpu/m6502/m6502.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm6502.lst" }, {"@echo Generating m6502 disassembler source file...", PYTHON .. " $(1) s m6502 $(<) $(2) $(@)" }}, + { MAME_DIR .. "src/devices/cpu/m6502/om65c02.lst", GEN_DIR .. "emu/cpu/m6502/m65c02.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm65c02.lst" }, {"@echo Generating m65c02 disassembler source file...", PYTHON .. " $(1) s m65c02 $(<) $(2) $(@)" }}, + { MAME_DIR .. "src/devices/cpu/m6502/om65ce02.lst", GEN_DIR .. "emu/cpu/m6502/m65ce02.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm65ce02.lst" }, {"@echo Generating m65ce02 disassembler source file...", PYTHON .. " $(1) s m65ce02 $(<) $(2) $(@)" }}, + { MAME_DIR .. "src/devices/cpu/m6502/om6509.lst", GEN_DIR .. "emu/cpu/m6502/m6509.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm6509.lst" }, {"@echo Generating m6509 disassembler source file...", PYTHON .. " $(1) s m6509 $(<) $(2) $(@)" }}, + { MAME_DIR .. "src/devices/cpu/m6502/om6510.lst", GEN_DIR .. "emu/cpu/m6502/m6510.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm6510.lst" }, {"@echo Generating m6510 disassembler source file...", PYTHON .. " $(1) s m6510 $(<) $(2) $(@)" }}, + { MAME_DIR .. "src/devices/cpu/m6502/on2a03.lst", GEN_DIR .. "emu/cpu/m6502/n2a03.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dn2a03.lst" }, {"@echo Generating n2a03 disassembler source file...", PYTHON .. " $(1) s n2a03 $(<) $(2) $(@)" }}, + { MAME_DIR .. "src/devices/cpu/m6502/om740.lst" , GEN_DIR .. "emu/cpu/m6502/m740.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm740.lst" }, {"@echo Generating m740 disassembler source file...", PYTHON .. " $(1) s m740 $(<) $(2) $(@)" }}, + { MAME_DIR .. "src/devices/cpu/m6502/dr65c02.lst", GEN_DIR .. "emu/cpu/m6502/r65c02.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", }, {"@echo Generating r65c02 disassembler source file...", PYTHON .. " $(1) s r65c02 - $(<) $(@)" }}, + } + dependency { { MAME_DIR .. "src/devices/cpu/m6502/deco16.cpp", GEN_DIR .. "emu/cpu/m6502/deco16.hxx" }, { MAME_DIR .. "src/devices/cpu/m6502/m4510.cpp", GEN_DIR .. "emu/cpu/m6502/m4510.hxx" }, @@ -1296,20 +1396,51 @@ if (CPUS["M6502"]~=null) then { MAME_DIR .. "src/devices/cpu/m6502/r65c02.cpp", GEN_DIR .. "emu/cpu/m6502/r65c02.hxx" }, { MAME_DIR .. "src/devices/cpu/m6502/m740.cpp", GEN_DIR .. "emu/cpu/m6502/m740.hxx" }, } +end - custombuildtask { - { MAME_DIR .. "src/devices/cpu/m6502/odeco16.lst", GEN_DIR .. "emu/cpu/m6502/deco16.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/ddeco16.lst" }, {"@echo Generating deco16 source file...", PYTHON .. " $(1) deco16_device $(<) $(2) $(@)" }}, - { MAME_DIR .. "src/devices/cpu/m6502/om4510.lst", GEN_DIR .. "emu/cpu/m6502/m4510.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm4510.lst" }, {"@echo Generating m4510 source file...", PYTHON .. " $(1) m4510_device $(<) $(2) $(@)" }}, - { MAME_DIR .. "src/devices/cpu/m6502/om6502.lst", GEN_DIR .. "emu/cpu/m6502/m6502.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm6502.lst" }, {"@echo Generating m6502 source file...", PYTHON .. " $(1) m6502_device $(<) $(2) $(@)" }}, - { MAME_DIR .. "src/devices/cpu/m6502/om65c02.lst", GEN_DIR .. "emu/cpu/m6502/m65c02.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm65c02.lst" }, {"@echo Generating m65c02 source file...", PYTHON .. " $(1) m65c02_device $(<) $(2) $(@)" }}, - { MAME_DIR .. "src/devices/cpu/m6502/om65ce02.lst",GEN_DIR .. "emu/cpu/m6502/m65ce02.hxx",{ MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm65ce02.lst" }, {"@echo Generating m65ce02 source file...", PYTHON .. " $(1) m65ce02_device $(<) $(2) $(@)" }}, - { MAME_DIR .. "src/devices/cpu/m6502/om6509.lst", GEN_DIR .. "emu/cpu/m6502/m6509.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm6509.lst" }, {"@echo Generating m6509 source file...", PYTHON .. " $(1) m6509_device $(<) $(2) $(@)" }}, - { MAME_DIR .. "src/devices/cpu/m6502/om6510.lst", GEN_DIR .. "emu/cpu/m6502/m6510.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm6510.lst" }, {"@echo Generating m6510 source file...", PYTHON .. " $(1) m6510_device $(<) $(2) $(@)" }}, - { MAME_DIR .. "src/devices/cpu/m6502/on2a03.lst", GEN_DIR .. "emu/cpu/m6502/n2a03.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dn2a03.lst" }, {"@echo Generating n2a03 source file...", PYTHON .. " $(1) n2a03_device $(<) $(2) $(@)" }}, - { MAME_DIR .. "src/devices/cpu/m6502/om740.lst" , GEN_DIR .. "emu/cpu/m6502/m740.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm740.lst" }, {"@echo Generating m740 source file...", PYTHON .. " $(1) m740_device $(<) $(2) $(@)" }}, - - { MAME_DIR .. "src/devices/cpu/m6502/dr65c02.lst", GEN_DIR .. "emu/cpu/m6502/r65c02.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py" }, {"@echo Generating r65c02 source file...", PYTHON .. " $(1) r65c02_device - $(<) $(@)" }}, - } +if (CPUS["M6502"]~=null or _OPTIONS["with-tools"]) then + table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/m6502/odeco16.lst", GEN_DIR .. "emu/cpu/m6502/deco16d.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/ddeco16.lst" }, {"@echo Generating deco16 disassembler source file...", PYTHON .. " $(1) d deco16 $(<) $(2) $(@)" }}) + table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/m6502/om4510.lst", GEN_DIR .. "emu/cpu/m6502/m4510d.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm4510.lst" }, {"@echo Generating m4510 disassembler source file...", PYTHON .. " $(1) d m4510 $(<) $(2) $(@)" }}) + table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/m6502/om6502.lst", GEN_DIR .. "emu/cpu/m6502/m6502d.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm6502.lst" }, {"@echo Generating m6502 disassembler source file...", PYTHON .. " $(1) d m6502 $(<) $(2) $(@)" }}) + table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/m6502/om65c02.lst", GEN_DIR .. "emu/cpu/m6502/m65c02d.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm65c02.lst" }, {"@echo Generating m65c02 disassembler source file...", PYTHON .. " $(1) d m65c02 $(<) $(2) $(@)" }}) + table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/m6502/om65ce02.lst", GEN_DIR .. "emu/cpu/m6502/m65ce02d.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm65ce02.lst" }, {"@echo Generating m65ce02 disassembler source file...", PYTHON .. " $(1) d m65ce02 $(<) $(2) $(@)" }}) + table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/m6502/om6509.lst", GEN_DIR .. "emu/cpu/m6502/m6509d.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm6509.lst" }, {"@echo Generating m6509 disassembler source file...", PYTHON .. " $(1) d m6509 $(<) $(2) $(@)" }}) + table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/m6502/om6510.lst", GEN_DIR .. "emu/cpu/m6502/m6510d.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm6510.lst" }, {"@echo Generating m6510 disassembler source file...", PYTHON .. " $(1) d m6510 $(<) $(2) $(@)" }}) + table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/m6502/on2a03.lst", GEN_DIR .. "emu/cpu/m6502/n2a03d.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dn2a03.lst" }, {"@echo Generating n2a03 disassembler source file...", PYTHON .. " $(1) d n2a03 $(<) $(2) $(@)" }}) + table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/m6502/om740.lst" , GEN_DIR .. "emu/cpu/m6502/m740d.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", MAME_DIR .. "src/devices/cpu/m6502/dm740.lst" }, {"@echo Generating m740 disassembler source file...", PYTHON .. " $(1) d m740 $(<) $(2) $(@)" }}) + table.insert(disasm_custombuildtask, { MAME_DIR .. "src/devices/cpu/m6502/dr65c02.lst", GEN_DIR .. "emu/cpu/m6502/r65c02d.hxx", { MAME_DIR .. "src/devices/cpu/m6502/m6502make.py", }, {"@echo Generating r65c02 disassembler source file...", PYTHON .. " $(1) d r65c02 - $(<) $(@)" }}) + + table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/m6502/deco16d.cpp", GEN_DIR .. "emu/cpu/m6502/deco16d.hxx" }) + table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/m6502/m4510d.cpp", GEN_DIR .. "emu/cpu/m6502/m4510d.hxx" }) + table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/m6502/m6502d.cpp", GEN_DIR .. "emu/cpu/m6502/m6502d.hxx" }) + table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/m6502/m65c02d.cpp", GEN_DIR .. "emu/cpu/m6502/m65c02d.hxx" }) + table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/m6502/m65ce02d.cpp", GEN_DIR .. "emu/cpu/m6502/m65ce02d.hxx" }) + table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/m6502/m6509d.cpp", GEN_DIR .. "emu/cpu/m6502/m6509d.hxx" }) + table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/m6502/m6510d.cpp", GEN_DIR .. "emu/cpu/m6502/m6510d.hxx" }) + table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/m6502/n2a03d.cpp", GEN_DIR .. "emu/cpu/m6502/n2a03d.hxx" }) + table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/m6502/r65c02d.cpp", GEN_DIR .. "emu/cpu/m6502/r65c02d.hxx" }) + table.insert(disasm_dependency, { MAME_DIR .. "src/devices/cpu/m6502/m740d.cpp", GEN_DIR .. "emu/cpu/m6502/m740d.hxx" }) + + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/deco16d.cpp") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/deco16d.h") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/m4510d.cpp") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/m4510d.h") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/m6502d.cpp") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/m6502d.h") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/m6509d.cpp") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/m6509d.h") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/m6510d.cpp") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/m6510d.h") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/m65c02d.cpp") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/m65c02d.h") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/m65ce02d.cpp") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/m65ce02d.h") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/m740d.cpp") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/m740d.h") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/n2a03d.cpp") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/n2a03d.h") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/r65c02d.cpp") + table.insert(disasm_files, MAME_DIR .. "src/devices/cpu/m6502/r65c02d.h") end -------------------------------------------------- @@ -1331,6 +1462,7 @@ end if (CPUS["M6800"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/m6800/6800dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/m6800/6800dasm.h") end -------------------------------------------------- @@ -1353,6 +1485,7 @@ end if (CPUS["M6805"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/m6805/6805dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/m6805/6805dasm.h") end -------------------------------------------------- @@ -1388,6 +1521,7 @@ end if (CPUS["M6809"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/m6809/6x09dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/m6809/6x09dasm.h") end -------------------------------------------------- @@ -1406,6 +1540,7 @@ end if (CPUS["MC68HC11"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mc68hc11/hc11dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mc68hc11/hc11dasm.h") end -------------------------------------------------- @@ -1429,6 +1564,7 @@ end if (CPUS["M680X0"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/m68000/m68kdasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/m68000/m68kdasm.h") end -------------------------------------------------- @@ -1446,19 +1582,20 @@ if (CPUS["DSP56156"]~=null) then MAME_DIR .. "src/devices/cpu/dsp56k/dsp56pcu.h", MAME_DIR .. "src/devices/cpu/dsp56k/dsp56def.h", MAME_DIR .. "src/devices/cpu/dsp56k/dsp56ops.hxx", - MAME_DIR .. "src/devices/cpu/dsp56k/inst.h", - MAME_DIR .. "src/devices/cpu/dsp56k/opcode.h", - MAME_DIR .. "src/devices/cpu/dsp56k/pmove.h", - MAME_DIR .. "src/devices/cpu/dsp56k/tables.h", } end if (CPUS["DSP56156"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/dsp56k/dsp56dsm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/dsp56k/dsp56dsm.h") table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/dsp56k/opcode.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/dsp56k/opcode.h") table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/dsp56k/inst.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/dsp56k/inst.h") table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/dsp56k/pmove.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/dsp56k/pmove.h") table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/dsp56k/tables.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/dsp56k/tables.h") end -------------------------------------------------- @@ -1479,7 +1616,9 @@ end if (CPUS["PDP1"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/pdp1/pdp1dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/pdp1/pdp1dasm.h") table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/pdp1/tx0dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/pdp1/tx0dasm.h") end -------------------------------------------------- @@ -1496,6 +1635,7 @@ end if (CPUS["PATINHOFEIO"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/patinhofeio/patinho_feio_dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/patinhofeio/patinho_feio_dasm.h") end -------------------------------------------------- @@ -1516,6 +1656,7 @@ end if (CPUS["POWERPC"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/powerpc/ppc_dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/powerpc/ppc_dasm.h") end -------------------------------------------------- @@ -1530,7 +1671,6 @@ if (CPUS["NEC"]~=null) then files { MAME_DIR .. "src/devices/cpu/nec/nec.cpp", MAME_DIR .. "src/devices/cpu/nec/nec.h", - MAME_DIR .. "src/devices/cpu/nec/nec_common.h", MAME_DIR .. "src/devices/cpu/nec/necea.h", MAME_DIR .. "src/devices/cpu/nec/necinstr.h", MAME_DIR .. "src/devices/cpu/nec/necinstr.hxx", @@ -1550,6 +1690,7 @@ end if (CPUS["NEC"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/nec/necdasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/nec/necdasm.h") end if (CPUS["V30MZ"]~=null) then @@ -1561,6 +1702,7 @@ end if (CPUS["V30MZ"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/nec/necdasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/nec/necdasm.h") end -------------------------------------------------- @@ -1589,6 +1731,7 @@ end if (CPUS["V60"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/v60/v60d.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/v60/v60d.h") end -------------------------------------------------- @@ -1605,6 +1748,7 @@ end if (CPUS["V810"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/v810/v810dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/v810/v810dasm.h") end -------------------------------------------------- @@ -1621,6 +1765,7 @@ end if (CPUS["UPD7725"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/upd7725/dasm7725.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/upd7725/dasm7725.h") end -------------------------------------------------- @@ -1642,6 +1787,7 @@ end if (CPUS["UPD7810"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/upd7810/upd7810_dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/upd7810/upd7810_dasm.h") end -------------------------------------------------- @@ -1659,6 +1805,7 @@ end if (CPUS["UCOM4"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/ucom4/ucom4d.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/ucom4/ucom4d.h") end -------------------------------------------------- @@ -1679,6 +1826,7 @@ end if (CPUS["MINX"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/minx/minxd.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/minx/minxd.h") end -------------------------------------------------- @@ -1730,6 +1878,7 @@ end if (CPUS["RSP"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/rsp/rsp_dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/rsp/rsp_dasm.h") end -------------------------------------------------- @@ -1746,6 +1895,7 @@ end if (CPUS["MN10200"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mn10200/mn102dis.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/mn10200/mn102dis.h") end -------------------------------------------------- @@ -1764,6 +1914,7 @@ end if (CPUS["SATURN"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/saturn/saturnds.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/saturn/saturnds.h") end -------------------------------------------------- @@ -1790,6 +1941,7 @@ end if (CPUS["SM510"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/sm510/sm510d.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/sm510/sm510d.h") end -------------------------------------------------- @@ -1807,6 +1959,7 @@ end if (CPUS["SM8500"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/sm8500/sm8500d.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/sm8500/sm8500d.h") end -------------------------------------------------- @@ -1824,6 +1977,7 @@ end if (CPUS["S2650"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/s2650/2650dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/s2650/2650dasm.h") end -------------------------------------------------- @@ -1843,6 +1997,7 @@ end if (CPUS["SC61860"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/sc61860/scdasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/sc61860/scdasm.h") end -------------------------------------------------- @@ -1860,6 +2015,7 @@ end if (CPUS["SPC700"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/spc700/spc700ds.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/spc700/spc700ds.h") end -------------------------------------------------- @@ -1876,6 +2032,7 @@ end if (CPUS["SSP1601"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/ssp1601/ssp1601d.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/ssp1601/ssp1601d.h") end -------------------------------------------------- @@ -1892,6 +2049,7 @@ end if (CPUS["UNSP"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/unsp/unspdasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/unsp/unspdasm.h") end -------------------------------------------------- @@ -1908,6 +2066,7 @@ end if (CPUS["AVR8"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/avr8/avr8dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/avr8/avr8dasm.h") end -------------------------------------------------- @@ -1944,6 +2103,7 @@ end if (CPUS["TMS1000"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms1000/tms1k_dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms1000/tms1k_dasm.h") end -------------------------------------------------- @@ -1961,6 +2121,7 @@ end if (CPUS["TMS7000"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms7000/7000dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms7000/7000dasm.h") end -------------------------------------------------- @@ -1987,6 +2148,7 @@ end if (CPUS["TMS9900"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms9900/9900dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms9900/9900dasm.h") end -------------------------------------------------- @@ -2003,12 +2165,12 @@ if (CPUS["TMS340X0"]~=null) then MAME_DIR .. "src/devices/cpu/tms34010/34010ops.h", MAME_DIR .. "src/devices/cpu/tms34010/34010ops.hxx", MAME_DIR .. "src/devices/cpu/tms34010/34010tbl.hxx", - --MAME_DIR .. "src/devices/cpu/tms34010/dis34010.cpp", } end if (CPUS["TMS340X0"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms34010/34010dsm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms34010/34010dsm.h") end -------------------------------------------------- @@ -2020,12 +2182,12 @@ if (CPUS["TMS32010"]~=null) then files { MAME_DIR .. "src/devices/cpu/tms32010/tms32010.cpp", MAME_DIR .. "src/devices/cpu/tms32010/tms32010.h", - --MAME_DIR .. "src/devices/cpu/tms32010/dis32010.cpp", } end if (CPUS["TMS32010"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms32010/32010dsm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms32010/32010dsm.h") end -------------------------------------------------- @@ -2037,12 +2199,12 @@ if (CPUS["TMS32025"]~=null) then files { MAME_DIR .. "src/devices/cpu/tms32025/tms32025.cpp", MAME_DIR .. "src/devices/cpu/tms32025/tms32025.h", - --MAME_DIR .. "src/devices/cpu/tms32025/dis32025.cpp", } end if (CPUS["TMS32025"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms32025/32025dsm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms32025/32025dsm.h") end -------------------------------------------------- @@ -2060,6 +2222,7 @@ end if (CPUS["TMS32031"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms32031/dis32031.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms32031/dis32031.h") end -------------------------------------------------- @@ -2078,6 +2241,7 @@ end if (CPUS["TMS32051"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms32051/dis32051.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms32051/dis32051.h") end -------------------------------------------------- @@ -2095,7 +2259,9 @@ end if (CPUS["TMS32082"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms32082/dis_mp.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms32082/dis_mp.h") table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms32082/dis_pp.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms32082/dis_pp.h") end -------------------------------------------------- @@ -2120,6 +2286,7 @@ end if (CPUS["TMS57002"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms57002/57002dsm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tms57002/57002dsm.h") table.insert(disasm_dependency , { MAME_DIR .. "src/devices/cpu/tms57002/57002dsm.cpp", GEN_DIR .. "emu/cpu/tms57002/tms57002.hxx" } ) table.insert(disasm_custombuildtask , { MAME_DIR .. "src/devices/cpu/tms57002/tmsinstr.lst" , GEN_DIR .. "emu/cpu/tms57002/tms57002.hxx", { MAME_DIR .. "src/devices/cpu/tms57002/tmsmake.py" }, {"@echo Generating TMS57002 source file...", PYTHON .. " $(1) $(<) $(@)" }}) end @@ -2136,6 +2303,11 @@ if (CPUS["TLCS90"]~=null) then } end +if (CPUS["TLCS90"]~=null or _OPTIONS["with-tools"]) then + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tlcs90/tlcs90d.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tlcs90/tlcs90d.h") +end + -------------------------------------------------- -- Toshiba TLCS-870 Series --@src/devices/cpu/tlcs870/tlcs870.h,CPUS["TLCS870"] = true @@ -2148,6 +2320,11 @@ if (CPUS["TLCS870"]~=null) then } end +if (CPUS["TLCS870"]~=null or _OPTIONS["with-tools"]) then + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tlcs870/tlcs870d.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tlcs870/tlcs870d.h") +end + -------------------------------------------------- -- Toshiba TLCS-900 Series --@src/devices/cpu/tlcs900/tlcs900.h,CPUS["TLCS900"] = true @@ -2163,6 +2340,7 @@ end if (CPUS["TLCS900"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tlcs900/dasm900.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/tlcs900/dasm900.h") end -------------------------------------------------- @@ -2190,6 +2368,7 @@ end if (CPUS["Z80"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/z80/z80dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/z80/z80dasm.h") end -------------------------------------------------- @@ -2208,6 +2387,7 @@ end if (CPUS["LR35902"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/lr35902/lr35902d.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/lr35902/lr35902d.h") end -------------------------------------------------- @@ -2234,6 +2414,7 @@ end if (CPUS["Z180"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/z180/z180dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/z180/z180dasm.h") end -------------------------------------------------- @@ -2255,6 +2436,7 @@ end if (CPUS["Z8000"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/z8000/8000dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/z8000/8000dasm.h") end -------------------------------------------------- @@ -2272,6 +2454,7 @@ end if (CPUS["Z8"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/z8/z8dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/z8/z8dasm.h") end -------------------------------------------------- @@ -2288,6 +2471,7 @@ end if (CPUS["SUPERFX"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/superfx/sfx_dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/superfx/sfx_dasm.h") end -------------------------------------------------- @@ -2304,6 +2488,7 @@ end if (CPUS["PPS4"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/pps4/pps4dasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/pps4/pps4dasm.h") end -------------------------------------------------- @@ -2320,6 +2505,7 @@ end if (CPUS["HD61700"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/hd61700/hd61700d.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/hd61700/hd61700d.h") end -------------------------------------------------- @@ -2336,6 +2522,7 @@ end if (CPUS["LC8670"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/lc8670/lc8670dsm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/lc8670/lc8670dsm.h") end -------------------------------------------------- @@ -2352,6 +2539,7 @@ end if (CPUS["SCUDSP"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/scudsp/scudspdasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/scudsp/scudspdasm.h") end -------------------------------------------------- @@ -2369,6 +2557,7 @@ end if (CPUS["SCORE"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/score/scoredsm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/score/scoredsm.h") end -------------------------------------------------- @@ -2422,6 +2611,7 @@ end if (CPUS["ALTO2"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/alto2/alto2dsm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/alto2/alto2dsm.h") end ------------------------------------------ @@ -2433,7 +2623,6 @@ if (CPUS["MB86901"]~=null) then files { MAME_DIR .. "src/devices/cpu/sparc/mb86901.cpp", MAME_DIR .. "src/devices/cpu/sparc/sparcv8ops.ipp", - MAME_DIR .. "src/devices/cpu/sparc/sparcdasm.h", MAME_DIR .. "src/devices/cpu/sparc/sparcdefs.h", MAME_DIR .. "src/devices/cpu/sparc/sparc.h", } @@ -2441,6 +2630,7 @@ end if (CPUS["MB86901"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/sparc/sparcdasm.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/sparc/sparcdasm.h") end -------------------------------------------------- @@ -2457,4 +2647,5 @@ end if (CPUS["CLIPPER"]~=null or _OPTIONS["with-tools"]) then table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/clipper/clipperd.cpp") + table.insert(disasm_files , MAME_DIR .. "src/devices/cpu/clipper/clipperd.h") end diff --git a/scripts/src/devices.lua b/scripts/src/devices.lua index ede4d8b0a86..89d88fd7274 100644 --- a/scripts/src/devices.lua +++ b/scripts/src/devices.lua @@ -79,15 +79,11 @@ if #disasm_files > 0 then } if #disasm_dependency > 0 then - dependency { - disasm_dependency[1] - } + dependency(disasm_dependency) end if #disasm_custombuildtask > 0 then - custombuildtask { - disasm_custombuildtask[1] - } + custombuildtask(disasm_custombuildtask) end end diff --git a/scripts/src/emu.lua b/scripts/src/emu.lua index e3110bfe5cf..c4f9f0e6d7e 100644 --- a/scripts/src/emu.lua +++ b/scripts/src/emu.lua @@ -187,6 +187,8 @@ files { MAME_DIR .. "src/emu/rendersw.hxx", MAME_DIR .. "src/emu/ui/uimain.h", MAME_DIR .. "src/emu/ui/cmddata.h", -- TODO: remove + MAME_DIR .. "src/emu/debug/debugbuf.cpp", + MAME_DIR .. "src/emu/debug/debugbuf.h", MAME_DIR .. "src/emu/debug/debugcmd.cpp", MAME_DIR .. "src/emu/debug/debugcmd.h", MAME_DIR .. "src/emu/debug/debugcon.cpp", diff --git a/scripts/src/lib.lua b/scripts/src/lib.lua index 07e73c73495..28fb3b7c9a6 100644 --- a/scripts/src/lib.lua +++ b/scripts/src/lib.lua @@ -57,6 +57,8 @@ project "utils" MAME_DIR .. "src/lib/util/crypto.hpp", MAME_DIR .. "src/lib/util/delegate.cpp", MAME_DIR .. "src/lib/util/delegate.h", + MAME_DIR .. "src/lib/util/disasmintf.cpp", + MAME_DIR .. "src/lib/util/disasmintf.h", MAME_DIR .. "src/lib/util/flac.cpp", MAME_DIR .. "src/lib/util/flac.h", MAME_DIR .. "src/lib/util/harddisk.cpp", diff --git a/src/devices/cpu/8x300/8x300.cpp b/src/devices/cpu/8x300/8x300.cpp index 44bb9b34fe6..93db492465e 100644 --- a/src/devices/cpu/8x300/8x300.cpp +++ b/src/devices/cpu/8x300/8x300.cpp @@ -11,6 +11,7 @@ #include "emu.h" #include "8x300.h" +#include "8x300dasm.h" #include "debugger.h" #define FETCHOP(a) (m_direct->read_word(a)) @@ -590,8 +591,7 @@ void n8x300_cpu_device::execute_run() } while (m_icount > 0); } -offs_t n8x300_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *n8x300_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( n8x300 ); - return CPU_DISASSEMBLE_NAME(n8x300)(this, stream, pc, oprom, opram, options); + return new n8x300_disassembler; } diff --git a/src/devices/cpu/8x300/8x300.h b/src/devices/cpu/8x300/8x300.h index 5bba395cca6..d98cdd2c84d 100644 --- a/src/devices/cpu/8x300/8x300.h +++ b/src/devices/cpu/8x300/8x300.h @@ -63,9 +63,7 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 2; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; address_space_config m_program_config; address_space_config m_io_config; diff --git a/src/devices/cpu/8x300/8x300dasm.cpp b/src/devices/cpu/8x300/8x300dasm.cpp index a6375072a49..db231195f04 100644 --- a/src/devices/cpu/8x300/8x300dasm.cpp +++ b/src/devices/cpu/8x300/8x300dasm.cpp @@ -8,7 +8,7 @@ */ #include "emu.h" -#include "8x300.h" +#include "8x300dasm.h" #define SRC ((opcode & 0x1f00) >> 8) #define DST (opcode & 0x001f) @@ -16,7 +16,7 @@ #define IMM8 (opcode & 0x00ff) #define IMM5 (opcode & 0x001f) -static const char *reg_names[32] = +const char *const n8x300_disassembler::reg_names[32] = { "AUX", "R1", "R2", "R3", "R4", "R5", "R6", "IVL", "OVF", "R11", "Unused12", "Unused13", "Unused14", "Unused15", "Unused16", "IVR", @@ -25,7 +25,7 @@ static const char *reg_names[32] = }; // determines if right rotate or I/O field length is to be used -static inline bool is_rot(uint16_t opcode) +bool n8x300_disassembler::is_rot(uint16_t opcode) { if((opcode & 0x1000) || (opcode & 0x0010)) return false; @@ -33,7 +33,7 @@ static inline bool is_rot(uint16_t opcode) return true; } -static inline bool is_src_rot(uint16_t opcode) +bool n8x300_disassembler::is_src_rot(uint16_t opcode) { if((opcode & 0x1000)) return false; @@ -41,10 +41,15 @@ static inline bool is_src_rot(uint16_t opcode) return true; } -CPU_DISASSEMBLE(n8x300) +u32 n8x300_disassembler::opcode_alignment() const +{ + return 2; +} + +offs_t n8x300_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { unsigned startpc = pc; - uint16_t opcode = (oprom[pc - startpc] << 8) | oprom[pc+1 - startpc]; + uint16_t opcode = opcodes.r16(pc); uint8_t inst = opcode >> 13; pc+=2; diff --git a/src/devices/cpu/8x300/8x300dasm.h b/src/devices/cpu/8x300/8x300dasm.h new file mode 100644 index 00000000000..f5fe389c614 --- /dev/null +++ b/src/devices/cpu/8x300/8x300dasm.h @@ -0,0 +1,31 @@ +// license:BSD-3-Clause +// copyright-holders:Barry Rodewald +/* + * 8x300dasm.c + * Implementation of the Scientific Micro Systems SMS300 / Signetics 8X300 Microcontroller + * + * Created on: 18/12/2013 + */ + +#ifndef MAME_CPU_8X300_8X300DASM_H +#define MAME_CPU_8X300_8X300DASM_H + +#pragma once + +class n8x300_disassembler : public util::disasm_interface +{ +public: + n8x300_disassembler() = default; + virtual ~n8x300_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *const reg_names[32]; + + bool is_rot(uint16_t opcode); + bool is_src_rot(uint16_t opcode); +}; + +#endif diff --git a/src/devices/cpu/adsp2100/2100dasm.cpp b/src/devices/cpu/adsp2100/2100dasm.cpp index a126cfa0bcb..b3efa6ac6ec 100644 --- a/src/devices/cpu/adsp2100/2100dasm.cpp +++ b/src/devices/cpu/adsp2100/2100dasm.cpp @@ -1,32 +1,32 @@ // license:BSD-3-Clause // copyright-holders:Aaron Giles #include "emu.h" -#include "adsp2100.h" +#include "2100dasm.h" -static const char *const flag_change[] = { "", "TOGGLE %s ", "RESET %s ", "SET %s " }; -static const char *const mode_change[] = { "", "", "DIS %s ", "ENA %s " }; +const char *const adsp21xx_disassembler::flag_change[] = { "", "TOGGLE %s ", "RESET %s ", "SET %s " }; +const char *const adsp21xx_disassembler::mode_change[] = { "", "", "DIS %s ", "ENA %s " }; -static const char *const alu_xop[] = { "AX0", "AX1", "AR", "MR0", "MR1", "MR2", "SR0", "SR1" }; -static const char *const alu_yop[] = { "AY0", "AY1", "AF", "0" }; -static const char *const alu_dst[] = { "AR", "AF", "NONE" }; +const char *const adsp21xx_disassembler::alu_xop[] = { "AX0", "AX1", "AR", "MR0", "MR1", "MR2", "SR0", "SR1" }; +const char *const adsp21xx_disassembler::alu_yop[] = { "AY0", "AY1", "AF", "0" }; +const char *const adsp21xx_disassembler::alu_dst[] = { "AR", "AF", "NONE" }; -static const char *const mac_xop[] = { "MX0", "MX1", "AR", "MR0", "MR1", "MR2", "SR0", "SR1" }; -static const char *const mac_yop[] = { "MY0", "MY1", "MF", "0" }; -static const char *const mac_dst[] = { "MR", "MF", "NONE" }; +const char *const adsp21xx_disassembler::mac_xop[] = { "MX0", "MX1", "AR", "MR0", "MR1", "MR2", "SR0", "SR1" }; +const char *const adsp21xx_disassembler::mac_yop[] = { "MY0", "MY1", "MF", "0" }; +const char *const adsp21xx_disassembler::mac_dst[] = { "MR", "MF", "NONE" }; -static const char *const shift_xop[] = { "SI", "??", "AR", "MR0", "MR1", "MR2", "SR0", "SR1" }; +const char *const adsp21xx_disassembler::shift_xop[] = { "SI", "??", "AR", "MR0", "MR1", "MR2", "SR0", "SR1" }; -static const char *const reg_grp[][16] = +const char *const adsp21xx_disassembler::reg_grp[][16] = { { "AX0", "AX1", "MX0", "MX1", "AY0", "AY1", "MY0", "MY1", "SI", "SE", "AR", "MR0", "MR1", "MR2", "SR0", "SR1" }, { "I0", "I1", "I2", "I3", "M0", "M1", "M2", "M3", "L0", "L1", "L2", "L3", "??", "??", "PMOVLAY", "DMOVLAY" }, { "I4", "I5", "I6", "I7", "M4", "M5", "M6", "M7", "L4", "L5", "L6", "L7", "??", "??", "??", "??" }, { "ASTAT", "MSTAT", "SSTAT", "IMASK", "ICNTL", "CNTR", "SB", "PX", "RX0", "TX0", "RX1", "TX1", "IFC", "OWRCNTR", "??", "??" } }; -static const char *const dual_xreg[] = { "AX0", "AX1", "MX0", "MX1" }; -static const char *const dual_yreg[] = { "AY0", "AY1", "MY0", "MY1" }; +const char *const adsp21xx_disassembler::dual_xreg[] = { "AX0", "AX1", "MX0", "MX1" }; +const char *const adsp21xx_disassembler::dual_yreg[] = { "AY0", "AY1", "MY0", "MY1" }; -static const char *const condition[] = +const char *const adsp21xx_disassembler::condition[] = { "IF EQ ", "IF NE ", @@ -46,7 +46,7 @@ static const char *const condition[] = "" }; -static const char *const do_condition[] = +const char *const adsp21xx_disassembler::do_condition[] = { "NE", "EQ", @@ -66,7 +66,7 @@ static const char *const do_condition[] = "FOREVER" }; -static const char *const alumac_op[][2] = +const char *const adsp21xx_disassembler::alumac_op[][2] = { { "", "" }, { "%s = %s * %s (RND)", "%s = %s * %s (RND)" }, @@ -103,7 +103,7 @@ static const char *const alumac_op[][2] = { "%s = ABS %s", "%s = ABS %s" } }; -static const char *const shift_op[] = +const char *const adsp21xx_disassembler::shift_op[] = { "SR = LSHIFT %s (HI)", "SR = SR OR LSHIFT %s (HI)", @@ -123,7 +123,7 @@ static const char *const shift_op[] = "SB = EXPADJ %s", }; -static const char *const shift_by_op[] = +const char *const adsp21xx_disassembler::shift_by_op[] = { "SR = LSHIFT %s BY %d (HI)", "SR = SR OR LSHIFT %s BY %d (HI)", @@ -143,7 +143,7 @@ static const char *const shift_by_op[] = "???" }; -static const char *const constants[] = +const char *const adsp21xx_disassembler::constants[] = { "$0001", "$FFFE", @@ -180,9 +180,7 @@ static const char *const constants[] = }; - - -static void alumac(std::ostream &stream, int dest, int op) +void adsp21xx_disassembler::alumac(std::ostream &stream, int dest, int op) { int opindex = (op >> 13) & 31; const char *xop, *yop, *dst, *opstring; @@ -207,7 +205,7 @@ static void alumac(std::ostream &stream, int dest, int op) } -static void aluconst(std::ostream &stream, int dest, int op) +void adsp21xx_disassembler::aluconst(std::ostream &stream, int dest, int op) { int opindex = (op >> 13) & 31; const char *xop, *dst, *cval, *opstring; @@ -232,10 +230,9 @@ static void aluconst(std::ostream &stream, int dest, int op) } -/* execute instructions on this CPU until icount expires */ -CPU_DISASSEMBLE(adsp21xx) +offs_t adsp21xx_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - unsigned int op = oprom[0] | (oprom[1] << 8) | (oprom[2] << 16); + unsigned int op = opcodes.r32(pc); unsigned dasmflags = 0; int temp; @@ -281,7 +278,7 @@ CPU_DISASSEMBLE(adsp21xx) if (op & 1) { util::stream_format(stream, "%s", "CALL "); - dasmflags = DASMFLAG_STEP_OVER; + dasmflags = STEP_OVER; } else util::stream_format(stream, "%s", "JUMP "); @@ -295,7 +292,7 @@ CPU_DISASSEMBLE(adsp21xx) if (op & 0x000010) { util::stream_format(stream, "%s", "POP PC "); - dasmflags = DASMFLAG_STEP_OUT; + dasmflags = STEP_OUT; } if (op & 0x000008) util::stream_format(stream, "%s", "POP LOOP "); if (op & 0x000004) util::stream_format(stream, "%s", "POP CNTR "); @@ -349,7 +346,7 @@ CPU_DISASSEMBLE(adsp21xx) util::stream_format(stream, "%s", "RTI"); else util::stream_format(stream, "%s", "RTS"); - dasmflags = DASMFLAG_STEP_OUT; + dasmflags = STEP_OUT; } else util::stream_format(stream, "??? (%06X)", op); @@ -362,7 +359,7 @@ CPU_DISASSEMBLE(adsp21xx) if (op & 0x000010) { util::stream_format(stream, "CALL (I%d)", 4 + ((op >> 6) & 3)); - dasmflags = DASMFLAG_STEP_OVER; + dasmflags = STEP_OVER; } else util::stream_format(stream, "JUMP (I%d)", 4 + ((op >> 6) & 3)); @@ -440,7 +437,7 @@ CPU_DISASSEMBLE(adsp21xx) if (op & 0x040000) { util::stream_format(stream, "%sCALL $%04X", condition[op & 15], (op >> 4) & 0x3fff); - dasmflags = DASMFLAG_STEP_OVER; + dasmflags = STEP_OVER; } else util::stream_format(stream, "%sJUMP $%04X", condition[op & 15], (op >> 4) & 0x3fff); @@ -549,5 +546,10 @@ CPU_DISASSEMBLE(adsp21xx) break; } - return 1 | dasmflags | DASMFLAG_SUPPORTED; + return 1 | dasmflags | SUPPORTED; +} + +uint32_t adsp21xx_disassembler::opcode_alignment() const +{ + return 1; } diff --git a/src/devices/cpu/adsp2100/2100dasm.h b/src/devices/cpu/adsp2100/2100dasm.h new file mode 100644 index 00000000000..1c80c47a554 --- /dev/null +++ b/src/devices/cpu/adsp2100/2100dasm.h @@ -0,0 +1,43 @@ +// license:BSD-3-Clause +// copyright-holders:Aaron Giles + +#ifndef MAME_CPU_ADSP2100_2100DASM_H +#define MAME_CPU_ADSP2100_2100DASM_H + +#pragma once + +class adsp21xx_disassembler : public util::disasm_interface +{ +public: + adsp21xx_disassembler() = default; + virtual ~adsp21xx_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *const flag_change[]; + static const char *const mode_change[]; + static const char *const alu_xop[]; + static const char *const alu_yop[]; + static const char *const alu_dst[]; + static const char *const mac_xop[]; + static const char *const mac_yop[]; + static const char *const mac_dst[]; + static const char *const shift_xop[];; + static const char *const reg_grp[][16]; + static const char *const dual_xreg[]; + static const char *const dual_yreg[]; + static const char *const condition[]; + static const char *const do_condition[]; + static const char *const alumac_op[][2]; + static const char *const shift_op[]; + static const char *const shift_by_op[]; + static const char *const constants[]; + + void alumac(std::ostream &stream, int dest, int op); + void aluconst(std::ostream &stream, int dest, int op); + +}; + +#endif diff --git a/src/devices/cpu/adsp2100/adsp2100.cpp b/src/devices/cpu/adsp2100/adsp2100.cpp index d0c10e06dce..dd1b0ef0086 100644 --- a/src/devices/cpu/adsp2100/adsp2100.cpp +++ b/src/devices/cpu/adsp2100/adsp2100.cpp @@ -100,6 +100,7 @@ #include "emu.h" #include "debugger.h" #include "adsp2100.h" +#include "2100dasm.h" // device type definitions @@ -758,41 +759,17 @@ void adsp21xx_device::state_string_export(const device_state_entry &entry, std:: //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t adsp21xx_device::disasm_min_opcode_bytes() const -{ - return 4; -} - - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t adsp21xx_device::disasm_max_opcode_bytes() const -{ - return 4; -} - - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t adsp21xx_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *adsp21xx_device::create_disassembler() { - extern CPU_DISASSEMBLE( adsp21xx ); - return CPU_DISASSEMBLE_NAME(adsp21xx)(this, stream, pc, oprom, opram, options); + return new adsp21xx_disassembler; } - /*************************************************************************** MEMORY ACCESSORS ***************************************************************************/ diff --git a/src/devices/cpu/adsp2100/adsp2100.h b/src/devices/cpu/adsp2100/adsp2100.h index faaddcdcc10..6835e984c31 100644 --- a/src/devices/cpu/adsp2100/adsp2100.h +++ b/src/devices/cpu/adsp2100/adsp2100.h @@ -243,9 +243,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // helpers void create_tables(); diff --git a/src/devices/cpu/alph8201/8201dasm.cpp b/src/devices/cpu/alph8201/8201dasm.cpp index 8e5e99ffd37..a987d5ededd 100644 --- a/src/devices/cpu/alph8201/8201dasm.cpp +++ b/src/devices/cpu/alph8201/8201dasm.cpp @@ -20,11 +20,10 @@ cpu/alph8201/ will be removed when the alpha 8304 has been dumped. ****************************************************************************/ #include "emu.h" +#include "8201dasm.h" #include -typedef unsigned char byte; - #define FMT(a,b) a, b #define PTRS_PER_FORMAT 2 @@ -171,7 +170,7 @@ Notes: /****************************************************/ -static const char *const Formats[] = { +const char *const alpha8201_disassembler::Formats[] = { FMT("0000_0000", "NOP"), // 00 FMT("0000_0001", "RRCA"), // 01 FMT("0000_0010", "RLCA"), // 02 @@ -270,24 +269,10 @@ static const char *const Formats[] = { nullptr }; -#define MAX_OPS ((ARRAY_LENGTH(Formats) - 1) / PTRS_PER_FORMAT) - -struct AD8201Opcode { - byte mask; - byte bits; - byte type; - byte pmask; - byte pdown; - const char *fmt; -}; - -static AD8201Opcode Op[MAX_OPS+1]; -static int OpInizialized = 0; - -static void InitDasm8201(void) +alpha8201_disassembler::alpha8201_disassembler() { const char *p; - byte mask, bits; + u8 mask, bits; int bit; int i; char chr , type; @@ -345,11 +330,10 @@ static void InitDasm8201(void) Op[i].type |= 0x02; /* double param */ } } - - OpInizialized = 1; + op_count = i; } -CPU_DISASSEMBLE(alpha8201) +offs_t alpha8201_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { offs_t dasmflags = 0; int i; @@ -357,11 +341,9 @@ CPU_DISASSEMBLE(alpha8201) int cnt = 1; int code , disp; - if (!OpInizialized) InitDasm8201(); - - code = oprom[0]; + code = opcodes.r8(pc); op = -1; /* no matching opcode */ - for ( i = 0; i < MAX_OPS; i++) + for ( i = 0; i < op_count; i++) { if( (code & Op[i].mask) == Op[i].bits ) { @@ -382,7 +364,7 @@ CPU_DISASSEMBLE(alpha8201) if (Op[op].type & 0x10) { - disp = opram[1]; + disp = params.r8(pc+1); cnt++; } else @@ -403,13 +385,18 @@ CPU_DISASSEMBLE(alpha8201) case 0xcd: case 0xce: case 0xdf: - dasmflags = DASMFLAG_STEP_OVER; + dasmflags = STEP_OVER; break; case 0xff: - dasmflags = DASMFLAG_STEP_OUT; + dasmflags = STEP_OUT; break; } - return cnt | dasmflags | DASMFLAG_SUPPORTED; + return cnt | dasmflags | SUPPORTED; +} + +u32 alpha8201_disassembler::opcode_alignment() const +{ + return 1; } diff --git a/src/devices/cpu/alph8201/8201dasm.h b/src/devices/cpu/alph8201/8201dasm.h new file mode 100644 index 00000000000..85676c5de10 --- /dev/null +++ b/src/devices/cpu/alph8201/8201dasm.h @@ -0,0 +1,51 @@ +// license:BSD-3-Clause +// copyright-holders:Tatsuyuki Satoh +/* + +Notice: The alpha 8201 is now emulated using mame/alpha8201.* + +cpu/alph8201/ will be removed when the alpha 8304 has been dumped. + + + + +*/ + +/**************************************************************************** + Alpha 8201/8301 Disassembler + + Copyright Tatsuyuki Satoh + Originally written for the MAME project. + +****************************************************************************/ + +#ifndef MAME_CPU_ALPH8201_8201DASM_H +#define MAME_CPU_ALPH8201_8201DASM_H + +#pragma once + +class alpha8201_disassembler : public util::disasm_interface +{ +public: + alpha8201_disassembler(); + virtual ~alpha8201_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + struct AD8201Opcode { + u8 mask; + u8 bits; + u8 type; + u8 pmask; + u8 pdown; + const char *fmt; + }; + + static const char *const Formats[]; + AD8201Opcode Op[256]; + int op_count; +}; + +#endif diff --git a/src/devices/cpu/alph8201/alph8201.cpp b/src/devices/cpu/alph8201/alph8201.cpp index 5dc141d7d82..b3eda17fd48 100644 --- a/src/devices/cpu/alph8201/alph8201.cpp +++ b/src/devices/cpu/alph8201/alph8201.cpp @@ -163,7 +163,7 @@ Timming #include "emu.h" #include "alph8201.h" #include "debugger.h" - +#include "8201dasm.h" DEFINE_DEVICE_TYPE(ALPHA8201L, alpha8201_cpu_device, "alpha8201l", "ALPHA-8201L") DEFINE_DEVICE_TYPE(ALPHA8301L, alpha8301_cpu_device, "alpha8301l", "ALPHA-8301L") @@ -690,9 +690,7 @@ void alpha8201_cpu_device::execute_set_input(int inputnum, int state) } } - -offs_t alpha8201_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +util::disasm_interface *alpha8201_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( alpha8201 ); - return CPU_DISASSEMBLE_NAME(alpha8201)(this, stream, pc, oprom, opram, options); + return new alpha8201_disassembler; } diff --git a/src/devices/cpu/alph8201/alph8201.h b/src/devices/cpu/alph8201/alph8201.h index 93640f17301..aa17c6d8dc0 100644 --- a/src/devices/cpu/alph8201/alph8201.h +++ b/src/devices/cpu/alph8201/alph8201.h @@ -83,9 +83,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual u32 disasm_min_opcode_bytes() const override { return 1; } - virtual u32 disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; u8 M_RDMEM(u16 A) { return m_program->read_byte(A); } void M_WRMEM(u16 A, u8 V) { m_program->write_byte(A, V); } diff --git a/src/devices/cpu/alto2/a2ram.cpp b/src/devices/cpu/alto2/a2ram.cpp index 39996f98fa7..3aab054871d 100644 --- a/src/devices/cpu/alto2/a2ram.cpp +++ b/src/devices/cpu/alto2/a2ram.cpp @@ -99,7 +99,7 @@ void alto2_cpu_device::rdram() #if DEBUG_RDRAM char buffer[256]; uint8_t* oprom = m_ucode_cram.get() + 4 * wordaddr; - disasm_disassemble(buffer, wordaddr, oprom, oprom, 0); + disassemble(buffer, wordaddr, oprom, oprom, 0); printf("RD CRAM_BANKSEL=%d RAM%d [%04o] upper:%06o lower:%06o value:%011o '%s'\n", GET_CRAM_BANKSEL(m_cram_addr), bank, wordaddr, m_myl, m_alu, value, buffer); @@ -144,7 +144,7 @@ void alto2_cpu_device::wrtram() #if DEBUG_WRTRAM char buffer[256]; uint8_t* oprom = m_ucode_cram.get() + 4 * wordaddr; - disasm_disassemble(buffer, wordaddr, oprom, oprom, 0); + disassemble(buffer, wordaddr, oprom, oprom, 0); printf("WR CRAM_BANKSEL=%d RAM%d [%04o] upper:%06o lower:%06o value:%011o '%s'\n", GET_CRAM_BANKSEL(m_cram_addr), bank, wordaddr, m_myl, m_alu, value, buffer); diff --git a/src/devices/cpu/alto2/alto2cpu.cpp b/src/devices/cpu/alto2/alto2cpu.cpp index fd7a1f6dede..21f9faa2625 100644 --- a/src/devices/cpu/alto2/alto2cpu.cpp +++ b/src/devices/cpu/alto2/alto2cpu.cpp @@ -7,6 +7,7 @@ *****************************************************************************/ #include "emu.h" #include "alto2cpu.h" +#include "alto2dsm.h" #include "a2roms.h" #define DEBUG_UCODE_CONST_DATA 0 //!< define to 1 to dump decoded micro code and constants @@ -2980,3 +2981,8 @@ void alto2_cpu_device::soft_reset() m_unload_time = 0; // reset the word unload timing accu m_bitclk_time = 0; // reset the bitclk timing accu } + +util::disasm_interface *alto2_cpu_device::create_disassembler() +{ + return new alto2_disassembler; +} diff --git a/src/devices/cpu/alto2/alto2cpu.h b/src/devices/cpu/alto2/alto2cpu.h index f71b183b52a..6bebea1f803 100644 --- a/src/devices/cpu/alto2/alto2cpu.h +++ b/src/devices/cpu/alto2/alto2cpu.h @@ -238,9 +238,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; //! device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 4; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: diff --git a/src/devices/cpu/alto2/alto2dsm.cpp b/src/devices/cpu/alto2/alto2dsm.cpp index b70c35d182c..c621daaf3e7 100644 --- a/src/devices/cpu/alto2/alto2dsm.cpp +++ b/src/devices/cpu/alto2/alto2dsm.cpp @@ -5,7 +5,7 @@ * **********************************************************/ #include "emu.h" -#include "alto2cpu.h" +#include "alto2dsm.h" #define loc_DASTART 0000420 // display list header #define loc_DVIBITS 0000421 // display vertical field interrupt bitword @@ -68,7 +68,7 @@ /** * @brief short names for the 16 tasks */ -static const char *taskname[16] = { +const char *const alto2_disassembler::taskname[16] = { "EMU", // emulator task "T01", "T02", @@ -90,7 +90,7 @@ static const char *taskname[16] = { /** * @brief names for the 32 R registers */ -static const char *regname[32] = { +const char *const alto2_disassembler::regname[32] = { "AC(3)", // emulator accu 3 "AC(2)", // emulator accu 2 "AC(1)", // emulator accu 1 @@ -126,7 +126,7 @@ static const char *regname[32] = { }; //! for ALUF which is the value loaded into T, if t flags is set -static const char* t_bus_alu[16] = { +const char *const alto2_disassembler::t_bus_alu[16] = { "ALU", "BUS", "ALU", @@ -148,7 +148,7 @@ static const char* t_bus_alu[16] = { /** * @brief copy of the constant PROM, which this disassembler may not have access to */ -static uint16_t const_prom[PROM_SIZE] = { +uint16_t alto2_disassembler::const_prom[PROM_SIZE] = { /* 0000 */ 0x0000, 0x0001, 0x0002, 0xfffe, 0xffff, 0xffff, 0x000f, 0xffff, /* 0008 */ 0x0003, 0x0004, 0x0005, 0x0006, 0x0007, 0x0008, 0xfff8, 0xfff8, /* 0010 */ 0x0010, 0x001f, 0x0020, 0x003f, 0x0040, 0x007f, 0x0080, 0x0007, @@ -187,34 +187,22 @@ static uint16_t const_prom[PROM_SIZE] = { * @brief print a symbolic name for an mpc address * * @param a microcode address (mpc) - * @return pointer to const string with the address or symbolic name + * @return string with the address or symbolic name */ -static const char *addrname(int a) +std::string alto2_disassembler::addrname(int a) const { - static char buffer[4][32]; - static int which = 0; - char *dst; - - which = (which + 1) % 4; - dst = buffer[which]; - - if (a < 020) { + if (a < 020) // start value for mpc per task is the task number - snprintf(dst, sizeof(buffer[0]), "*%s", taskname[a]); - } else { - snprintf(dst, sizeof(buffer[0]), "%04o", a); - } - return dst; + return util::string_format("*%s", taskname[a]); + else + return util::string_format("%04o", a); } -offs_t alto2_cpu_device::disasm_disassemble(std::ostream &main_stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +offs_t alto2_disassembler::disassemble(std::ostream &main_stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { std::ostringstream stream; - uint32_t mir = (static_cast(oprom[0]) << 24) | - (static_cast(oprom[1]) << 16) | - (static_cast(oprom[2]) << 8) | - (static_cast(oprom[3]) << 0); + uint32_t mir = opcodes.r32(pc); int rsel = (mir >> 27) & 31; int aluf = (mir >> 23) & 15; int bs = (mir >> 20) & 7; @@ -223,17 +211,13 @@ offs_t alto2_cpu_device::disasm_disassemble(std::ostream &main_stream, offs_t pc int t = (mir >> 11) & 1; int l = (mir >> 10) & 1; offs_t next = mir & 1023; - const uint8_t* src = oprom - 4 * pc + 4 * next; - uint32_t next2 = (static_cast(src[0]) << 24) | - (static_cast(src[1]) << 16) | - (static_cast(src[2]) << 8) | - (static_cast(src[3]) << 0); + uint32_t next2 = opcodes.r32(next); uint16_t prefetch = next2 & 1023; - offs_t result = 1 | DASMFLAG_SUPPORTED; + offs_t result = 1 | SUPPORTED; uint8_t pa; if (next != pc + 1) - result |= DASMFLAG_STEP_OUT; + result |= STEP_OUT; if (t) util::stream_format(stream, "T<-%s ", t_bus_alu[aluf]); @@ -395,3 +379,9 @@ offs_t alto2_cpu_device::disasm_disassemble(std::ostream &main_stream, offs_t pc return result; } + + +u32 alto2_disassembler::opcode_alignment() const +{ + return 1; +} diff --git a/src/devices/cpu/alto2/alto2dsm.h b/src/devices/cpu/alto2/alto2dsm.h new file mode 100644 index 00000000000..cb0d734fd58 --- /dev/null +++ b/src/devices/cpu/alto2/alto2dsm.h @@ -0,0 +1,31 @@ +// license:BSD-3-Clause +// copyright-holders:Juergen Buchmueller +/********************************************************** + * Xerox AltoII disassembler + * + **********************************************************/ + +#ifndef MAME_CPU_ALTO2_ALTO2DSM_H +#define MAME_CPU_ALTO2_ALTO2DSM_H + +#pragma once + +class alto2_disassembler : public util::disasm_interface +{ +public: + alto2_disassembler() = default; + virtual ~alto2_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *const taskname[16]; + static const char *const regname[32]; + static const char *const t_bus_alu[16]; + static uint16_t const_prom[]; + + std::string addrname(int a) const; +}; + +#endif diff --git a/src/devices/cpu/am29000/am29000.cpp b/src/devices/cpu/am29000/am29000.cpp index cd0d4624d9c..624cf2ae29f 100644 --- a/src/devices/cpu/am29000/am29000.cpp +++ b/src/devices/cpu/am29000/am29000.cpp @@ -17,6 +17,7 @@ #include "emu.h" #include "debugger.h" #include "am29000.h" +#include "am29dasm.h" DEFINE_DEVICE_TYPE(AM29000, am29000_cpu_device, "am29000", "AMC Am29000") @@ -702,9 +703,7 @@ void am29000_cpu_device::execute_set_input(int inputnum, int state) // TODO : CHECK IRQs } - -offs_t am29000_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *am29000_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( am29000 ); - return CPU_DISASSEMBLE_NAME(am29000)(this, stream, pc, oprom, opram, options); + return new am29000_disassembler; } diff --git a/src/devices/cpu/am29000/am29000.h b/src/devices/cpu/am29000/am29000.h index 084b0fdd995..746a8dd7254 100644 --- a/src/devices/cpu/am29000/am29000.h +++ b/src/devices/cpu/am29000/am29000.h @@ -458,9 +458,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 4; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; void signal_exception(uint32_t type); void external_irq_check(); diff --git a/src/devices/cpu/am29000/am29dasm.cpp b/src/devices/cpu/am29000/am29dasm.cpp index 8c7f832e69f..7e69544ab2c 100644 --- a/src/devices/cpu/am29000/am29dasm.cpp +++ b/src/devices/cpu/am29000/am29dasm.cpp @@ -9,7 +9,7 @@ ***************************************************************************/ #include "emu.h" -#include "am29000.h" +#include "am29dasm.h" /*************************************************************************** @@ -36,38 +36,38 @@ CODE ***************************************************************************/ -static std::string dasm_type1(uint32_t op) +std::string am29000_disassembler::dasm_type1(uint32_t op) { return (op & OP_M_BIT) ? string_format("r%d, r%d, $%02x", OP_RC, OP_RA, OP_I8) : string_format("r%d, r%d, r%d", OP_RC, OP_RA, OP_RB); } -static std::string dasm_type2(uint32_t op) +std::string am29000_disassembler::dasm_type2(uint32_t op) { return string_format("r%d, r%d, r%d", OP_RC, OP_RA, OP_RB); } -static std::string dasm_type3(uint32_t op) +std::string am29000_disassembler::dasm_type3(uint32_t op) { return string_format("r%d, $%04x", OP_RA, OP_I16); } -static std::string dasm_type4(uint32_t op, uint32_t pc) +std::string am29000_disassembler::dasm_type4(uint32_t op, uint32_t pc) { return (op & OP_M_BIT) ? string_format("r%d, $%04x", OP_RA, OP_IJMP) : string_format("r%d, $%04x", OP_RA, pc + OP_SJMP); } -static std::string dasm_type5(uint32_t op) +std::string am29000_disassembler::dasm_type5(uint32_t op) { return (op & OP_M_BIT) ? string_format("trap%d, r%d, $%02x", OP_VN, OP_RA, OP_I8) : string_format("trap%d, r%d, r%d", OP_VN, OP_RA, OP_RB); } -static std::string dasm_type6(uint32_t op) +std::string am29000_disassembler::dasm_type6(uint32_t op) { return (op & OP_M_BIT) ? string_format("%d, %x, r%d, $%02x", OP_CE, OP_CNTL, OP_RA, OP_I8) @@ -82,7 +82,7 @@ static std::string dasm_type6(uint32_t op) #define TYPE_6 dasm_type6(op) -static const char* get_spr(int spid) +const char* am29000_disassembler::get_spr(int spid) { switch (spid) { @@ -117,9 +117,14 @@ static const char* get_spr(int spid) } } -CPU_DISASSEMBLE(am29000) +u32 am29000_disassembler::opcode_alignment() const { - uint32_t op = (oprom[0] << 24) | (oprom[1] << 16) | (oprom[2] << 8) | oprom[3]; + return 4; +} + +offs_t am29000_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + uint32_t op = opcodes.r32(pc); uint32_t flags = 0; switch (op >> 24) @@ -228,5 +233,5 @@ CPU_DISASSEMBLE(am29000) default: util::stream_format(stream, "??????"); break; } - return 4 | flags | DASMFLAG_SUPPORTED; + return 4 | flags | SUPPORTED; } diff --git a/src/devices/cpu/am29000/am29dasm.h b/src/devices/cpu/am29000/am29dasm.h new file mode 100644 index 00000000000..40507a7332e --- /dev/null +++ b/src/devices/cpu/am29000/am29dasm.h @@ -0,0 +1,36 @@ +// license:BSD-3-Clause +// copyright-holders:Philip Bennett +/*************************************************************************** + + am29dasm.c + Disassembler for the portable Am29000 emulator. + Written by Phil Bennett + +***************************************************************************/ + +#ifndef MAME_CPU_AM29000_AM29DASM_H +#define MAME_CPU_AM29000_AM29DASM_H + +#pragma once + +class am29000_disassembler : public util::disasm_interface +{ +public: + am29000_disassembler() = default; + virtual ~am29000_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + std::string dasm_type1(uint32_t op); + std::string dasm_type2(uint32_t op); + std::string dasm_type3(uint32_t op); + std::string dasm_type4(uint32_t op, uint32_t pc); + std::string dasm_type5(uint32_t op); + std::string dasm_type6(uint32_t op); + const char* get_spr(int spid); + +}; + +#endif diff --git a/src/devices/cpu/amis2000/amis2000.cpp b/src/devices/cpu/amis2000/amis2000.cpp index 457a99ead5d..bd3eda7852a 100644 --- a/src/devices/cpu/amis2000/amis2000.cpp +++ b/src/devices/cpu/amis2000/amis2000.cpp @@ -20,6 +20,7 @@ #include "emu.h" #include "amis2000.h" +#include "amis2000d.h" #include "debugger.h" @@ -98,10 +99,9 @@ void amis2000_base_device::state_string_export(const device_state_entry &entry, } } -offs_t amis2000_base_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +util::disasm_interface *amis2000_base_device::create_disassembler() { - extern CPU_DISASSEMBLE(amis2000); - return CPU_DISASSEMBLE_NAME(amis2000)(this, stream, pc, oprom, opram, options); + return new amis2000_disassembler; } diff --git a/src/devices/cpu/amis2000/amis2000.h b/src/devices/cpu/amis2000/amis2000.h index e3caee13b14..1bf4bf66460 100644 --- a/src/devices/cpu/amis2000/amis2000.h +++ b/src/devices/cpu/amis2000/amis2000.h @@ -87,9 +87,7 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual u32 disasm_min_opcode_bytes() const override { return 1; } - virtual u32 disasm_max_opcode_bytes() const override { return 1; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; // device_state_interface overrides virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; diff --git a/src/devices/cpu/amis2000/amis2000d.cpp b/src/devices/cpu/amis2000/amis2000d.cpp index adf5e2ed338..cff6155fa0a 100644 --- a/src/devices/cpu/amis2000/amis2000d.cpp +++ b/src/devices/cpu/amis2000/amis2000d.cpp @@ -7,21 +7,9 @@ */ #include "emu.h" -#include "debugger.h" -#include "amis2000.h" +#include "amis2000d.h" - -enum e_mnemonics -{ - mLAB = 0, mLAE, mLAI, mLBE, mLBEP, mLBF, mLBZ, mXAB, mXABU, mXAE, - mLAM, mXC, mXCI, mXCD, mSTM, mRSM, - mADD, mADCS, mADIS, mAND, mXOR, mCMA, mSTC, mRSC, mSF1, mRF1, mSF2, mRF2, - mSAM, mSZM, mSBE, mSZC, mSOS, mSZK, mSZI, mTF1, mTF2, - mPP, mJMP, mJMS, mRT, mRTS, mNOP, mHALT, - mINP, mOUT, mDISB, mDISN, mMVS, mPSH, mPSL, mEUR -}; - -static const char *const s_mnemonics[] = +const char *const amis2000_disassembler::s_mnemonics[] = { "LAB", "LAE", "LAI", "LBE", "LBEP", "LBF", "LBZ", "XAB", "XABU", "XAE", "LAM", "XC", "XCI", "XCD", "STM", "RSM", @@ -32,7 +20,7 @@ static const char *const s_mnemonics[] = }; // number of bits per opcode parameter, negative indicates complement -static const s8 s_bits[] = +const s8 amis2000_disassembler::s_bits[] = { 0, 0, 4, 2, 2, 2, 2, 0, 0, 0, -2, -2, -2, -2, 2, 2, @@ -42,21 +30,18 @@ static const s8 s_bits[] = 0, 0, 0, 0, 0, 0, 0, 0 }; -#define _OVER DASMFLAG_STEP_OVER -#define _OUT DASMFLAG_STEP_OUT - -static const u32 s_flags[] = +const u32 amis2000_disassembler::s_flags[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, _OVER, _OUT, _OUT, 0, 0, + 0, 0, STEP_OVER, STEP_OUT, STEP_OUT, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; -static const u8 s2000_mnemonic[0x100] = +const u8 amis2000_disassembler::s2000_mnemonic[0x100] = { /* 0x00 */ mNOP, mHALT, mRT, mRTS, mPSH, mPSL, mAND, mSOS, @@ -98,12 +83,9 @@ static const u8 s2000_mnemonic[0x100] = mJMP, mJMP, mJMP, mJMP, mJMP, mJMP, mJMP, mJMP }; - - -CPU_DISASSEMBLE(amis2000) +offs_t amis2000_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - int pos = 0; - u8 op = oprom[pos++]; + u8 op = opcodes.r8(pc); u8 instr = s2000_mnemonic[op]; util::stream_format(stream, "%-5s ", s_mnemonics[instr]); @@ -128,5 +110,10 @@ CPU_DISASSEMBLE(amis2000) util::stream_format(stream, "$%02X", param); } - return pos | s_flags[instr] | DASMFLAG_SUPPORTED; + return 1 | s_flags[instr] | SUPPORTED; +} + +u32 amis2000_disassembler::opcode_alignment() const +{ + return 1; } diff --git a/src/devices/cpu/amis2000/amis2000d.h b/src/devices/cpu/amis2000/amis2000d.h new file mode 100644 index 00000000000..0de1a455fa8 --- /dev/null +++ b/src/devices/cpu/amis2000/amis2000d.h @@ -0,0 +1,40 @@ +// license:BSD-3-Clause +// copyright-holders:hap +/* + + AMI S2000-family disassembler + +*/ + +#ifndef MAME_CPU_AMIS2000_AMIS2000D_H +#define MAME_CPU_AMIS2000_AMIS2000D_H + +#pragma once + +class amis2000_disassembler : public util::disasm_interface +{ +public: + amis2000_disassembler() = default; + virtual ~amis2000_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum e_mnemonics + { + mLAB = 0, mLAE, mLAI, mLBE, mLBEP, mLBF, mLBZ, mXAB, mXABU, mXAE, + mLAM, mXC, mXCI, mXCD, mSTM, mRSM, + mADD, mADCS, mADIS, mAND, mXOR, mCMA, mSTC, mRSC, mSF1, mRF1, mSF2, mRF2, + mSAM, mSZM, mSBE, mSZC, mSOS, mSZK, mSZI, mTF1, mTF2, + mPP, mJMP, mJMS, mRT, mRTS, mNOP, mHALT, + mINP, mOUT, mDISB, mDISN, mMVS, mPSH, mPSL, mEUR + }; + + static const char *const s_mnemonics[]; + static const s8 s_bits[]; + static const u32 s_flags[]; + static const u8 s2000_mnemonic[0x100]; +}; + +#endif diff --git a/src/devices/cpu/apexc/apexc.cpp b/src/devices/cpu/apexc/apexc.cpp index e26c6c094b4..4278d5b2d48 100644 --- a/src/devices/cpu/apexc/apexc.cpp +++ b/src/devices/cpu/apexc/apexc.cpp @@ -327,6 +327,7 @@ field: X address D Function Y address D (part 2) #include "emu.h" #include "apexc.h" +#include "apexcdsm.h" #include "debugger.h" @@ -854,9 +855,7 @@ void apexc_cpu_device::execute_run() } while (m_icount > 0); } - -offs_t apexc_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *apexc_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( apexc ); - return CPU_DISASSEMBLE_NAME(apexc)(this, stream, pc, oprom, opram, options); + return new apexc_disassembler; } diff --git a/src/devices/cpu/apexc/apexc.h b/src/devices/cpu/apexc/apexc.h index 76a91a98207..92cc60d7f09 100644 --- a/src/devices/cpu/apexc/apexc.h +++ b/src/devices/cpu/apexc/apexc.h @@ -40,9 +40,7 @@ protected: virtual void state_import(const device_state_entry &entry) override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 4; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; inline uint32_t apexc_readmem(uint32_t address) { return m_program->read_dword((address)<<2); } inline void apexc_writemem(uint32_t address, uint32_t data) { m_program->write_dword((address)<<2, (data)); } diff --git a/src/devices/cpu/apexc/apexcdsm.cpp b/src/devices/cpu/apexc/apexcdsm.cpp index e3626a40af9..bb581dd2850 100644 --- a/src/devices/cpu/apexc/apexcdsm.cpp +++ b/src/devices/cpu/apexc/apexcdsm.cpp @@ -10,9 +10,7 @@ #include "emu.h" -#include "debugger.h" - -#include "apexc.h" +#include "apexcdsm.h" /* Here is the format used for debugger output. @@ -63,15 +61,8 @@ The X value shows where the data word is located, and the Y value is the address of the next instruction. */ -enum format_type {branch, shiftl, shiftr, multiply, store, swap, one_address, two_address}; - -struct instr_desc -{ - const char *mnemonic; - format_type format; /* -> X and Y are format */ -}; -static const instr_desc instructions[16] = +const apexc_disassembler::instr_desc apexc_disassembler::instructions[16] = { { "Stop", one_address }, { "I", one_address }, { "P", one_address }, { "B", branch }, @@ -83,7 +74,12 @@ static const instr_desc instructions[16] = { "A", store }, { "S", swap } }; -CPU_DISASSEMBLE(apexc) +u32 apexc_disassembler::opcode_alignment() const +{ + return 4; +} + +offs_t apexc_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { uint32_t instruction; /* 32-bit machine instruction */ int x, y, function, c6, vector; /* instruction fields */ @@ -92,7 +88,7 @@ CPU_DISASSEMBLE(apexc) char mnemonic[9]; /* storage for generated mnemonic */ /* read the instruction to disassemble */ - instruction = oprom[0] << 24 | oprom[1] << 16 | oprom[2] << 8 | oprom[3]; + instruction = opcodes.r32(pc); /* isolate the instruction fields */ x = (instruction >> 22) & 0x3FF; diff --git a/src/devices/cpu/apexc/apexcdsm.h b/src/devices/cpu/apexc/apexcdsm.h new file mode 100644 index 00000000000..b310df1f496 --- /dev/null +++ b/src/devices/cpu/apexc/apexcdsm.h @@ -0,0 +1,37 @@ +// license:BSD-3-Clause +// copyright-holders:Raphael Nabet +/* + cpu/apexc/apexcsm.c : APE(X)C CPU disassembler + + By Raphael Nabet + + see cpu/apexc.c for background and tech info +*/ + +#ifndef MAME_CPU_APEXC_APEXCDSM_H +#define MAME_CPU_APEXC_APEXCDSM_H + +#pragma once + +class apexc_disassembler : public util::disasm_interface +{ +public: + apexc_disassembler() = default; + virtual ~apexc_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum format_type {branch, shiftl, shiftr, multiply, store, swap, one_address, two_address}; + + struct instr_desc + { + const char *mnemonic; + format_type format; /* -> X and Y are format */ + }; + + static const instr_desc instructions[16]; +}; + +#endif diff --git a/src/devices/cpu/arc/arc.cpp b/src/devices/cpu/arc/arc.cpp index eb71302468a..fa421875bd1 100644 --- a/src/devices/cpu/arc/arc.cpp +++ b/src/devices/cpu/arc/arc.cpp @@ -12,6 +12,7 @@ #include "emu.h" #include "debugger.h" #include "arc.h" +#include "arcdasm.h" DEFINE_DEVICE_TYPE(ARC, arc_cpu_device, "arc_a4", "ARCtangent A4") @@ -26,13 +27,11 @@ arc_cpu_device::arc_cpu_device(const machine_config &mconfig, const char *tag, d } -offs_t arc_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *arc_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( arc ); - return CPU_DISASSEMBLE_NAME(arc)(this, stream, pc, oprom, opram, options); + return new arc_disassembler; } - /*****************************************************************************/ /*****************************************************************************/ diff --git a/src/devices/cpu/arc/arc.h b/src/devices/cpu/arc/arc.h index cf244c8f5b2..7bdf1123ec8 100644 --- a/src/devices/cpu/arc/arc.h +++ b/src/devices/cpu/arc/arc.h @@ -43,9 +43,7 @@ protected: virtual void state_export(const device_state_entry &entry) override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 4; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/arc/arcdasm.cpp b/src/devices/cpu/arc/arcdasm.cpp index e8c2d425736..fa7b6f2028e 100644 --- a/src/devices/cpu/arc/arcdasm.cpp +++ b/src/devices/cpu/arc/arcdasm.cpp @@ -7,7 +7,7 @@ \*********************************/ #include "emu.h" -#include +#include "arcdasm.h" /*****************************************************************************/ @@ -15,7 +15,7 @@ /*****************************************************************************/ -static const char *basic[0x20] = +const char *const arc_disassembler::basic[0x20] = { /* 00 */ "LD r+r", /* 01 */ "LD r+o", @@ -51,7 +51,7 @@ static const char *basic[0x20] = /* 1f */ "MIN" }; -static const char *conditions[0x20] = +const char *arc_disassembler::conditions[0x20] = { /* 00 */ "AL", // (aka RA - Always) /* 01 */ "EQ", // (aka Z - Zero @@ -87,7 +87,7 @@ static const char *conditions[0x20] = /* 1f */ "0x1f Reserved" }; -static const char *delaytype[0x4] = +const char *arc_disassembler::delaytype[0x4] = { "ND", // NO DELAY - execute next instruction only when NOT jumping "D", // always execute next instruction @@ -95,7 +95,7 @@ static const char *delaytype[0x4] = "Res!", // reserved / invalid }; -static const char *regnames[0x40] = +const char *arc_disassembler::regnames[0x40] = { /* 0x00 */ "r00", /* 0x01 */ "r01", @@ -180,10 +180,14 @@ static const char *regnames[0x40] = #define ARC_REGOP_SHIMM ((op & 0x000001ff) >> 0 ) // aka D -CPU_DISASSEMBLE(arc) +u32 arc_disassembler::opcode_alignment() const { - uint32_t op = oprom[0] | (oprom[1] << 8) | (oprom[2] << 16) | (oprom[3] << 24); - op = big_endianize_int32(op); + return 4; +} + +offs_t arc_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + uint32_t op = opcodes.r32(pc); uint8_t opcode = ARC_OPERATION; @@ -205,5 +209,5 @@ CPU_DISASSEMBLE(arc) break; } - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } diff --git a/src/devices/cpu/arc/arcdasm.h b/src/devices/cpu/arc/arcdasm.h new file mode 100644 index 00000000000..a6bfe559f25 --- /dev/null +++ b/src/devices/cpu/arc/arcdasm.h @@ -0,0 +1,31 @@ +// license:BSD-3-Clause +// copyright-holders:David Haywood +/*********************************\ + + ARCtangent A4 disassembler + +\*********************************/ + +#ifndef MAME_CPU_ARC_ARCDASM_H +#define MAME_CPU_ARC_ARCDASM_H + +#pragma once + +class arc_disassembler : public util::disasm_interface +{ +public: + arc_disassembler() = default; + virtual ~arc_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *const basic[0x20]; + static const char *conditions[0x20]; + static const char *delaytype[0x4]; + static const char *regnames[0x40]; + +}; + +#endif diff --git a/src/devices/cpu/arcompact/arcompact.cpp b/src/devices/cpu/arcompact/arcompact.cpp index 79ae7c6d6c6..bffbcda8213 100644 --- a/src/devices/cpu/arcompact/arcompact.cpp +++ b/src/devices/cpu/arcompact/arcompact.cpp @@ -21,7 +21,7 @@ #include "emu.h" #include "debugger.h" #include "arcompact.h" -#include "arcompact_common.h" +#include "arcompactdasm.h" DEFINE_DEVICE_TYPE(ARCA5, arcompact_device, "arc_a5", "ARCtangent A5") @@ -64,10 +64,9 @@ device_memory_interface::space_config_vector arcompact_device::memory_space_conf }; } -offs_t arcompact_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *arcompact_device::create_disassembler() { - extern CPU_DISASSEMBLE( arcompact ); - return CPU_DISASSEMBLE_NAME(arcompact)(this, stream, pc, oprom, opram, options); + return new arcompact_disassembler; } @@ -104,7 +103,7 @@ void arcompact_device::device_start() for (int i = 0x100; i < 0x140; i++) { - state_add(i, regnames[i-0x100], m_debugger_temp).callimport().callexport().formatstr("%08X"); + state_add(i, arcompact_disassembler::regnames[i-0x100], m_debugger_temp).callimport().callexport().formatstr("%08X"); } diff --git a/src/devices/cpu/arcompact/arcompact.h b/src/devices/cpu/arcompact/arcompact.h index 0a88fc119bf..fc7d7dbe5dc 100644 --- a/src/devices/cpu/arcompact/arcompact.h +++ b/src/devices/cpu/arcompact/arcompact.h @@ -102,9 +102,7 @@ protected: virtual void state_export(const device_state_entry &entry) override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 8; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; diff --git a/src/devices/cpu/arcompact/arcompact_common.cpp b/src/devices/cpu/arcompact/arcompact_common.cpp deleted file mode 100644 index f9b74683461..00000000000 --- a/src/devices/cpu/arcompact/arcompact_common.cpp +++ /dev/null @@ -1,527 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:David Haywood -/*********************************\ - - ARCompact Core - -\*********************************/ - -// condition codes (basic ones are the same as arc -const char *conditions[0x20] = -{ - /* 00 */ "AL", // (aka RA - Always) - /* 01 */ "EQ", // (aka Z - Zero - /* 02 */ "NE", // (aka NZ - Non-Zero) - /* 03 */ "PL", // (aka P - Positive) - /* 04 */ "MI", // (aka N - Negative) - /* 05 */ "CS", // (aka C, LO - Carry set / Lower than) (unsigned) - /* 06 */ "CC", // (aka CC, NC, HS - Carry Clear / Higher or Same) (unsigned) - /* 07 */ "VS", // (aka V - Overflow set) - /* 08 */ "VC", // (aka NV - Overflow clear) - /* 09 */ "GT", // ( - Greater than) (signed) - /* 0a */ "GE", // ( - Greater than or Equal) (signed) - /* 0b */ "LT", // ( - Less than) (signed) - /* 0c */ "LE", // ( - Less than or Equal) (signed) - /* 0d */ "HI", // ( - Higher than) (unsigned) - /* 0e */ "LS", // ( - Lower or Same) (unsigned) - /* 0f */ "PNZ",// ( - Positive non-0 value) - /* 10 */ "0x10 Reserved", // possible CPU implementation specifics - /* 11 */ "0x11 Reserved", - /* 12 */ "0x12 Reserved", - /* 13 */ "0x13 Reserved", - /* 14 */ "0x14 Reserved", - /* 15 */ "0x15 Reserved", - /* 16 */ "0x16 Reserved", - /* 17 */ "0x17 Reserved", - /* 18 */ "0x18 Reserved", - /* 19 */ "0x19 Reserved", - /* 1a */ "0x1a Reserved", - /* 1b */ "0x1b Reserved", - /* 1c */ "0x1c Reserved", - /* 1d */ "0x1d Reserved", - /* 1e */ "0x1e Reserved", - /* 1f */ "0x1f Reserved" -}; - -#define UNUSED_REG "unusedreg" - -#define AUX_UNUSED_16 \ - /* 0xxx0 */ UNUSED_REG, /* 0xxx1 */ UNUSED_REG, /* 0xxx2 */ UNUSED_REG, /* 0xxx3 */ UNUSED_REG, /* 0xxx4 */ UNUSED_REG, /* 0xxx5 */ UNUSED_REG, /* 0xxx6 */ UNUSED_REG, /* 0xxx7 */ UNUSED_REG, /* 0xxx8 */ UNUSED_REG, /* 0xxx9 */ UNUSED_REG, /* 0xxxa */ UNUSED_REG, /* 0xxxb */ UNUSED_REG, /* 0xxxc */ UNUSED_REG, /* 0xxxd */ UNUSED_REG, /* 0xxxe */ UNUSED_REG, /* 0xxxf */ UNUSED_REG, - -// the Auxiliary Register set is actually a 2^32 dword address space (so 16 GB / 34-bit) -// this table just allows us to improve the debugger display for some of the common core / internal ones -const char *auxregnames[0x420] = -{ - /* 0x000 */ "STATUS", - /* 0x001 */ "SEMAPHOR", - /* 0x002 */ "LP_START", - /* 0x003 */ "LP_END", - /* 0x004 */ "IDENTITY", - /* 0x005 */ "DEBUG", - /* 0x006 */ "PC", - /* 0x007 */ UNUSED_REG, - /* 0x008 */ UNUSED_REG, - /* 0x009 */ UNUSED_REG, - /* 0x00a */ "STATUS32", - /* 0x00b */ "STATUS32_L1", - /* 0x00c */ "STATUS32_L2", - /* 0x00d */ UNUSED_REG, - /* 0x00e */ UNUSED_REG, - /* 0x00f */ UNUSED_REG, - - /* 0x010 */ UNUSED_REG, - /* 0x011 */ UNUSED_REG, - /* 0x012 */ "MULHI", // extension register - /* 0x013 */ UNUSED_REG, - /* 0x014 */ UNUSED_REG, - /* 0x015 */ UNUSED_REG, - /* 0x016 */ UNUSED_REG, - /* 0x017 */ UNUSED_REG, - /* 0x018 */ UNUSED_REG, - /* 0x019 */ UNUSED_REG, - /* 0x01a */ UNUSED_REG, - /* 0x01b */ UNUSED_REG, - /* 0x01c */ UNUSED_REG, - /* 0x01d */ UNUSED_REG, - /* 0x01e */ UNUSED_REG, - /* 0x01f */ UNUSED_REG, - - /* 0x020 */ UNUSED_REG, - /* 0x021 */ "COUNT0", - /* 0x022 */ "CONTROL0", - /* 0x023 */ "LIMIT0", - /* 0x024 */ UNUSED_REG, - /* 0x025 */ "INT_VECTOR_BASE", - /* 0x026 */ UNUSED_REG, - /* 0x027 */ UNUSED_REG, - /* 0x028 */ UNUSED_REG, - /* 0x029 */ UNUSED_REG, - /* 0x02a */ UNUSED_REG, - /* 0x02b */ UNUSED_REG, - /* 0x02c */ UNUSED_REG, - /* 0x02d */ UNUSED_REG, - /* 0x02e */ UNUSED_REG, - /* 0x02f */ UNUSED_REG, - AUX_UNUSED_16 /* 0x030 - 0x03f */ - /* 0x040 */ UNUSED_REG, - /* 0x041 */ "AUX_MACMODE", - /* 0x042 */ UNUSED_REG, - /* 0x043 */ "AUX_IRQLV12", - /* 0x044 */ UNUSED_REG, - /* 0x045 */ UNUSED_REG, - /* 0x046 */ UNUSED_REG, - /* 0x047 */ UNUSED_REG, - /* 0x048 */ UNUSED_REG, - /* 0x049 */ UNUSED_REG, - /* 0x04a */ UNUSED_REG, - /* 0x04b */ UNUSED_REG, - /* 0x04c */ UNUSED_REG, - /* 0x04d */ UNUSED_REG, - /* 0x04e */ UNUSED_REG, - /* 0x04f */ UNUSED_REG, - AUX_UNUSED_16 /* 0x050 - 0x05f */ - // build configuration registers 0x060 - 0x07f - /* 0x060 */ "RESERVED AUX 0x60",/* 0x061 */ "RESERVED AUX 0x61",/* 0x062 */ "RESERVED AUX 0x62",/* 0x063 */ "RESERVED AUX 0x63",/* 0x064 */ "RESERVED AUX 0x64",/* 0x065 */ "RESERVED AUX 0x65",/* 0x066 */ "RESERVED AUX 0x66",/* 0x067 */ "RESERVED AUX 0x67",/* 0x068 */ "RESERVED AUX 0x68",/* 0x069 */ "RESERVED AUX 0x69",/* 0x06a */ "RESERVED AUX 0x6a",/* 0x06b */ "RESERVED AUX 0x6b",/* 0x06c */ "RESERVED AUX 0x6c",/* 0x06d */ "RESERVED AUX 0x6d",/* 0x06e */ "RESERVED AUX 0x6e",/* 0x06f */ "RESERVED AUX 0x6f", - /* 0x070 */ "RESERVED AUX 0x70",/* 0x071 */ "RESERVED AUX 0x71",/* 0x072 */ "RESERVED AUX 0x72",/* 0x073 */ "RESERVED AUX 0x73",/* 0x074 */ "RESERVED AUX 0x74",/* 0x075 */ "RESERVED AUX 0x75",/* 0x076 */ "RESERVED AUX 0x76",/* 0x077 */ "RESERVED AUX 0x77",/* 0x078 */ "RESERVED AUX 0x78",/* 0x079 */ "RESERVED AUX 0x79",/* 0x07a */ "RESERVED AUX 0x7a",/* 0x07b */ "RESERVED AUX 0x7b",/* 0x07c */ "RESERVED AUX 0x7c",/* 0x07d */ "RESERVED AUX 0x7d",/* 0x07e */ "RESERVED AUX 0x7e",/* 0x07f */ "RESERVED AUX 0x7f", - AUX_UNUSED_16 /* 0x080 - 0x08f */ - AUX_UNUSED_16 /* 0x090 - 0x09f */ - AUX_UNUSED_16 /* 0x0a0 - 0x0af */ - AUX_UNUSED_16 /* 0x0b0 - 0x0bf */ - // build configuration registers 0x0c0 - 0x0ff - /* 0x0c0 */ "RESERVED AUX 0xc0",/* 0x0c1 */ "RESERVED AUX 0xc1",/* 0x0c2 */ "RESERVED AUX 0xc2",/* 0x0c3 */ "RESERVED AUX 0xc3",/* 0x0c4 */ "RESERVED AUX 0xc4",/* 0x0c5 */ "RESERVED AUX 0xc5",/* 0x0c6 */ "RESERVED AUX 0xc6",/* 0x0c7 */ "RESERVED AUX 0xc7",/* 0x0c8 */ "RESERVED AUX 0xc8",/* 0x0c9 */ "RESERVED AUX 0xc9",/* 0x0ca */ "RESERVED AUX 0xca",/* 0x0cb */ "RESERVED AUX 0xcb",/* 0x0cc */ "RESERVED AUX 0xcc",/* 0x0cd */ "RESERVED AUX 0xcd",/* 0x0ce */ "RESERVED AUX 0xce",/* 0x0cf */ "RESERVED AUX 0xcf", - /* 0x0d0 */ "RESERVED AUX 0xd0",/* 0x0d1 */ "RESERVED AUX 0xd1",/* 0x0d2 */ "RESERVED AUX 0xd2",/* 0x0d3 */ "RESERVED AUX 0xd3",/* 0x0d4 */ "RESERVED AUX 0xd4",/* 0x0d5 */ "RESERVED AUX 0xd5",/* 0x0d6 */ "RESERVED AUX 0xd6",/* 0x0d7 */ "RESERVED AUX 0xd7",/* 0x0d8 */ "RESERVED AUX 0xd8",/* 0x0d9 */ "RESERVED AUX 0xd9",/* 0x0da */ "RESERVED AUX 0xda",/* 0x0db */ "RESERVED AUX 0xdb",/* 0x0dc */ "RESERVED AUX 0xdc",/* 0x0dd */ "RESERVED AUX 0xdd",/* 0x0de */ "RESERVED AUX 0xde",/* 0x0df */ "RESERVED AUX 0xdf", - /* 0x0e0 */ "RESERVED AUX 0xe0",/* 0x0e1 */ "RESERVED AUX 0xe1",/* 0x0e2 */ "RESERVED AUX 0xe2",/* 0x0e3 */ "RESERVED AUX 0xe3",/* 0x0e4 */ "RESERVED AUX 0xe4",/* 0x0e5 */ "RESERVED AUX 0xe5",/* 0x0e6 */ "RESERVED AUX 0xe6",/* 0x0e7 */ "RESERVED AUX 0xe7",/* 0x0e8 */ "RESERVED AUX 0xe8",/* 0x0e9 */ "RESERVED AUX 0xe9",/* 0x0ea */ "RESERVED AUX 0xea",/* 0x0eb */ "RESERVED AUX 0xeb",/* 0x0ec */ "RESERVED AUX 0xec",/* 0x0ed */ "RESERVED AUX 0xed",/* 0x0ee */ "RESERVED AUX 0xee",/* 0x0ef */ "RESERVED AUX 0xef", - /* 0x0f0 */ "RESERVED AUX 0xf0",/* 0x0f1 */ "RESERVED AUX 0xf1",/* 0x0f2 */ "RESERVED AUX 0xf2",/* 0x0f3 */ "RESERVED AUX 0xf3",/* 0x0f4 */ "RESERVED AUX 0xf4",/* 0x0f5 */ "RESERVED AUX 0xf5",/* 0x0f6 */ "RESERVED AUX 0xf6",/* 0x0f7 */ "RESERVED AUX 0xf7",/* 0x0f8 */ "RESERVED AUX 0xf8",/* 0x0f9 */ "RESERVED AUX 0xf9",/* 0x0fa */ "RESERVED AUX 0xfa",/* 0x0fb */ "RESERVED AUX 0xfb",/* 0x0fc */ "RESERVED AUX 0xfc",/* 0x0fd */ "RESERVED AUX 0xfd",/* 0x0fe */ "RESERVED AUX 0xfe",/* 0x0ff */ "RESERVED AUX 0xff", - /* 0x100 */ "COUNT1", - /* 0x101 */ "CONTROL1", - /* 0x102 */ "LIMIT1", - /* 0x103 */ UNUSED_REG, - /* 0x104 */ UNUSED_REG, - /* 0x105 */ UNUSED_REG, - /* 0x106 */ UNUSED_REG, - /* 0x107 */ UNUSED_REG, - /* 0x108 */ UNUSED_REG, - /* 0x109 */ UNUSED_REG, - /* 0x10a */ UNUSED_REG, - /* 0x10b */ UNUSED_REG, - /* 0x10c */ UNUSED_REG, - /* 0x10d */ UNUSED_REG, - /* 0x10e */ UNUSED_REG, - /* 0x10f */ UNUSED_REG, - AUX_UNUSED_16 /* 0x110 - 0x11f */ - AUX_UNUSED_16 /* 0x120 - 0x12f */ - AUX_UNUSED_16 /* 0x130 - 0x13f */ - AUX_UNUSED_16 /* 0x140 - 0x14f */ - AUX_UNUSED_16 /* 0x150 - 0x15f */ - AUX_UNUSED_16 /* 0x160 - 0x16f */ - AUX_UNUSED_16 /* 0x170 - 0x17f */ - AUX_UNUSED_16 /* 0x180 - 0x18f */ - AUX_UNUSED_16 /* 0x190 - 0x19f */ - AUX_UNUSED_16 /* 0x1a0 - 0x1af */ - AUX_UNUSED_16 /* 0x1b0 - 0x1bf */ - AUX_UNUSED_16 /* 0x1c0 - 0x1cf */ - AUX_UNUSED_16 /* 0x1d0 - 0x1df */ - AUX_UNUSED_16 /* 0x1e0 - 0x1ef */ - AUX_UNUSED_16 /* 0x1f0 - 0x1ff */ - /* 0x200 */ "AUX_IRQ_LEV", - /* 0x201 */ "AUX_IRQ_HINT", - /* 0x203 */ UNUSED_REG, - /* 0x203 */ UNUSED_REG, - /* 0x204 */ UNUSED_REG, - /* 0x205 */ UNUSED_REG, - /* 0x206 */ UNUSED_REG, - /* 0x207 */ UNUSED_REG, - /* 0x208 */ UNUSED_REG, - /* 0x209 */ UNUSED_REG, - /* 0x20a */ UNUSED_REG, - /* 0x20b */ UNUSED_REG, - /* 0x20c */ UNUSED_REG, - /* 0x20d */ UNUSED_REG, - /* 0x20e */ UNUSED_REG, - /* 0x20f */ UNUSED_REG, - AUX_UNUSED_16 /* 0x210 - 0x21f */ - AUX_UNUSED_16 /* 0x220 - 0x22f */ - AUX_UNUSED_16 /* 0x230 - 0x23f */ - AUX_UNUSED_16 /* 0x240 - 0x24f */ - AUX_UNUSED_16 /* 0x250 - 0x25f */ - AUX_UNUSED_16 /* 0x260 - 0x26f */ - AUX_UNUSED_16 /* 0x270 - 0x27f */ - AUX_UNUSED_16 /* 0x280 - 0x28f */ - AUX_UNUSED_16 /* 0x290 - 0x29f */ - AUX_UNUSED_16 /* 0x2a0 - 0x2af */ - AUX_UNUSED_16 /* 0x2b0 - 0x2bf */ - AUX_UNUSED_16 /* 0x2c0 - 0x2cf */ - AUX_UNUSED_16 /* 0x2d0 - 0x2df */ - AUX_UNUSED_16 /* 0x2e0 - 0x2ef */ - AUX_UNUSED_16 /* 0x2f0 - 0x2ff */ - - AUX_UNUSED_16 /* 0x300 - 0x30f */ - AUX_UNUSED_16 /* 0x310 - 0x31f */ - AUX_UNUSED_16 /* 0x320 - 0x32f */ - AUX_UNUSED_16 /* 0x330 - 0x33f */ - AUX_UNUSED_16 /* 0x340 - 0x34f */ - AUX_UNUSED_16 /* 0x350 - 0x35f */ - AUX_UNUSED_16 /* 0x360 - 0x36f */ - AUX_UNUSED_16 /* 0x370 - 0x37f */ - AUX_UNUSED_16 /* 0x380 - 0x38f */ - AUX_UNUSED_16 /* 0x390 - 0x39f */ - AUX_UNUSED_16 /* 0x3a0 - 0x3af */ - AUX_UNUSED_16 /* 0x3b0 - 0x3bf */ - AUX_UNUSED_16 /* 0x3c0 - 0x3cf */ - AUX_UNUSED_16 /* 0x3d0 - 0x3df */ - AUX_UNUSED_16 /* 0x3e0 - 0x3ef */ - AUX_UNUSED_16 /* 0x3f0 - 0x3ff */ - - /* 0x400 */ "ERET", - /* 0x401 */ "ERBTA", - /* 0x403 */ "ERSTATUS", - /* 0x403 */ "ECR", - /* 0x404 */ "EFA", - /* 0x405 */ UNUSED_REG, - /* 0x406 */ UNUSED_REG, - /* 0x407 */ UNUSED_REG, - /* 0x408 */ UNUSED_REG, - /* 0x409 */ UNUSED_REG, - /* 0x40a */ "ICAUSE1", - /* 0x40b */ "ICAUSE2", - /* 0x40c */ "AUX_IENABLE", - /* 0x40d */ "AUX_ITRIGGER", - /* 0x40e */ UNUSED_REG, - /* 0x40f */ UNUSED_REG, - - /* 0x410 */ "XPU", - /* 0x411 */ UNUSED_REG, - /* 0x412 */ "BTA", - /* 0x413 */ "BTA_L1", - /* 0x414 */ "BTA_L2", - /* 0x415 */ "AUX_IRQ_PULSE_CANCEL", - /* 0x416 */ "AUX_IRQ_PENDING", - /* 0x417 */ UNUSED_REG, - /* 0x418 */ UNUSED_REG, - /* 0x419 */ UNUSED_REG, - /* 0x41a */ UNUSED_REG, - /* 0x41b */ UNUSED_REG, - /* 0x41c */ UNUSED_REG, - /* 0x41d */ UNUSED_REG, - /* 0x41e */ UNUSED_REG, - /* 0x41f */ UNUSED_REG -}; - -//#define EXPLICIT_EXTENSIONS - -const char *datasize[0x4] = -{ -#ifdef EXPLICIT_EXTENSIONS - /* 00 */ ".L", // Dword (default) (can use no extension, using .L to be explicit) -#else - /* 00 */ "",// Dword (default) -#endif - /* 01 */ ".B", // Byte - /* 02 */ ".W", // Word - /* 03 */ "." -}; - -const char *dataextend[0x2] = -{ -#ifdef EXPLICIT_EXTENSIONS - /* 00 */ ".ZX", // Zero Extend (can use no extension, using .ZX to be explicit) -#else - /* 00 */ "", // Zero Extend -#endif - /* 01 */ ".X" // Sign Extend -}; - -const char *addressmode[0x4] = -{ -#ifdef EXPLICIT_EXTENSIONS - /* 00 */ ".AN", // No Writeback (can use no extension, using .AN to be explicit) -#else - /* 00 */ "", // No Writeback -#endif - /* 01 */ ".AW", // Writeback pre memory access - /* 02 */ ".AB", // Writeback post memory access - /* 03 */ ".AS" // scaled -}; - -const char *cachebit[0x2] = -{ -#ifdef EXPLICIT_EXTENSIONS - /* 00 */ ".EN", // Data Cache Enabled (can use no extension, using .EN to be explicit) -#else - /* 00 */ "", // Data Cache Enabled -#endif - /* 01 */ ".DI" // Direct to Memory (Cache Bypass) -}; - -const char *flagbit[0x2] = -{ -#ifdef EXPLICIT_EXTENSIONS - /* 00 */ ".NF", // Don't Set Flags (can use no extension, using .NF to be explicit) -#else - /* 00 */ "", // Don't Set Flags -#endif - /* 01 */ ".F" // Set Flags -}; - -const char *delaybit[0x2] = -{ - /* 00 */ ".ND", // Don't execute opcode in delay slot - /* 01 */ ".D" // Execute Opcode in delay slot -}; - - -const char *regnames[0x40] = -{ - /* 00 */ "r0", - /* 01 */ "r1", - /* 02 */ "r2", - /* 03 */ "r3", - /* 04 */ "r4", - /* 05 */ "r5", - /* 06 */ "r6", - /* 07 */ "r7", - /* 08 */ "r8", - /* 09 */ "r9", - /* 0a */ "r10", - /* 0b */ "r11", - /* 0c */ "r12", - /* 0d */ "r13", - /* 0e */ "r14", - /* 0f */ "r15", - - /* 10 */ "r16", - /* 11 */ "r17", - /* 12 */ "r18", - /* 13 */ "r19", - /* 14 */ "r20", - /* 15 */ "r21", - /* 16 */ "r22", - /* 17 */ "r23", - /* 18 */ "r24", - /* 19 */ "r25", - /* 1a */ "r26_GP", - /* 1b */ "r27_FP", - /* 1c */ "r28_SP", - /* 1d */ "r29_ILINK1", - /* 1e */ "r30_ILINK2", - /* 1f */ "r31_BLINK", - - /* 20 */ "r32(ext)", - /* 21 */ "r33(ext)", - /* 22 */ "r34(ext)", - /* 23 */ "r35(ext)", - /* 24 */ "r36(ext)", - /* 25 */ "r37(ext)", - /* 26 */ "r38(ext)", - /* 27 */ "r39(ext)", - /* 28 */ "r40(ext)", - /* 29 */ "r41(ext)", - /* 2a */ "r42(ext)", - /* 2b */ "r43(ext)", - /* 2c */ "r44(ext)", - /* 2d */ "r45(ext)", - /* 2e */ "r46(ext)", - /* 2f */ "r47(ext)", - - /* 30 */ "r48(ext)", - /* 31 */ "r49(ext)", - /* 32 */ "r50(ext)", - /* 33 */ "r51(ext)", - /* 34 */ "r52(ext)", - /* 35 */ "r53(ext)", - /* 36 */ "r54(ext)", - /* 37 */ "r55(ext)", - /* 38 */ "r56(ext)", - /* 39 */ "r57(M-LO)", // MLO (result registers for optional multply functions) - /* 3a */ "r58(M-MID)", // MMID - /* 3b */ "r59(M-HI)", // MHI - /* 3c */ "r60(LP_COUNT)", - /* 3d */ "r61(reserved)", - /* 3e */ "r62(LIMM)", // use Long Immediate Data instead of register - /* 3f */ "r63(PCL)" -}; - -#if 0 -const char *opcodes_temp[0x40] = -{ - /* 00 */ "0x00", - /* 01 */ "0x01", - /* 02 */ "0x02", - /* 03 */ "0x03", - /* 04 */ "0x04", - /* 05 */ "0x05", - /* 06 */ "0x06", - /* 07 */ "0x07", - /* 08 */ "0x08", - /* 09 */ "0x09", - /* 0a */ "0x0a", - /* 0b */ "0x0b", - /* 0c */ "0x0c", - /* 0d */ "0x0d", - /* 0e */ "0x0e", - /* 0f */ "0x0f", - - /* 10 */ "0x10", - /* 11 */ "0x11", - /* 12 */ "0x12", - /* 13 */ "0x13", - /* 14 */ "0x14", - /* 15 */ "0x15", - /* 16 */ "0x16", - /* 17 */ "0x17", - /* 18 */ "0x18", - /* 19 */ "0x19", - /* 1a */ "0x1a", - /* 1b */ "0x1b", - /* 1c */ "0x1c", - /* 1d */ "0x1d", - /* 1e */ "0x1e", - /* 1f */ "0x1f", - - /* 20 */ "0x20", - /* 21 */ "0x21", - /* 22 */ "0x22", - /* 23 */ "0x23", - /* 24 */ "0x24", - /* 25 */ "0x25", - /* 26 */ "0x26", - /* 27 */ "0x27", - /* 28 */ "0x28", - /* 29 */ "0x29", - /* 2a */ "0x2a", - /* 2b */ "0x2b", - /* 2c */ "0x2c", - /* 2d */ "0x2d", - /* 2e */ "0x2e", - /* 2f */ "0x2f", - - /* 30 */ "0x30", - /* 31 */ "0x31", - /* 32 */ "0x32", - /* 33 */ "0x33", - /* 34 */ "0x34", - /* 35 */ "0x35", - /* 36 */ "0x36", - /* 37 */ "0x37", - /* 38 */ "0x38", - /* 39 */ "0x39", - /* 3a */ "0x3a", - /* 3b */ "0x3b", - /* 3c */ "0x3c", - /* 3d */ "0x3d", - /* 3e */ "0x3e", - /* 3f */ "0x3f", -}; -#endif - - -const char *opcodes_04[0x40] = -{ - /* 00 */ "ADD", - /* 01 */ "ADC", - /* 02 */ "SUB", - /* 03 */ "SBC", - /* 04 */ "AND", - /* 05 */ "OR", - /* 06 */ "BIC", - /* 07 */ "XOR", - /* 08 */ "MAX", - /* 09 */ "MIN", - /* 0a */ "MOV", - /* 0b */ "TST", - /* 0c */ "CMP", - /* 0d */ "RCMP", - /* 0e */ "RSUB", - /* 0f */ "BSET", - - /* 10 */ "BCLR", - /* 11 */ "BTST", - /* 12 */ "BXOR", - /* 13 */ "BSMK", - /* 14 */ "ADD1", - /* 15 */ "ADD2", - /* 16 */ "ADD3", - /* 17 */ "SUB1", - /* 18 */ "SUB2", - /* 19 */ "SUB3", - /* 1a */ "MPY", - /* 1b */ "MPYH", - /* 1c */ "MPYHU", - /* 1d */ "MPYU", - /* 1e */ "0x1e", - /* 1f */ "0x1f", - - /* 20 */ "Jcc", - /* 21 */ "Jcc.D", - /* 22 */ "JLcc", - /* 23 */ "JLcc.D", - /* 24 */ "0x24", - /* 25 */ "0x25", - /* 26 */ "0x26", - /* 27 */ "0x27", - /* 28 */ "LPcc", - /* 29 */ "FLAG", - /* 2a */ "LR", - /* 2b */ "SR", - /* 2c */ "0x2c", - /* 2d */ "0x2d", - /* 2e */ "0x2e", - /* 2f */ "SOP table", - - /* 30 */ "LD", - /* 31 */ "LD", - /* 32 */ "LD", - /* 33 */ "LD", - /* 34 */ "LD", - /* 35 */ "LD", - /* 36 */ "LD", - /* 37 */ "LD", - /* 38 */ "0x38", - /* 39 */ "0x39", - /* 3a */ "0x3a", - /* 3b */ "0x3b", - /* 3c */ "0x3c", - /* 3d */ "0x3d", - /* 3e */ "0x3e", - /* 3f */ "0x3f", -}; diff --git a/src/devices/cpu/arcompact/arcompact_common.h b/src/devices/cpu/arcompact/arcompact_common.h deleted file mode 100644 index 86259ba2972..00000000000 --- a/src/devices/cpu/arcompact/arcompact_common.h +++ /dev/null @@ -1,24 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:David Haywood -/*********************************\ - - ARCompact Core - -\*********************************/ - -extern const char *conditions[0x20]; -extern const char *auxregnames[0x420]; -extern const char *datasize[0x4]; -extern const char *dataextend[0x2]; -extern const char *addressmode[0x4]; -extern const char *cachebit[0x2]; -extern const char *flagbit[0x2]; -extern const char *delaybit[0x2]; -extern const char *regnames[0x40]; -extern const char *opcodes_04[0x40]; - -#define REG_BLINK (0x1f) // r31 -#define REG_SP (0x1c) // r28 -#define REG_ILINK1 (0x1d) // r29 -#define REG_ILINK2 (0x1e) // r30 -#define REG_LP_COUNT (0x3c) // r60 diff --git a/src/devices/cpu/arcompact/arcompact_execute.cpp b/src/devices/cpu/arcompact/arcompact_execute.cpp index 53d3ce742cb..fc4dcca37a6 100644 --- a/src/devices/cpu/arcompact/arcompact_execute.cpp +++ b/src/devices/cpu/arcompact/arcompact_execute.cpp @@ -4,7 +4,13 @@ #include "emu.h" #include "debugger.h" #include "arcompact.h" -#include "arcompact_common.h" +#include "arcompactdasm.h" + +#define REG_BLINK (0x1f) // r31 +#define REG_SP (0x1c) // r28 +#define REG_ILINK1 (0x1d) // r29 +#define REG_ILINK2 (0x1e) // r30 +#define REG_LP_COUNT (0x3c) // r60 #define ARCOMPACT_LOGGING 1 @@ -128,35 +134,35 @@ int arcompact_device::check_condition(uint8_t condition) case 0x00: return 1; // AL case 0x01: return CONDITION_EQ; case 0x02: return !CONDITION_EQ; // NE - case 0x03: fatalerror("unhandled condition check %s", conditions[condition]); return -1; + case 0x03: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; case 0x04: return CONDITION_MI; // MI (N) case 0x05: return CONDITION_CS; // CS (Carry Set / Lower than) - case 0x06: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x07: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x08: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x09: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x0a: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x0b: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x0c: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x0d: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x0e: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x0f: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x10: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x11: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x12: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x13: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x14: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x15: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x16: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x17: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x18: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x19: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x1a: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x1b: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x1c: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x1d: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x1e: fatalerror("unhandled condition check %s", conditions[condition]); return -1; - case 0x1f: fatalerror("unhandled condition check %s", conditions[condition]); return -1; + case 0x06: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x07: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x08: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x09: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x0a: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x0b: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x0c: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x0d: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x0e: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x0f: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x10: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x11: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x12: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x13: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x14: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x15: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x16: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x17: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x18: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x19: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x1a: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x1b: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x1c: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x1d: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x1e: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; + case 0x1f: fatalerror("unhandled condition check %s", arcompact_disassembler::conditions[condition]); return -1; } return -1; @@ -1844,58 +1850,58 @@ ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_helper(OPS_32, const char ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_01(OPS_32) { - return arcompact_handle04_helper(PARAMS, opcodes_04[0x01], /*"ADC"*/ 0,0); + return arcompact_handle04_helper(PARAMS, arcompact_disassembler::opcodes_04[0x01], /*"ADC"*/ 0,0); } ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_03(OPS_32) { - return arcompact_handle04_helper(PARAMS, opcodes_04[0x03], /*"SBC"*/ 0,0); + return arcompact_handle04_helper(PARAMS, arcompact_disassembler::opcodes_04[0x03], /*"SBC"*/ 0,0); } ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_08(OPS_32) { - return arcompact_handle04_helper(PARAMS, opcodes_04[0x08], /*"MAX"*/ 0,0); + return arcompact_handle04_helper(PARAMS, arcompact_disassembler::opcodes_04[0x08], /*"MAX"*/ 0,0); } ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_09(OPS_32) { - return arcompact_handle04_helper(PARAMS, opcodes_04[0x09], /*"MIN"*/ 0,0); + return arcompact_handle04_helper(PARAMS, arcompact_disassembler::opcodes_04[0x09], /*"MIN"*/ 0,0); } ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_0b(OPS_32) { - return arcompact_handle04_helper(PARAMS, opcodes_04[0x0b], /*"TST"*/ 1,0); + return arcompact_handle04_helper(PARAMS, arcompact_disassembler::opcodes_04[0x0b], /*"TST"*/ 1,0); } ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_0c(OPS_32) { - return arcompact_handle04_helper(PARAMS, opcodes_04[0x0c], /*"CMP"*/ 1,0); + return arcompact_handle04_helper(PARAMS, arcompact_disassembler::opcodes_04[0x0c], /*"CMP"*/ 1,0); } ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_0d(OPS_32) { - return arcompact_handle04_helper(PARAMS, opcodes_04[0x0d], /*"RCMP"*/ 1,0); + return arcompact_handle04_helper(PARAMS, arcompact_disassembler::opcodes_04[0x0d], /*"RCMP"*/ 1,0); } ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_10(OPS_32) { - return arcompact_handle04_helper(PARAMS, opcodes_04[0x10], /*"BCLR"*/ 0,0); + return arcompact_handle04_helper(PARAMS, arcompact_disassembler::opcodes_04[0x10], /*"BCLR"*/ 0,0); } ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_11(OPS_32) { - return arcompact_handle04_helper(PARAMS, opcodes_04[0x11], /*"BTST"*/ 0,0); + return arcompact_handle04_helper(PARAMS, arcompact_disassembler::opcodes_04[0x11], /*"BTST"*/ 0,0); } ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_12(OPS_32) { - return arcompact_handle04_helper(PARAMS, opcodes_04[0x12], /*"BXOR"*/ 0,0); + return arcompact_handle04_helper(PARAMS, arcompact_disassembler::opcodes_04[0x12], /*"BXOR"*/ 0,0); } @@ -1905,22 +1911,22 @@ ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_12(OPS_32) ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_1a(OPS_32) { - return arcompact_handle04_helper(PARAMS, opcodes_04[0x1a], /*"MPY"*/ 0,0); + return arcompact_handle04_helper(PARAMS, arcompact_disassembler::opcodes_04[0x1a], /*"MPY"*/ 0,0); } // * ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_1b(OPS_32) { - return arcompact_handle04_helper(PARAMS, opcodes_04[0x1b], /*"MPYH"*/ 0,0); + return arcompact_handle04_helper(PARAMS, arcompact_disassembler::opcodes_04[0x1b], /*"MPYH"*/ 0,0); } // * ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_1c(OPS_32) { - return arcompact_handle04_helper(PARAMS, opcodes_04[0x1c], /*"MPYHU"*/ 0,0); + return arcompact_handle04_helper(PARAMS, arcompact_disassembler::opcodes_04[0x1c], /*"MPYHU"*/ 0,0); } // * ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_1d(OPS_32) { - return arcompact_handle04_helper(PARAMS, opcodes_04[0x1d], /*"MPYU"*/ 0,0); + return arcompact_handle04_helper(PARAMS, arcompact_disassembler::opcodes_04[0x1d], /*"MPYU"*/ 0,0); } // * ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_20_p00(OPS_32) @@ -2202,12 +2208,12 @@ ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_21_p11_m1(OPS_32) ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_22(OPS_32) { - return arcompact_handle04_helper(PARAMS, opcodes_04[0x22], /*"JL"*/ 1,1); + return arcompact_handle04_helper(PARAMS, arcompact_disassembler::opcodes_04[0x22], /*"JL"*/ 1,1); } ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_23(OPS_32) { - return arcompact_handle04_helper(PARAMS, opcodes_04[0x23], /*"JL.D"*/ 1,1); + return arcompact_handle04_helper(PARAMS, arcompact_disassembler::opcodes_04[0x23], /*"JL.D"*/ 1,1); } @@ -2238,7 +2244,7 @@ ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_28(OPS_32) // LPcc (loop { // 0010 0RRR 1110 1000 0RRR uuuu uu1Q QQQQ COMMON32_GET_u6 COMMON32_GET_CONDITION - //arcompact_fatal("Lp conditional %s not supported %d", conditions[condition], u); + //arcompact_fatal("Lp conditional %s not supported %d", arcompact_disassembler::conditions[condition], u); // if the loop condition fails then just jump to after the end of the loop, don't set any registers if (!check_condition(condition)) @@ -2264,7 +2270,7 @@ ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_28(OPS_32) // LPcc (loop ARCOMPACT_RETTYPE arcompact_device::arcompact_handle04_29(OPS_32) { // leapster bios uses formats for FLAG that are not defined, bug I guess work anyway (P modes 0 / 1) - return arcompact_handle04_helper(PARAMS, opcodes_04[0x29], /*"FLAG"*/ 1,1); + return arcompact_handle04_helper(PARAMS, arcompact_disassembler::opcodes_04[0x29], /*"FLAG"*/ 1,1); } diff --git a/src/devices/cpu/arcompact/arcompactdasm.cpp b/src/devices/cpu/arcompact/arcompactdasm.cpp index cd557017332..7283cfd06b6 100644 --- a/src/devices/cpu/arcompact/arcompactdasm.cpp +++ b/src/devices/cpu/arcompact/arcompactdasm.cpp @@ -7,51 +7,564 @@ \*********************************/ #include "emu.h" -#include +#include "arcompactdasm.h" -#include "arcompactdasm_dispatch.h" -#include "arcompactdasm_ops.h" +u32 arcompact_disassembler::opcode_alignment() const +{ + return 2; +} + + +// condition codes (basic ones are the same as arc +const char *const arcompact_disassembler::conditions[0x20] = +{ + /* 00 */ "AL", // (aka RA - Always) + /* 01 */ "EQ", // (aka Z - Zero + /* 02 */ "NE", // (aka NZ - Non-Zero) + /* 03 */ "PL", // (aka P - Positive) + /* 04 */ "MI", // (aka N - Negative) + /* 05 */ "CS", // (aka C, LO - Carry set / Lower than) (unsigned) + /* 06 */ "CC", // (aka CC, NC, HS - Carry Clear / Higher or Same) (unsigned) + /* 07 */ "VS", // (aka V - Overflow set) + /* 08 */ "VC", // (aka NV - Overflow clear) + /* 09 */ "GT", // ( - Greater than) (signed) + /* 0a */ "GE", // ( - Greater than or Equal) (signed) + /* 0b */ "LT", // ( - Less than) (signed) + /* 0c */ "LE", // ( - Less than or Equal) (signed) + /* 0d */ "HI", // ( - Higher than) (unsigned) + /* 0e */ "LS", // ( - Lower or Same) (unsigned) + /* 0f */ "PNZ",// ( - Positive non-0 value) + /* 10 */ "0x10 Reserved", // possible CPU implementation specifics + /* 11 */ "0x11 Reserved", + /* 12 */ "0x12 Reserved", + /* 13 */ "0x13 Reserved", + /* 14 */ "0x14 Reserved", + /* 15 */ "0x15 Reserved", + /* 16 */ "0x16 Reserved", + /* 17 */ "0x17 Reserved", + /* 18 */ "0x18 Reserved", + /* 19 */ "0x19 Reserved", + /* 1a */ "0x1a Reserved", + /* 1b */ "0x1b Reserved", + /* 1c */ "0x1c Reserved", + /* 1d */ "0x1d Reserved", + /* 1e */ "0x1e Reserved", + /* 1f */ "0x1f Reserved" +}; + +#define UNUSED_REG "unusedreg" + +#define AUX_UNUSED_16 \ + /* 0xxx0 */ UNUSED_REG, /* 0xxx1 */ UNUSED_REG, /* 0xxx2 */ UNUSED_REG, /* 0xxx3 */ UNUSED_REG, /* 0xxx4 */ UNUSED_REG, /* 0xxx5 */ UNUSED_REG, /* 0xxx6 */ UNUSED_REG, /* 0xxx7 */ UNUSED_REG, /* 0xxx8 */ UNUSED_REG, /* 0xxx9 */ UNUSED_REG, /* 0xxxa */ UNUSED_REG, /* 0xxxb */ UNUSED_REG, /* 0xxxc */ UNUSED_REG, /* 0xxxd */ UNUSED_REG, /* 0xxxe */ UNUSED_REG, /* 0xxxf */ UNUSED_REG, + +// the Auxiliary Register set is actually a 2^32 dword address space (so 16 GB / 34-bit) +// this table just allows us to improve the debugger display for some of the common core / internal ones +const char *const arcompact_disassembler::auxregnames[0x420] = +{ + /* 0x000 */ "STATUS", + /* 0x001 */ "SEMAPHOR", + /* 0x002 */ "LP_START", + /* 0x003 */ "LP_END", + /* 0x004 */ "IDENTITY", + /* 0x005 */ "DEBUG", + /* 0x006 */ "PC", + /* 0x007 */ UNUSED_REG, + /* 0x008 */ UNUSED_REG, + /* 0x009 */ UNUSED_REG, + /* 0x00a */ "STATUS32", + /* 0x00b */ "STATUS32_L1", + /* 0x00c */ "STATUS32_L2", + /* 0x00d */ UNUSED_REG, + /* 0x00e */ UNUSED_REG, + /* 0x00f */ UNUSED_REG, + + /* 0x010 */ UNUSED_REG, + /* 0x011 */ UNUSED_REG, + /* 0x012 */ "MULHI", // extension register + /* 0x013 */ UNUSED_REG, + /* 0x014 */ UNUSED_REG, + /* 0x015 */ UNUSED_REG, + /* 0x016 */ UNUSED_REG, + /* 0x017 */ UNUSED_REG, + /* 0x018 */ UNUSED_REG, + /* 0x019 */ UNUSED_REG, + /* 0x01a */ UNUSED_REG, + /* 0x01b */ UNUSED_REG, + /* 0x01c */ UNUSED_REG, + /* 0x01d */ UNUSED_REG, + /* 0x01e */ UNUSED_REG, + /* 0x01f */ UNUSED_REG, + /* 0x020 */ UNUSED_REG, + /* 0x021 */ "COUNT0", + /* 0x022 */ "CONTROL0", + /* 0x023 */ "LIMIT0", + /* 0x024 */ UNUSED_REG, + /* 0x025 */ "INT_VECTOR_BASE", + /* 0x026 */ UNUSED_REG, + /* 0x027 */ UNUSED_REG, + /* 0x028 */ UNUSED_REG, + /* 0x029 */ UNUSED_REG, + /* 0x02a */ UNUSED_REG, + /* 0x02b */ UNUSED_REG, + /* 0x02c */ UNUSED_REG, + /* 0x02d */ UNUSED_REG, + /* 0x02e */ UNUSED_REG, + /* 0x02f */ UNUSED_REG, + AUX_UNUSED_16 /* 0x030 - 0x03f */ + /* 0x040 */ UNUSED_REG, + /* 0x041 */ "AUX_MACMODE", + /* 0x042 */ UNUSED_REG, + /* 0x043 */ "AUX_IRQLV12", + /* 0x044 */ UNUSED_REG, + /* 0x045 */ UNUSED_REG, + /* 0x046 */ UNUSED_REG, + /* 0x047 */ UNUSED_REG, + /* 0x048 */ UNUSED_REG, + /* 0x049 */ UNUSED_REG, + /* 0x04a */ UNUSED_REG, + /* 0x04b */ UNUSED_REG, + /* 0x04c */ UNUSED_REG, + /* 0x04d */ UNUSED_REG, + /* 0x04e */ UNUSED_REG, + /* 0x04f */ UNUSED_REG, + AUX_UNUSED_16 /* 0x050 - 0x05f */ + // build configuration registers 0x060 - 0x07f + /* 0x060 */ "RESERVED AUX 0x60",/* 0x061 */ "RESERVED AUX 0x61",/* 0x062 */ "RESERVED AUX 0x62",/* 0x063 */ "RESERVED AUX 0x63",/* 0x064 */ "RESERVED AUX 0x64",/* 0x065 */ "RESERVED AUX 0x65",/* 0x066 */ "RESERVED AUX 0x66",/* 0x067 */ "RESERVED AUX 0x67",/* 0x068 */ "RESERVED AUX 0x68",/* 0x069 */ "RESERVED AUX 0x69",/* 0x06a */ "RESERVED AUX 0x6a",/* 0x06b */ "RESERVED AUX 0x6b",/* 0x06c */ "RESERVED AUX 0x6c",/* 0x06d */ "RESERVED AUX 0x6d",/* 0x06e */ "RESERVED AUX 0x6e",/* 0x06f */ "RESERVED AUX 0x6f", + /* 0x070 */ "RESERVED AUX 0x70",/* 0x071 */ "RESERVED AUX 0x71",/* 0x072 */ "RESERVED AUX 0x72",/* 0x073 */ "RESERVED AUX 0x73",/* 0x074 */ "RESERVED AUX 0x74",/* 0x075 */ "RESERVED AUX 0x75",/* 0x076 */ "RESERVED AUX 0x76",/* 0x077 */ "RESERVED AUX 0x77",/* 0x078 */ "RESERVED AUX 0x78",/* 0x079 */ "RESERVED AUX 0x79",/* 0x07a */ "RESERVED AUX 0x7a",/* 0x07b */ "RESERVED AUX 0x7b",/* 0x07c */ "RESERVED AUX 0x7c",/* 0x07d */ "RESERVED AUX 0x7d",/* 0x07e */ "RESERVED AUX 0x7e",/* 0x07f */ "RESERVED AUX 0x7f", + AUX_UNUSED_16 /* 0x080 - 0x08f */ + AUX_UNUSED_16 /* 0x090 - 0x09f */ + AUX_UNUSED_16 /* 0x0a0 - 0x0af */ + AUX_UNUSED_16 /* 0x0b0 - 0x0bf */ + // build configuration registers 0x0c0 - 0x0ff + /* 0x0c0 */ "RESERVED AUX 0xc0",/* 0x0c1 */ "RESERVED AUX 0xc1",/* 0x0c2 */ "RESERVED AUX 0xc2",/* 0x0c3 */ "RESERVED AUX 0xc3",/* 0x0c4 */ "RESERVED AUX 0xc4",/* 0x0c5 */ "RESERVED AUX 0xc5",/* 0x0c6 */ "RESERVED AUX 0xc6",/* 0x0c7 */ "RESERVED AUX 0xc7",/* 0x0c8 */ "RESERVED AUX 0xc8",/* 0x0c9 */ "RESERVED AUX 0xc9",/* 0x0ca */ "RESERVED AUX 0xca",/* 0x0cb */ "RESERVED AUX 0xcb",/* 0x0cc */ "RESERVED AUX 0xcc",/* 0x0cd */ "RESERVED AUX 0xcd",/* 0x0ce */ "RESERVED AUX 0xce",/* 0x0cf */ "RESERVED AUX 0xcf", + /* 0x0d0 */ "RESERVED AUX 0xd0",/* 0x0d1 */ "RESERVED AUX 0xd1",/* 0x0d2 */ "RESERVED AUX 0xd2",/* 0x0d3 */ "RESERVED AUX 0xd3",/* 0x0d4 */ "RESERVED AUX 0xd4",/* 0x0d5 */ "RESERVED AUX 0xd5",/* 0x0d6 */ "RESERVED AUX 0xd6",/* 0x0d7 */ "RESERVED AUX 0xd7",/* 0x0d8 */ "RESERVED AUX 0xd8",/* 0x0d9 */ "RESERVED AUX 0xd9",/* 0x0da */ "RESERVED AUX 0xda",/* 0x0db */ "RESERVED AUX 0xdb",/* 0x0dc */ "RESERVED AUX 0xdc",/* 0x0dd */ "RESERVED AUX 0xdd",/* 0x0de */ "RESERVED AUX 0xde",/* 0x0df */ "RESERVED AUX 0xdf", + /* 0x0e0 */ "RESERVED AUX 0xe0",/* 0x0e1 */ "RESERVED AUX 0xe1",/* 0x0e2 */ "RESERVED AUX 0xe2",/* 0x0e3 */ "RESERVED AUX 0xe3",/* 0x0e4 */ "RESERVED AUX 0xe4",/* 0x0e5 */ "RESERVED AUX 0xe5",/* 0x0e6 */ "RESERVED AUX 0xe6",/* 0x0e7 */ "RESERVED AUX 0xe7",/* 0x0e8 */ "RESERVED AUX 0xe8",/* 0x0e9 */ "RESERVED AUX 0xe9",/* 0x0ea */ "RESERVED AUX 0xea",/* 0x0eb */ "RESERVED AUX 0xeb",/* 0x0ec */ "RESERVED AUX 0xec",/* 0x0ed */ "RESERVED AUX 0xed",/* 0x0ee */ "RESERVED AUX 0xee",/* 0x0ef */ "RESERVED AUX 0xef", + /* 0x0f0 */ "RESERVED AUX 0xf0",/* 0x0f1 */ "RESERVED AUX 0xf1",/* 0x0f2 */ "RESERVED AUX 0xf2",/* 0x0f3 */ "RESERVED AUX 0xf3",/* 0x0f4 */ "RESERVED AUX 0xf4",/* 0x0f5 */ "RESERVED AUX 0xf5",/* 0x0f6 */ "RESERVED AUX 0xf6",/* 0x0f7 */ "RESERVED AUX 0xf7",/* 0x0f8 */ "RESERVED AUX 0xf8",/* 0x0f9 */ "RESERVED AUX 0xf9",/* 0x0fa */ "RESERVED AUX 0xfa",/* 0x0fb */ "RESERVED AUX 0xfb",/* 0x0fc */ "RESERVED AUX 0xfc",/* 0x0fd */ "RESERVED AUX 0xfd",/* 0x0fe */ "RESERVED AUX 0xfe",/* 0x0ff */ "RESERVED AUX 0xff", + /* 0x100 */ "COUNT1", + /* 0x101 */ "CONTROL1", + /* 0x102 */ "LIMIT1", + /* 0x103 */ UNUSED_REG, + /* 0x104 */ UNUSED_REG, + /* 0x105 */ UNUSED_REG, + /* 0x106 */ UNUSED_REG, + /* 0x107 */ UNUSED_REG, + /* 0x108 */ UNUSED_REG, + /* 0x109 */ UNUSED_REG, + /* 0x10a */ UNUSED_REG, + /* 0x10b */ UNUSED_REG, + /* 0x10c */ UNUSED_REG, + /* 0x10d */ UNUSED_REG, + /* 0x10e */ UNUSED_REG, + /* 0x10f */ UNUSED_REG, + AUX_UNUSED_16 /* 0x110 - 0x11f */ + AUX_UNUSED_16 /* 0x120 - 0x12f */ + AUX_UNUSED_16 /* 0x130 - 0x13f */ + AUX_UNUSED_16 /* 0x140 - 0x14f */ + AUX_UNUSED_16 /* 0x150 - 0x15f */ + AUX_UNUSED_16 /* 0x160 - 0x16f */ + AUX_UNUSED_16 /* 0x170 - 0x17f */ + AUX_UNUSED_16 /* 0x180 - 0x18f */ + AUX_UNUSED_16 /* 0x190 - 0x19f */ + AUX_UNUSED_16 /* 0x1a0 - 0x1af */ + AUX_UNUSED_16 /* 0x1b0 - 0x1bf */ + AUX_UNUSED_16 /* 0x1c0 - 0x1cf */ + AUX_UNUSED_16 /* 0x1d0 - 0x1df */ + AUX_UNUSED_16 /* 0x1e0 - 0x1ef */ + AUX_UNUSED_16 /* 0x1f0 - 0x1ff */ + /* 0x200 */ "AUX_IRQ_LEV", + /* 0x201 */ "AUX_IRQ_HINT", + /* 0x203 */ UNUSED_REG, + /* 0x203 */ UNUSED_REG, + /* 0x204 */ UNUSED_REG, + /* 0x205 */ UNUSED_REG, + /* 0x206 */ UNUSED_REG, + /* 0x207 */ UNUSED_REG, + /* 0x208 */ UNUSED_REG, + /* 0x209 */ UNUSED_REG, + /* 0x20a */ UNUSED_REG, + /* 0x20b */ UNUSED_REG, + /* 0x20c */ UNUSED_REG, + /* 0x20d */ UNUSED_REG, + /* 0x20e */ UNUSED_REG, + /* 0x20f */ UNUSED_REG, + AUX_UNUSED_16 /* 0x210 - 0x21f */ + AUX_UNUSED_16 /* 0x220 - 0x22f */ + AUX_UNUSED_16 /* 0x230 - 0x23f */ + AUX_UNUSED_16 /* 0x240 - 0x24f */ + AUX_UNUSED_16 /* 0x250 - 0x25f */ + AUX_UNUSED_16 /* 0x260 - 0x26f */ + AUX_UNUSED_16 /* 0x270 - 0x27f */ + AUX_UNUSED_16 /* 0x280 - 0x28f */ + AUX_UNUSED_16 /* 0x290 - 0x29f */ + AUX_UNUSED_16 /* 0x2a0 - 0x2af */ + AUX_UNUSED_16 /* 0x2b0 - 0x2bf */ + AUX_UNUSED_16 /* 0x2c0 - 0x2cf */ + AUX_UNUSED_16 /* 0x2d0 - 0x2df */ + AUX_UNUSED_16 /* 0x2e0 - 0x2ef */ + AUX_UNUSED_16 /* 0x2f0 - 0x2ff */ -/*****************************************************************************/ + AUX_UNUSED_16 /* 0x300 - 0x30f */ + AUX_UNUSED_16 /* 0x310 - 0x31f */ + AUX_UNUSED_16 /* 0x320 - 0x32f */ + AUX_UNUSED_16 /* 0x330 - 0x33f */ + AUX_UNUSED_16 /* 0x340 - 0x34f */ + AUX_UNUSED_16 /* 0x350 - 0x35f */ + AUX_UNUSED_16 /* 0x360 - 0x36f */ + AUX_UNUSED_16 /* 0x370 - 0x37f */ + AUX_UNUSED_16 /* 0x380 - 0x38f */ + AUX_UNUSED_16 /* 0x390 - 0x39f */ + AUX_UNUSED_16 /* 0x3a0 - 0x3af */ + AUX_UNUSED_16 /* 0x3b0 - 0x3bf */ + AUX_UNUSED_16 /* 0x3c0 - 0x3cf */ + AUX_UNUSED_16 /* 0x3d0 - 0x3df */ + AUX_UNUSED_16 /* 0x3e0 - 0x3ef */ + AUX_UNUSED_16 /* 0x3f0 - 0x3ff */ + /* 0x400 */ "ERET", + /* 0x401 */ "ERBTA", + /* 0x403 */ "ERSTATUS", + /* 0x403 */ "ECR", + /* 0x404 */ "EFA", + /* 0x405 */ UNUSED_REG, + /* 0x406 */ UNUSED_REG, + /* 0x407 */ UNUSED_REG, + /* 0x408 */ UNUSED_REG, + /* 0x409 */ UNUSED_REG, + /* 0x40a */ "ICAUSE1", + /* 0x40b */ "ICAUSE2", + /* 0x40c */ "AUX_IENABLE", + /* 0x40d */ "AUX_ITRIGGER", + /* 0x40e */ UNUSED_REG, + /* 0x40f */ UNUSED_REG, + /* 0x410 */ "XPU", + /* 0x411 */ UNUSED_REG, + /* 0x412 */ "BTA", + /* 0x413 */ "BTA_L1", + /* 0x414 */ "BTA_L2", + /* 0x415 */ "AUX_IRQ_PULSE_CANCEL", + /* 0x416 */ "AUX_IRQ_PENDING", + /* 0x417 */ UNUSED_REG, + /* 0x418 */ UNUSED_REG, + /* 0x419 */ UNUSED_REG, + /* 0x41a */ UNUSED_REG, + /* 0x41b */ UNUSED_REG, + /* 0x41c */ UNUSED_REG, + /* 0x41d */ UNUSED_REG, + /* 0x41e */ UNUSED_REG, + /* 0x41f */ UNUSED_REG +}; + +//#define EXPLICIT_EXTENSIONS + +const char *const arcompact_disassembler::datasize[0x4] = +{ +#ifdef EXPLICIT_EXTENSIONS + /* 00 */ ".L", // Dword (default) (can use no extension, using .L to be explicit) +#else + /* 00 */ "",// Dword (default) +#endif + /* 01 */ ".B", // Byte + /* 02 */ ".W", // Word + /* 03 */ "." +}; + +const char *const arcompact_disassembler::dataextend[0x2] = +{ +#ifdef EXPLICIT_EXTENSIONS + /* 00 */ ".ZX", // Zero Extend (can use no extension, using .ZX to be explicit) +#else + /* 00 */ "", // Zero Extend +#endif + /* 01 */ ".X" // Sign Extend +}; + +const char *const arcompact_disassembler::addressmode[0x4] = +{ +#ifdef EXPLICIT_EXTENSIONS + /* 00 */ ".AN", // No Writeback (can use no extension, using .AN to be explicit) +#else + /* 00 */ "", // No Writeback +#endif + /* 01 */ ".AW", // Writeback pre memory access + /* 02 */ ".AB", // Writeback post memory access + /* 03 */ ".AS" // scaled +}; + +const char *const arcompact_disassembler::cachebit[0x2] = +{ +#ifdef EXPLICIT_EXTENSIONS + /* 00 */ ".EN", // Data Cache Enabled (can use no extension, using .EN to be explicit) +#else + /* 00 */ "", // Data Cache Enabled +#endif + /* 01 */ ".DI" // Direct to Memory (Cache Bypass) +}; + +const char *const arcompact_disassembler::flagbit[0x2] = +{ +#ifdef EXPLICIT_EXTENSIONS + /* 00 */ ".NF", // Don't Set Flags (can use no extension, using .NF to be explicit) +#else + /* 00 */ "", // Don't Set Flags +#endif + /* 01 */ ".F" // Set Flags +}; + +const char *const arcompact_disassembler::delaybit[0x2] = +{ + /* 00 */ ".ND", // Don't execute opcode in delay slot + /* 01 */ ".D" // Execute Opcode in delay slot +}; + + +const char *const arcompact_disassembler::regnames[0x40] = +{ + /* 00 */ "r0", + /* 01 */ "r1", + /* 02 */ "r2", + /* 03 */ "r3", + /* 04 */ "r4", + /* 05 */ "r5", + /* 06 */ "r6", + /* 07 */ "r7", + /* 08 */ "r8", + /* 09 */ "r9", + /* 0a */ "r10", + /* 0b */ "r11", + /* 0c */ "r12", + /* 0d */ "r13", + /* 0e */ "r14", + /* 0f */ "r15", + + /* 10 */ "r16", + /* 11 */ "r17", + /* 12 */ "r18", + /* 13 */ "r19", + /* 14 */ "r20", + /* 15 */ "r21", + /* 16 */ "r22", + /* 17 */ "r23", + /* 18 */ "r24", + /* 19 */ "r25", + /* 1a */ "r26_GP", + /* 1b */ "r27_FP", + /* 1c */ "r28_SP", + /* 1d */ "r29_ILINK1", + /* 1e */ "r30_ILINK2", + /* 1f */ "r31_BLINK", + + /* 20 */ "r32(ext)", + /* 21 */ "r33(ext)", + /* 22 */ "r34(ext)", + /* 23 */ "r35(ext)", + /* 24 */ "r36(ext)", + /* 25 */ "r37(ext)", + /* 26 */ "r38(ext)", + /* 27 */ "r39(ext)", + /* 28 */ "r40(ext)", + /* 29 */ "r41(ext)", + /* 2a */ "r42(ext)", + /* 2b */ "r43(ext)", + /* 2c */ "r44(ext)", + /* 2d */ "r45(ext)", + /* 2e */ "r46(ext)", + /* 2f */ "r47(ext)", + + /* 30 */ "r48(ext)", + /* 31 */ "r49(ext)", + /* 32 */ "r50(ext)", + /* 33 */ "r51(ext)", + /* 34 */ "r52(ext)", + /* 35 */ "r53(ext)", + /* 36 */ "r54(ext)", + /* 37 */ "r55(ext)", + /* 38 */ "r56(ext)", + /* 39 */ "r57(M-LO)", // MLO (result registers for optional multply functions) + /* 3a */ "r58(M-MID)", // MMID + /* 3b */ "r59(M-HI)", // MHI + /* 3c */ "r60(LP_COUNT)", + /* 3d */ "r61(reserved)", + /* 3e */ "r62(LIMM)", // use Long Immediate Data instead of register + /* 3f */ "r63(PCL)" +}; + +#if 0 +const char *const arcompact_disassembler::opcodes_temp[0x40] = +{ + /* 00 */ "0x00", + /* 01 */ "0x01", + /* 02 */ "0x02", + /* 03 */ "0x03", + /* 04 */ "0x04", + /* 05 */ "0x05", + /* 06 */ "0x06", + /* 07 */ "0x07", + /* 08 */ "0x08", + /* 09 */ "0x09", + /* 0a */ "0x0a", + /* 0b */ "0x0b", + /* 0c */ "0x0c", + /* 0d */ "0x0d", + /* 0e */ "0x0e", + /* 0f */ "0x0f", + + /* 10 */ "0x10", + /* 11 */ "0x11", + /* 12 */ "0x12", + /* 13 */ "0x13", + /* 14 */ "0x14", + /* 15 */ "0x15", + /* 16 */ "0x16", + /* 17 */ "0x17", + /* 18 */ "0x18", + /* 19 */ "0x19", + /* 1a */ "0x1a", + /* 1b */ "0x1b", + /* 1c */ "0x1c", + /* 1d */ "0x1d", + /* 1e */ "0x1e", + /* 1f */ "0x1f", + + /* 20 */ "0x20", + /* 21 */ "0x21", + /* 22 */ "0x22", + /* 23 */ "0x23", + /* 24 */ "0x24", + /* 25 */ "0x25", + /* 26 */ "0x26", + /* 27 */ "0x27", + /* 28 */ "0x28", + /* 29 */ "0x29", + /* 2a */ "0x2a", + /* 2b */ "0x2b", + /* 2c */ "0x2c", + /* 2d */ "0x2d", + /* 2e */ "0x2e", + /* 2f */ "0x2f", + + /* 30 */ "0x30", + /* 31 */ "0x31", + /* 32 */ "0x32", + /* 33 */ "0x33", + /* 34 */ "0x34", + /* 35 */ "0x35", + /* 36 */ "0x36", + /* 37 */ "0x37", + /* 38 */ "0x38", + /* 39 */ "0x39", + /* 3a */ "0x3a", + /* 3b */ "0x3b", + /* 3c */ "0x3c", + /* 3d */ "0x3d", + /* 3e */ "0x3e", + /* 3f */ "0x3f", +}; +#endif + + +const char *const arcompact_disassembler::opcodes_04[0x40] = +{ + /* 00 */ "ADD", + /* 01 */ "ADC", + /* 02 */ "SUB", + /* 03 */ "SBC", + /* 04 */ "AND", + /* 05 */ "OR", + /* 06 */ "BIC", + /* 07 */ "XOR", + /* 08 */ "MAX", + /* 09 */ "MIN", + /* 0a */ "MOV", + /* 0b */ "TST", + /* 0c */ "CMP", + /* 0d */ "RCMP", + /* 0e */ "RSUB", + /* 0f */ "BSET", -/*****************************************************************************/ + /* 10 */ "BCLR", + /* 11 */ "BTST", + /* 12 */ "BXOR", + /* 13 */ "BSMK", + /* 14 */ "ADD1", + /* 15 */ "ADD2", + /* 16 */ "ADD3", + /* 17 */ "SUB1", + /* 18 */ "SUB2", + /* 19 */ "SUB3", + /* 1a */ "MPY", + /* 1b */ "MPYH", + /* 1c */ "MPYHU", + /* 1d */ "MPYU", + /* 1e */ "0x1e", + /* 1f */ "0x1f", + /* 20 */ "Jcc", + /* 21 */ "Jcc.D", + /* 22 */ "JLcc", + /* 23 */ "JLcc.D", + /* 24 */ "0x24", + /* 25 */ "0x25", + /* 26 */ "0x26", + /* 27 */ "0x27", + /* 28 */ "LPcc", + /* 29 */ "FLAG", + /* 2a */ "LR", + /* 2b */ "SR", + /* 2c */ "0x2c", + /* 2d */ "0x2d", + /* 2e */ "0x2e", + /* 2f */ "SOP table", -#define ARCOMPACT_OPERATION ((op & 0xf800) >> 11) + /* 30 */ "LD", + /* 31 */ "LD", + /* 32 */ "LD", + /* 33 */ "LD", + /* 34 */ "LD", + /* 35 */ "LD", + /* 36 */ "LD", + /* 37 */ "LD", + /* 38 */ "0x38", + /* 39 */ "0x39", + /* 3a */ "0x3a", + /* 3b */ "0x3b", + /* 3c */ "0x3c", + /* 3d */ "0x3d", + /* 3e */ "0x3e", + /* 3f */ "0x3f", +}; -CPU_DISASSEMBLE(arcompact) +offs_t arcompact_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { int size; - uint32_t op = oprom[0] | (oprom[1] << 8); + uint32_t op = opcodes.r16(pc); - uint8_t instruction = ARCOMPACT_OPERATION; + uint8_t instruction = ((op & 0xf800) >> 11); if (instruction < 0x0c) { size = 4; op <<= 16; - op |= oprom[2] | (oprom[3] << 8); + op |= opcodes.r16(pc+2); op &= ~0xf8000000; switch (instruction) // 32-bit instructions (with optional extra dword for immediate data) { - case 0x00: size = arcompact_handle00_dasm(DASM_PARAMS); break; // Bcc - case 0x01: size = arcompact_handle01_dasm(DASM_PARAMS); break; // BLcc/BRcc - case 0x02: size = arcompact_handle02_dasm(DASM_PARAMS); break; // LD r+o - case 0x03: size = arcompact_handle03_dasm(DASM_PARAMS); break; // ST r+o - case 0x04: size = arcompact_handle04_dasm(DASM_PARAMS); break; // op a,b,c (basecase) - case 0x05: size = arcompact_handle05_dasm(DASM_PARAMS); break; // op a,b,c (05 ARC ext) - case 0x06: size = arcompact_handle06_dasm(DASM_PARAMS); break; // op a,b,c (06 ARC ext) - case 0x07: size = arcompact_handle07_dasm(DASM_PARAMS); break; // op a,b,c (07 User ext) - case 0x08: size = arcompact_handle08_dasm(DASM_PARAMS); break; // op a,b,c (08 User ext) - case 0x09: size = arcompact_handle09_dasm(DASM_PARAMS); break; // op a,b,c (09 Market ext) - case 0x0a: size = arcompact_handle0a_dasm(DASM_PARAMS); break; // op a,b,c (0a Market ext) - case 0x0b: size = arcompact_handle0b_dasm(DASM_PARAMS); break; // op a,b,c (0b Market ext) + case 0x00: size = handle00_dasm(stream, pc, op, opcodes); break; // Bcc + case 0x01: size = handle01_dasm(stream, pc, op, opcodes); break; // BLcc/BRcc + case 0x02: size = handle02_dasm(stream, pc, op, opcodes); break; // LD r+o + case 0x03: size = handle03_dasm(stream, pc, op, opcodes); break; // ST r+o + case 0x04: size = handle04_dasm(stream, pc, op, opcodes); break; // op a,b,c (basecase) + case 0x05: size = handle05_dasm(stream, pc, op, opcodes); break; // op a,b,c (05 ARC ext) + case 0x06: size = handle06_dasm(stream, pc, op, opcodes); break; // op a,b,c (06 ARC ext) + case 0x07: size = handle07_dasm(stream, pc, op, opcodes); break; // op a,b,c (07 User ext) + case 0x08: size = handle08_dasm(stream, pc, op, opcodes); break; // op a,b,c (08 User ext) + case 0x09: size = handle09_dasm(stream, pc, op, opcodes); break; // op a,b,c (09 Market ext) + case 0x0a: size = handle0a_dasm(stream, pc, op, opcodes); break; // op a,b,c (0a Market ext) + case 0x0b: size = handle0b_dasm(stream, pc, op, opcodes); break; // op a,b,c (0b Market ext) } } else @@ -62,28 +575,28 @@ CPU_DISASSEMBLE(arcompact) switch (instruction) // 16-bit instructions { - case 0x0c: size = arcompact_handle0c_dasm(DASM_PARAMS); break; // Load/Add reg-reg - case 0x0d: size = arcompact_handle0d_dasm(DASM_PARAMS); break; // Add/Sub/Shft imm - case 0x0e: size = arcompact_handle0e_dasm(DASM_PARAMS); break; // Mov/Cmp/Add - case 0x0f: size = arcompact_handle0f_dasm(DASM_PARAMS); break; // op_S b,b,c (single 16-bit ops) - case 0x10: size = arcompact_handle10_dasm(DASM_PARAMS); break; // LD_S - case 0x11: size = arcompact_handle11_dasm(DASM_PARAMS); break; // LDB_S - case 0x12: size = arcompact_handle12_dasm(DASM_PARAMS); break; // LDW_S - case 0x13: size = arcompact_handle13_dasm(DASM_PARAMS); break; // LSW_S.X - case 0x14: size = arcompact_handle14_dasm(DASM_PARAMS); break; // ST_S - case 0x15: size = arcompact_handle15_dasm(DASM_PARAMS); break; // STB_S - case 0x16: size = arcompact_handle16_dasm(DASM_PARAMS); break; // STW_S - case 0x17: size = arcompact_handle17_dasm(DASM_PARAMS); break; // Shift/Sub/Bit - case 0x18: size = arcompact_handle18_dasm(DASM_PARAMS); break; // Stack Instr - case 0x19: size = arcompact_handle19_dasm(DASM_PARAMS); break; // GP Instr - case 0x1a: size = arcompact_handle1a_dasm(DASM_PARAMS); break; // PCL Instr - case 0x1b: size = arcompact_handle1b_dasm(DASM_PARAMS); break; // MOV_S - case 0x1c: size = arcompact_handle1c_dasm(DASM_PARAMS); break; // ADD_S/CMP_S - case 0x1d: size = arcompact_handle1d_dasm(DASM_PARAMS); break; // BRcc_S - case 0x1e: size = arcompact_handle1e_dasm(DASM_PARAMS); break; // Bcc_S - case 0x1f: size = arcompact_handle1f_dasm(DASM_PARAMS); break; // BL_S + case 0x0c: size = handle0c_dasm(stream, pc, op, opcodes); break; // Load/Add reg-reg + case 0x0d: size = handle0d_dasm(stream, pc, op, opcodes); break; // Add/Sub/Shft imm + case 0x0e: size = handle0e_dasm(stream, pc, op, opcodes); break; // Mov/Cmp/Add + case 0x0f: size = handle0f_dasm(stream, pc, op, opcodes); break; // op_S b,b,c (single 16-bit ops) + case 0x10: size = handle10_dasm(stream, pc, op, opcodes); break; // LD_S + case 0x11: size = handle11_dasm(stream, pc, op, opcodes); break; // LDB_S + case 0x12: size = handle12_dasm(stream, pc, op, opcodes); break; // LDW_S + case 0x13: size = handle13_dasm(stream, pc, op, opcodes); break; // LSW_S.X + case 0x14: size = handle14_dasm(stream, pc, op, opcodes); break; // ST_S + case 0x15: size = handle15_dasm(stream, pc, op, opcodes); break; // STB_S + case 0x16: size = handle16_dasm(stream, pc, op, opcodes); break; // STW_S + case 0x17: size = handle17_dasm(stream, pc, op, opcodes); break; // Shift/Sub/Bit + case 0x18: size = handle18_dasm(stream, pc, op, opcodes); break; // Stack Instr + case 0x19: size = handle19_dasm(stream, pc, op, opcodes); break; // GP Instr + case 0x1a: size = handle1a_dasm(stream, pc, op, opcodes); break; // PCL Instr + case 0x1b: size = handle1b_dasm(stream, pc, op, opcodes); break; // MOV_S + case 0x1c: size = handle1c_dasm(stream, pc, op, opcodes); break; // ADD_S/CMP_S + case 0x1d: size = handle1d_dasm(stream, pc, op, opcodes); break; // BRcc_S + case 0x1e: size = handle1e_dasm(stream, pc, op, opcodes); break; // Bcc_S + case 0x1f: size = handle1f_dasm(stream, pc, op, opcodes); break; // BL_S } } - return size | DASMFLAG_SUPPORTED; + return size | SUPPORTED; } diff --git a/src/devices/cpu/arcompact/arcompactdasm.h b/src/devices/cpu/arcompact/arcompactdasm.h new file mode 100644 index 00000000000..7594c673a0d --- /dev/null +++ b/src/devices/cpu/arcompact/arcompactdasm.h @@ -0,0 +1,721 @@ +// license:BSD-3-Clause +// copyright-holders:David Haywood +/*********************************\ + + ARCompact disassembler + +\*********************************/ + + +#ifndef MAME_CPU_ARCOMPACT_ARCOMPACTDASM_H +#define MAME_CPU_ARCOMPACT_ARCOMPACTDASM_H + +#pragma once + +class arcompact_disassembler : public util::disasm_interface +{ +public: + arcompact_disassembler() = default; + virtual ~arcompact_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + + static const char *const conditions[0x20]; + static const char *const auxregnames[0x420]; + static const char *const datasize[0x4]; + static const char *const dataextend[0x2]; + static const char *const addressmode[0x4]; + static const char *const cachebit[0x2]; + static const char *const flagbit[0x2]; + static const char *const delaybit[0x2]; + static const char *const regnames[0x40]; + static const char *const opcodes_04[0x40]; + +private: + int handle01_01_00_helper(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext); + int handle01_01_01_helper(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext); + + int handle04_p00_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext, int ignore_dst, int b_reserved); + int handle04_p01_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext, int ignore_dst, int b_reserved); + int handle04_p10_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext, int b_reserved); + int handle04_p11_m0_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext, int b_reserved); + int handle04_p11_m1_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext, int b_reserved); + int handle04_p11_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext, int b_reserved); + int handle04_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext, int ignore_dst, int b_reserved); + int handle04_2f_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext); + int handle04_3x_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, int dsize, int extend); + int handle05_2f_0x_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext); + int handle0c_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext, int format); + int handle0d_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext); + int handle0e_0x_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext, int revop); + int handle0f_00_0x_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext); + int handle0f_0x_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext, int nodst); + int handle_ld_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext, int shift, int swap); + int handle_l7_0x_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext); + int handle18_0x_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext, int st, int format); + int handle19_0x_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext, int shift, int format); + int handle1d_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext); + int handle1e_0x_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext); + int handle1e_03_0x_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext); + + int handle00_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle00_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_00_00dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_00_01dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_00_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_00_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_00_02_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_00_03_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_00_04_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_00_05_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_00_0e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_00_0f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_01_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_01_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_01_02_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_01_03_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_01_04_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_01_05_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_01_0e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_01_0f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle02_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle03_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_02_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_03_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_04_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_05_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_06_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_07_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_08_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_09_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_0a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_0b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_0c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_0d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_0e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_0f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_10_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_11_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_12_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_13_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_14_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_15_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_16_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_17_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_18_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_19_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_1a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_1b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_1c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_1d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_20_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_21_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_22_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_23_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_28_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_29_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_02_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_03_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_04_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_05_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_06_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_07_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_08_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_09_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_0a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_0b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_0c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_02_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_03_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_04_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_05_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_30_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_31_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_32_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_33_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_34_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_35_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_36_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_37_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_02_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_03_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_04_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_05_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_06_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_07_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_08_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_0a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_0b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_28_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_29_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + + int handle06_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle07_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle08_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle09_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle0a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle0b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + + int handle0c_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0c_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0c_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0c_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0d_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0d_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0d_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0d_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0e_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0e_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0e_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0e_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_00_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_00_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_00_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_00_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_00_06_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_00_07_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_00_07_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_00_07_04_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_00_07_05_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_00_07_06_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_00_07_07_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_04_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_05_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_06_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_07_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_0b_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_0c_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_0d_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_0e_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_0f_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_10_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_11_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_12_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_13_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_14_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_15_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_16_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_18_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_19_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_1a_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_1b_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_1c_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_1d_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_1e_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_1f_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle10_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle11_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle12_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle13_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle14_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle15_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle16_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle17_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle17_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle17_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle17_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle17_04_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle17_05_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle17_06_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle17_07_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_04_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_05_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_05_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_11_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_11_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle19_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle19_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle19_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle19_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1a_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1b_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1c_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1c_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1d_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1d_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1e_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1e_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1e_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1e_03_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1e_03_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1e_03_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1e_03_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1e_03_04_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1e_03_05_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1e_03_06_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1e_03_07_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1f_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + + /************************************************************************************************************************************ + * * + * illegal opcode handlers (disassembly) * + * * + ************************************************************************************************************************************/ + + int handle01_01_00_06_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_00_07_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_00_08_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_00_09_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_00_0a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_00_0b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_00_0c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_00_0d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + + int handle01_01_01_06_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_01_07_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_01_08_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_01_09_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_01_0a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_01_0b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_01_0c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_01_0d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + + + int handle04_1e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_1f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + + int handle04_24_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_25_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_26_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_27_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + + int handle04_2c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + + int handle04_2f_0d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_0e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_0f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_10_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_11_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_12_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_13_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_14_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_15_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_16_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_17_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_18_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_19_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_1a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_1b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_1c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_1d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_1e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_1f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_20_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_21_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_22_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_23_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_24_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_25_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_26_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_27_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_28_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_29_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_2a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_2b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_2c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_2d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_2e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_2f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_30_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_31_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_32_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_33_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_34_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_35_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_36_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_37_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_38_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_39_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + + int handle04_2f_3f_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_06_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_07_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_08_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_09_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_0a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_0b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_0c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_0d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_0e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_0f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_10_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_11_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_12_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_13_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_14_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_15_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_16_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_17_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_18_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_19_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_1a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_1b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_1c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_1d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_1e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_1f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_20_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_21_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_22_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_23_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_24_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_25_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_26_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_27_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_28_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_29_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_2a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_2b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_2c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_2d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_2e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_2f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_30_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_31_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_32_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_33_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_34_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_35_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_36_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_37_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_38_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_39_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_3a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_3b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_3c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_3d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_3e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_3f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + + int handle05_2f_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_02_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_03_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_04_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_05_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_06_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_07_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_08_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_09_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_0a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_0b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_0c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_0d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_0e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_0f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_10_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_11_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_12_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_13_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_14_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_15_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_16_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_17_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_18_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_19_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_1a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_1b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_1c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_1d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_1e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_1f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_20_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_21_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_22_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_23_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_24_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_25_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_26_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_27_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_28_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_29_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_2a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_2b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_2c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_2d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_2e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_2f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_30_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_31_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_32_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_33_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_34_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_35_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_36_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_37_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_38_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_39_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + + int handle05_2f_3f_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_02_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_03_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_04_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_05_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_06_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_07_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_08_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_09_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_0a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_0b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_0c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_0d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_0e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_0f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_10_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_11_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_12_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_13_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_14_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_15_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_16_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_17_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_18_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_19_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_1a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_1b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_1c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_1d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_1e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_1f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_20_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_21_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_22_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_23_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_24_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_25_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_26_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_27_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_28_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_29_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_2a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_2b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_2c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_2d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_2e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_2f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_30_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_31_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_32_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_33_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_34_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_35_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_36_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_37_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_38_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_39_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_3a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_3b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_3c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_3d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_3e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_3f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + + + int handle04_38_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_39_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_3a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_3b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_3c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_3d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_3e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_3f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + + int handle05_09_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_0c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_0d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_0e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_0f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_10_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_11_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_12_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_13_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_14_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_15_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_16_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_17_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_18_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_19_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_1a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_1b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_1c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_1d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_1e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_1f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_20_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_21_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_22_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_23_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_24_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_25_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_26_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_27_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + + int handle05_2a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + + int handle05_30_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_31_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_32_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_33_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_34_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_35_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_36_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_37_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_38_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_39_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_3a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_3b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_3c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_3d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_3e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_3f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + + int handle0f_00_04_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_00_05_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_00_07_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_00_07_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_08_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_09_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_0a_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_17_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + + int handle18_05_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_05_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_05_04_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_05_05_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_05_06_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_05_07_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_04_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_05_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_06_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_07_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_08_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_09_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_0a_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_0b_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_0c_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_0d_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_0e_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_0f_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_10_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_12_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_13_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_14_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_15_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_16_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_17_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_18_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_19_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_1a_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_1b_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_1c_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_1d_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_1e_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_1f_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_04_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_05_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_06_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_07_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_08_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_09_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_0a_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_0b_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_0c_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_0d_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_0e_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_0f_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_10_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_12_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_13_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_14_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_15_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_16_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_17_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_18_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_19_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_1a_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_1b_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_1c_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_1d_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_1e_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_1f_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + + + + + int handle00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle01_01_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle04_2f_3f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + + int handle05_2f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + int handle05_2f_3f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes); + + + int handle0c_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0d_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0e_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle0f_00_07_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle17_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_05_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_06_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle18_07_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle19_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1c_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1d_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1e_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + int handle1e_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes); + +}; + +#endif diff --git a/src/devices/cpu/arcompact/arcompactdasm_dispatch.cpp b/src/devices/cpu/arcompact/arcompactdasm_dispatch.cpp index 769a8604fc8..f9b296baf34 100644 --- a/src/devices/cpu/arcompact/arcompactdasm_dispatch.cpp +++ b/src/devices/cpu/arcompact/arcompactdasm_dispatch.cpp @@ -7,12 +7,9 @@ \*********************************/ #include "emu.h" -#include +#include "arcompactdasm.h" -#include "arcompactdasm_dispatch.h" -#include "arcompactdasm_ops.h" - -int arcompact_handle00_dasm(DASM_OPS_32) +int arcompact_disassembler::handle00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { int size = 4; uint8_t subinstr = (op & 0x00010000) >> 16; @@ -20,14 +17,14 @@ int arcompact_handle00_dasm(DASM_OPS_32) switch (subinstr) { - case 0x00: size = arcompact_handle00_00_dasm(DASM_PARAMS); break; // Branch Conditionally - case 0x01: size = arcompact_handle00_01_dasm(DASM_PARAMS); break; // Branch Unconditionally Far + case 0x00:size = handle00_00_dasm(stream, pc, op, opcodes); break; // Branch Conditionally + case 0x01:size = handle00_01_dasm(stream, pc, op, opcodes); break; // Branch Unconditionally Far } return size; } -int arcompact_handle01_dasm(DASM_OPS_32) +int arcompact_disassembler::handle01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { int size = 4; uint8_t subinstr = (op & 0x00010000) >> 16; @@ -35,14 +32,14 @@ int arcompact_handle01_dasm(DASM_OPS_32) switch (subinstr) { - case 0x00: size = arcompact_handle01_00_dasm(DASM_PARAMS); break; // Branh & Link - case 0x01: size = arcompact_handle01_01_dasm(DASM_PARAMS); break; // Branch on Compare + case 0x00:size = handle01_00_dasm(stream, pc, op, opcodes); break; // Branh & Link + case 0x01:size = handle01_01_dasm(stream, pc, op, opcodes); break; // Branch on Compare } return size; } -int arcompact_handle01_00_dasm(DASM_OPS_32) +int arcompact_disassembler::handle01_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { int size = 4; uint8_t subinstr2 = (op & 0x00020000) >> 17; @@ -50,14 +47,14 @@ int arcompact_handle01_00_dasm(DASM_OPS_32) switch (subinstr2) { - case 0x00: size = arcompact_handle01_00_00dasm(DASM_PARAMS); break; // Branch and Link Conditionally - case 0x01: size = arcompact_handle01_00_01dasm(DASM_PARAMS); break; // Branch and Link Unconditional Far + case 0x00:size = handle01_00_00dasm(stream, pc, op, opcodes); break; // Branch and Link Conditionally + case 0x01:size = handle01_00_01dasm(stream, pc, op, opcodes); break; // Branch and Link Unconditional Far } return size; } -int arcompact_handle01_01_dasm(DASM_OPS_32) +int arcompact_disassembler::handle01_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { int size = 4; @@ -66,14 +63,14 @@ int arcompact_handle01_01_dasm(DASM_OPS_32) switch (subinstr2) { - case 0x00: size = arcompact_handle01_01_00_dasm(DASM_PARAMS); break; // Branch on Compare Register-Register - case 0x01: size = arcompact_handle01_01_01_dasm(DASM_PARAMS); break; // Branch on Compare/Bit Test Register-Immediate + case 0x00:size = handle01_01_00_dasm(stream, pc, op, opcodes); break; // Branch on Compare Register-Register + case 0x01:size = handle01_01_01_dasm(stream, pc, op, opcodes); break; // Branch on Compare/Bit Test Register-Immediate } return size; } -int arcompact_handle01_01_00_dasm(DASM_OPS_32) +int arcompact_disassembler::handle01_01_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { int size = 4; uint8_t subinstr3 = (op & 0x0000000f) >> 0; @@ -81,28 +78,28 @@ int arcompact_handle01_01_00_dasm(DASM_OPS_32) switch (subinstr3) { - case 0x00: size = arcompact_handle01_01_00_00_dasm(DASM_PARAMS); break; // BREQ (reg-reg) - case 0x01: size = arcompact_handle01_01_00_01_dasm(DASM_PARAMS); break; // BRNE (reg-reg) - case 0x02: size = arcompact_handle01_01_00_02_dasm(DASM_PARAMS); break; // BRLT (reg-reg) - case 0x03: size = arcompact_handle01_01_00_03_dasm(DASM_PARAMS); break; // BRGE (reg-reg) - case 0x04: size = arcompact_handle01_01_00_04_dasm(DASM_PARAMS); break; // BRLO (reg-reg) - case 0x05: size = arcompact_handle01_01_00_05_dasm(DASM_PARAMS); break; // BRHS (reg-reg) - case 0x06: size = arcompact_handle01_01_00_06_dasm(DASM_PARAMS); break; // reserved - case 0x07: size = arcompact_handle01_01_00_07_dasm(DASM_PARAMS); break; // reserved - case 0x08: size = arcompact_handle01_01_00_08_dasm(DASM_PARAMS); break; // reserved - case 0x09: size = arcompact_handle01_01_00_09_dasm(DASM_PARAMS); break; // reserved - case 0x0a: size = arcompact_handle01_01_00_0a_dasm(DASM_PARAMS); break; // reserved - case 0x0b: size = arcompact_handle01_01_00_0b_dasm(DASM_PARAMS); break; // reserved - case 0x0c: size = arcompact_handle01_01_00_0c_dasm(DASM_PARAMS); break; // reserved - case 0x0d: size = arcompact_handle01_01_00_0d_dasm(DASM_PARAMS); break; // reserved - case 0x0e: size = arcompact_handle01_01_00_0e_dasm(DASM_PARAMS); break; // BBIT0 (reg-reg) - case 0x0f: size = arcompact_handle01_01_00_0f_dasm(DASM_PARAMS); break; // BBIT1 (reg-reg) + case 0x00:size = handle01_01_00_00_dasm(stream, pc, op, opcodes); break; // BREQ (reg-reg) + case 0x01:size = handle01_01_00_01_dasm(stream, pc, op, opcodes); break; // BRNE (reg-reg) + case 0x02:size = handle01_01_00_02_dasm(stream, pc, op, opcodes); break; // BRLT (reg-reg) + case 0x03:size = handle01_01_00_03_dasm(stream, pc, op, opcodes); break; // BRGE (reg-reg) + case 0x04:size = handle01_01_00_04_dasm(stream, pc, op, opcodes); break; // BRLO (reg-reg) + case 0x05:size = handle01_01_00_05_dasm(stream, pc, op, opcodes); break; // BRHS (reg-reg) + case 0x06:size = handle01_01_00_06_dasm(stream, pc, op, opcodes); break; // reserved + case 0x07:size = handle01_01_00_07_dasm(stream, pc, op, opcodes); break; // reserved + case 0x08:size = handle01_01_00_08_dasm(stream, pc, op, opcodes); break; // reserved + case 0x09:size = handle01_01_00_09_dasm(stream, pc, op, opcodes); break; // reserved + case 0x0a:size = handle01_01_00_0a_dasm(stream, pc, op, opcodes); break; // reserved + case 0x0b:size = handle01_01_00_0b_dasm(stream, pc, op, opcodes); break; // reserved + case 0x0c:size = handle01_01_00_0c_dasm(stream, pc, op, opcodes); break; // reserved + case 0x0d:size = handle01_01_00_0d_dasm(stream, pc, op, opcodes); break; // reserved + case 0x0e:size = handle01_01_00_0e_dasm(stream, pc, op, opcodes); break; // BBIT0 (reg-reg) + case 0x0f:size = handle01_01_00_0f_dasm(stream, pc, op, opcodes); break; // BBIT1 (reg-reg) } return size; } -int arcompact_handle01_01_01_dasm(DASM_OPS_32) // Branch on Compare/Bit Test Register-Immediate +int arcompact_disassembler::handle01_01_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) // Branch on Compare/Bit Test Register-Immediate { int size = 4; uint8_t subinstr3 = (op & 0x0000000f) >> 0; @@ -110,28 +107,28 @@ int arcompact_handle01_01_01_dasm(DASM_OPS_32) // Branch on Compare/Bit Test Re switch (subinstr3) { - case 0x00: size = arcompact_handle01_01_01_00_dasm(DASM_PARAMS); break; // BREQ (reg-imm) - case 0x01: size = arcompact_handle01_01_01_01_dasm(DASM_PARAMS); break; // BRNE (reg-imm) - case 0x02: size = arcompact_handle01_01_01_02_dasm(DASM_PARAMS); break; // BRLT (reg-imm) - case 0x03: size = arcompact_handle01_01_01_03_dasm(DASM_PARAMS); break; // BRGE (reg-imm) - case 0x04: size = arcompact_handle01_01_01_04_dasm(DASM_PARAMS); break; // BRLO (reg-imm) - case 0x05: size = arcompact_handle01_01_01_05_dasm(DASM_PARAMS); break; // BRHS (reg-imm) - case 0x06: size = arcompact_handle01_01_01_06_dasm(DASM_PARAMS); break; // reserved - case 0x07: size = arcompact_handle01_01_01_07_dasm(DASM_PARAMS); break; // reserved - case 0x08: size = arcompact_handle01_01_01_08_dasm(DASM_PARAMS); break; // reserved - case 0x09: size = arcompact_handle01_01_01_09_dasm(DASM_PARAMS); break; // reserved - case 0x0a: size = arcompact_handle01_01_01_0a_dasm(DASM_PARAMS); break; // reserved - case 0x0b: size = arcompact_handle01_01_01_0b_dasm(DASM_PARAMS); break; // reserved - case 0x0c: size = arcompact_handle01_01_01_0c_dasm(DASM_PARAMS); break; // reserved - case 0x0d: size = arcompact_handle01_01_01_0d_dasm(DASM_PARAMS); break; // reserved - case 0x0e: size = arcompact_handle01_01_01_0e_dasm(DASM_PARAMS); break; // BBIT0 (reg-imm) - case 0x0f: size = arcompact_handle01_01_01_0f_dasm(DASM_PARAMS); break; // BBIT1 (reg-imm) + case 0x00:size = handle01_01_01_00_dasm(stream, pc, op, opcodes); break; // BREQ (reg-imm) + case 0x01:size = handle01_01_01_01_dasm(stream, pc, op, opcodes); break; // BRNE (reg-imm) + case 0x02:size = handle01_01_01_02_dasm(stream, pc, op, opcodes); break; // BRLT (reg-imm) + case 0x03:size = handle01_01_01_03_dasm(stream, pc, op, opcodes); break; // BRGE (reg-imm) + case 0x04:size = handle01_01_01_04_dasm(stream, pc, op, opcodes); break; // BRLO (reg-imm) + case 0x05:size = handle01_01_01_05_dasm(stream, pc, op, opcodes); break; // BRHS (reg-imm) + case 0x06:size = handle01_01_01_06_dasm(stream, pc, op, opcodes); break; // reserved + case 0x07:size = handle01_01_01_07_dasm(stream, pc, op, opcodes); break; // reserved + case 0x08:size = handle01_01_01_08_dasm(stream, pc, op, opcodes); break; // reserved + case 0x09:size = handle01_01_01_09_dasm(stream, pc, op, opcodes); break; // reserved + case 0x0a:size = handle01_01_01_0a_dasm(stream, pc, op, opcodes); break; // reserved + case 0x0b:size = handle01_01_01_0b_dasm(stream, pc, op, opcodes); break; // reserved + case 0x0c:size = handle01_01_01_0c_dasm(stream, pc, op, opcodes); break; // reserved + case 0x0d:size = handle01_01_01_0d_dasm(stream, pc, op, opcodes); break; // reserved + case 0x0e:size = handle01_01_01_0e_dasm(stream, pc, op, opcodes); break; // BBIT0 (reg-imm) + case 0x0f:size = handle01_01_01_0f_dasm(stream, pc, op, opcodes); break; // BBIT1 (reg-imm) } return size; } -int arcompact_handle04_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { int size = 4; // General Operations @@ -151,76 +148,76 @@ int arcompact_handle04_dasm(DASM_OPS_32) switch (subinstr) { - case 0x00: size = arcompact_handle04_00_dasm(DASM_PARAMS); break; // ADD - case 0x01: size = arcompact_handle04_01_dasm(DASM_PARAMS); break; // ADC - case 0x02: size = arcompact_handle04_02_dasm(DASM_PARAMS); break; // SUB - case 0x03: size = arcompact_handle04_03_dasm(DASM_PARAMS); break; // SBC - case 0x04: size = arcompact_handle04_04_dasm(DASM_PARAMS); break; // AND - case 0x05: size = arcompact_handle04_05_dasm(DASM_PARAMS); break; // OR - case 0x06: size = arcompact_handle04_06_dasm(DASM_PARAMS); break; // BIC - case 0x07: size = arcompact_handle04_07_dasm(DASM_PARAMS); break; // XOR - case 0x08: size = arcompact_handle04_08_dasm(DASM_PARAMS); break; // MAX - case 0x09: size = arcompact_handle04_09_dasm(DASM_PARAMS); break; // MIN - case 0x0a: size = arcompact_handle04_0a_dasm(DASM_PARAMS); break; // MOV - case 0x0b: size = arcompact_handle04_0b_dasm(DASM_PARAMS); break; // TST - case 0x0c: size = arcompact_handle04_0c_dasm(DASM_PARAMS); break; // CMP - case 0x0d: size = arcompact_handle04_0d_dasm(DASM_PARAMS); break; // RCMP - case 0x0e: size = arcompact_handle04_0e_dasm(DASM_PARAMS); break; // RSUB - case 0x0f: size = arcompact_handle04_0f_dasm(DASM_PARAMS); break; // BSET - case 0x10: size = arcompact_handle04_10_dasm(DASM_PARAMS); break; // BCLR - case 0x11: size = arcompact_handle04_11_dasm(DASM_PARAMS); break; // BTST - case 0x12: size = arcompact_handle04_12_dasm(DASM_PARAMS); break; // BXOR - case 0x13: size = arcompact_handle04_13_dasm(DASM_PARAMS); break; // BMSK - case 0x14: size = arcompact_handle04_14_dasm(DASM_PARAMS); break; // ADD1 - case 0x15: size = arcompact_handle04_15_dasm(DASM_PARAMS); break; // ADD2 - case 0x16: size = arcompact_handle04_16_dasm(DASM_PARAMS); break; // ADD3 - case 0x17: size = arcompact_handle04_17_dasm(DASM_PARAMS); break; // SUB1 - case 0x18: size = arcompact_handle04_18_dasm(DASM_PARAMS); break; // SUB2 - case 0x19: size = arcompact_handle04_19_dasm(DASM_PARAMS); break; // SUB3 - case 0x1a: size = arcompact_handle04_1a_dasm(DASM_PARAMS); break; // MPY * - case 0x1b: size = arcompact_handle04_1b_dasm(DASM_PARAMS); break; // MPYH * - case 0x1c: size = arcompact_handle04_1c_dasm(DASM_PARAMS); break; // MPYHU * - case 0x1d: size = arcompact_handle04_1d_dasm(DASM_PARAMS); break; // MPYU * - case 0x1e: size = arcompact_handle04_1e_dasm(DASM_PARAMS); break; // illegal - case 0x1f: size = arcompact_handle04_1f_dasm(DASM_PARAMS); break; // illegal - case 0x20: size = arcompact_handle04_20_dasm(DASM_PARAMS); break; // Jcc - case 0x21: size = arcompact_handle04_21_dasm(DASM_PARAMS); break; // Jcc.D - case 0x22: size = arcompact_handle04_22_dasm(DASM_PARAMS); break; // JLcc - case 0x23: size = arcompact_handle04_23_dasm(DASM_PARAMS); break; // JLcc.D - case 0x24: size = arcompact_handle04_24_dasm(DASM_PARAMS); break; // illegal - case 0x25: size = arcompact_handle04_25_dasm(DASM_PARAMS); break; // illegal - case 0x26: size = arcompact_handle04_26_dasm(DASM_PARAMS); break; // illegal - case 0x27: size = arcompact_handle04_27_dasm(DASM_PARAMS); break; // illegal - case 0x28: size = arcompact_handle04_28_dasm(DASM_PARAMS); break; // LPcc - case 0x29: size = arcompact_handle04_29_dasm(DASM_PARAMS); break; // FLAG - case 0x2a: size = arcompact_handle04_2a_dasm(DASM_PARAMS); break; // LR - case 0x2b: size = arcompact_handle04_2b_dasm(DASM_PARAMS); break; // SR - case 0x2c: size = arcompact_handle04_2c_dasm(DASM_PARAMS); break; // illegal - case 0x2d: size = arcompact_handle04_2d_dasm(DASM_PARAMS); break; // illegal - case 0x2e: size = arcompact_handle04_2e_dasm(DASM_PARAMS); break; // illegal - case 0x2f: size = arcompact_handle04_2f_dasm(DASM_PARAMS); break; // Sub Opcode - case 0x30: size = arcompact_handle04_30_dasm(DASM_PARAMS); break; // LD r-r - case 0x31: size = arcompact_handle04_31_dasm(DASM_PARAMS); break; // LD r-r - case 0x32: size = arcompact_handle04_32_dasm(DASM_PARAMS); break; // LD r-r - case 0x33: size = arcompact_handle04_33_dasm(DASM_PARAMS); break; // LD r-r - case 0x34: size = arcompact_handle04_34_dasm(DASM_PARAMS); break; // LD r-r - case 0x35: size = arcompact_handle04_35_dasm(DASM_PARAMS); break; // LD r-r - case 0x36: size = arcompact_handle04_36_dasm(DASM_PARAMS); break; // LD r-r - case 0x37: size = arcompact_handle04_37_dasm(DASM_PARAMS); break; // LD r-r - case 0x38: size = arcompact_handle04_38_dasm(DASM_PARAMS); break; // illegal - case 0x39: size = arcompact_handle04_39_dasm(DASM_PARAMS); break; // illegal - case 0x3a: size = arcompact_handle04_3a_dasm(DASM_PARAMS); break; // illegal - case 0x3b: size = arcompact_handle04_3b_dasm(DASM_PARAMS); break; // illegal - case 0x3c: size = arcompact_handle04_3c_dasm(DASM_PARAMS); break; // illegal - case 0x3d: size = arcompact_handle04_3d_dasm(DASM_PARAMS); break; // illegal - case 0x3e: size = arcompact_handle04_3e_dasm(DASM_PARAMS); break; // illegal - case 0x3f: size = arcompact_handle04_3f_dasm(DASM_PARAMS); break; // illegal + case 0x00:size = handle04_00_dasm(stream, pc, op, opcodes); break; // ADD + case 0x01:size = handle04_01_dasm(stream, pc, op, opcodes); break; // ADC + case 0x02:size = handle04_02_dasm(stream, pc, op, opcodes); break; // SUB + case 0x03:size = handle04_03_dasm(stream, pc, op, opcodes); break; // SBC + case 0x04:size = handle04_04_dasm(stream, pc, op, opcodes); break; // AND + case 0x05:size = handle04_05_dasm(stream, pc, op, opcodes); break; // OR + case 0x06:size = handle04_06_dasm(stream, pc, op, opcodes); break; // BIC + case 0x07:size = handle04_07_dasm(stream, pc, op, opcodes); break; // XOR + case 0x08:size = handle04_08_dasm(stream, pc, op, opcodes); break; // MAX + case 0x09:size = handle04_09_dasm(stream, pc, op, opcodes); break; // MIN + case 0x0a:size = handle04_0a_dasm(stream, pc, op, opcodes); break; // MOV + case 0x0b:size = handle04_0b_dasm(stream, pc, op, opcodes); break; // TST + case 0x0c:size = handle04_0c_dasm(stream, pc, op, opcodes); break; // CMP + case 0x0d:size = handle04_0d_dasm(stream, pc, op, opcodes); break; // RCMP + case 0x0e:size = handle04_0e_dasm(stream, pc, op, opcodes); break; // RSUB + case 0x0f:size = handle04_0f_dasm(stream, pc, op, opcodes); break; // BSET + case 0x10:size = handle04_10_dasm(stream, pc, op, opcodes); break; // BCLR + case 0x11:size = handle04_11_dasm(stream, pc, op, opcodes); break; // BTST + case 0x12:size = handle04_12_dasm(stream, pc, op, opcodes); break; // BXOR + case 0x13:size = handle04_13_dasm(stream, pc, op, opcodes); break; // BMSK + case 0x14:size = handle04_14_dasm(stream, pc, op, opcodes); break; // ADD1 + case 0x15:size = handle04_15_dasm(stream, pc, op, opcodes); break; // ADD2 + case 0x16:size = handle04_16_dasm(stream, pc, op, opcodes); break; // ADD3 + case 0x17:size = handle04_17_dasm(stream, pc, op, opcodes); break; // SUB1 + case 0x18:size = handle04_18_dasm(stream, pc, op, opcodes); break; // SUB2 + case 0x19:size = handle04_19_dasm(stream, pc, op, opcodes); break; // SUB3 + case 0x1a:size = handle04_1a_dasm(stream, pc, op, opcodes); break; // MPY * + case 0x1b:size = handle04_1b_dasm(stream, pc, op, opcodes); break; // MPYH * + case 0x1c:size = handle04_1c_dasm(stream, pc, op, opcodes); break; // MPYHU * + case 0x1d:size = handle04_1d_dasm(stream, pc, op, opcodes); break; // MPYU * + case 0x1e:size = handle04_1e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1f:size = handle04_1f_dasm(stream, pc, op, opcodes); break; // illegal + case 0x20:size = handle04_20_dasm(stream, pc, op, opcodes); break; // Jcc + case 0x21:size = handle04_21_dasm(stream, pc, op, opcodes); break; // Jcc.D + case 0x22:size = handle04_22_dasm(stream, pc, op, opcodes); break; // JLcc + case 0x23:size = handle04_23_dasm(stream, pc, op, opcodes); break; // JLcc.D + case 0x24:size = handle04_24_dasm(stream, pc, op, opcodes); break; // illegal + case 0x25:size = handle04_25_dasm(stream, pc, op, opcodes); break; // illegal + case 0x26:size = handle04_26_dasm(stream, pc, op, opcodes); break; // illegal + case 0x27:size = handle04_27_dasm(stream, pc, op, opcodes); break; // illegal + case 0x28:size = handle04_28_dasm(stream, pc, op, opcodes); break; // LPcc + case 0x29:size = handle04_29_dasm(stream, pc, op, opcodes); break; // FLAG + case 0x2a:size = handle04_2a_dasm(stream, pc, op, opcodes); break; // LR + case 0x2b:size = handle04_2b_dasm(stream, pc, op, opcodes); break; // SR + case 0x2c:size = handle04_2c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2d:size = handle04_2d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2e:size = handle04_2e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2f:size = handle04_2f_dasm(stream, pc, op, opcodes); break; // Sub Opcode + case 0x30:size = handle04_30_dasm(stream, pc, op, opcodes); break; // LD r-r + case 0x31:size = handle04_31_dasm(stream, pc, op, opcodes); break; // LD r-r + case 0x32:size = handle04_32_dasm(stream, pc, op, opcodes); break; // LD r-r + case 0x33:size = handle04_33_dasm(stream, pc, op, opcodes); break; // LD r-r + case 0x34:size = handle04_34_dasm(stream, pc, op, opcodes); break; // LD r-r + case 0x35:size = handle04_35_dasm(stream, pc, op, opcodes); break; // LD r-r + case 0x36:size = handle04_36_dasm(stream, pc, op, opcodes); break; // LD r-r + case 0x37:size = handle04_37_dasm(stream, pc, op, opcodes); break; // LD r-r + case 0x38:size = handle04_38_dasm(stream, pc, op, opcodes); break; // illegal + case 0x39:size = handle04_39_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3a:size = handle04_3a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3b:size = handle04_3b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3c:size = handle04_3c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3d:size = handle04_3d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3e:size = handle04_3e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3f:size = handle04_3f_dasm(stream, pc, op, opcodes); break; // illegal } return size; } -int arcompact_handle04_2f_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_2f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { int size = 4; uint8_t subinstr2 = (op & 0x0000003f) >> 0; @@ -228,77 +225,77 @@ int arcompact_handle04_2f_dasm(DASM_OPS_32) switch (subinstr2) { - case 0x00: size = arcompact_handle04_2f_00_dasm(DASM_PARAMS); break; // ASL - case 0x01: size = arcompact_handle04_2f_01_dasm(DASM_PARAMS); break; // ASR - case 0x02: size = arcompact_handle04_2f_02_dasm(DASM_PARAMS); break; // LSR - case 0x03: size = arcompact_handle04_2f_03_dasm(DASM_PARAMS); break; // ROR - case 0x04: size = arcompact_handle04_2f_04_dasm(DASM_PARAMS); break; // RCC - case 0x05: size = arcompact_handle04_2f_05_dasm(DASM_PARAMS); break; // SEXB - case 0x06: size = arcompact_handle04_2f_06_dasm(DASM_PARAMS); break; // SEXW - case 0x07: size = arcompact_handle04_2f_07_dasm(DASM_PARAMS); break; // EXTB - case 0x08: size = arcompact_handle04_2f_08_dasm(DASM_PARAMS); break; // EXTW - case 0x09: size = arcompact_handle04_2f_09_dasm(DASM_PARAMS); break; // ABS - case 0x0a: size = arcompact_handle04_2f_0a_dasm(DASM_PARAMS); break; // NOT - case 0x0b: size = arcompact_handle04_2f_0b_dasm(DASM_PARAMS); break; // RLC - case 0x0c: size = arcompact_handle04_2f_0c_dasm(DASM_PARAMS); break; // EX - case 0x0d: size = arcompact_handle04_2f_0d_dasm(DASM_PARAMS); break; // illegal - case 0x0e: size = arcompact_handle04_2f_0e_dasm(DASM_PARAMS); break; // illegal - case 0x0f: size = arcompact_handle04_2f_0f_dasm(DASM_PARAMS); break; // illegal - case 0x10: size = arcompact_handle04_2f_10_dasm(DASM_PARAMS); break; // illegal - case 0x11: size = arcompact_handle04_2f_11_dasm(DASM_PARAMS); break; // illegal - case 0x12: size = arcompact_handle04_2f_12_dasm(DASM_PARAMS); break; // illegal - case 0x13: size = arcompact_handle04_2f_13_dasm(DASM_PARAMS); break; // illegal - case 0x14: size = arcompact_handle04_2f_14_dasm(DASM_PARAMS); break; // illegal - case 0x15: size = arcompact_handle04_2f_15_dasm(DASM_PARAMS); break; // illegal - case 0x16: size = arcompact_handle04_2f_16_dasm(DASM_PARAMS); break; // illegal - case 0x17: size = arcompact_handle04_2f_17_dasm(DASM_PARAMS); break; // illegal - case 0x18: size = arcompact_handle04_2f_18_dasm(DASM_PARAMS); break; // illegal - case 0x19: size = arcompact_handle04_2f_19_dasm(DASM_PARAMS); break; // illegal - case 0x1a: size = arcompact_handle04_2f_1a_dasm(DASM_PARAMS); break; // illegal - case 0x1b: size = arcompact_handle04_2f_1b_dasm(DASM_PARAMS); break; // illegal - case 0x1c: size = arcompact_handle04_2f_1c_dasm(DASM_PARAMS); break; // illegal - case 0x1d: size = arcompact_handle04_2f_1d_dasm(DASM_PARAMS); break; // illegal - case 0x1e: size = arcompact_handle04_2f_1e_dasm(DASM_PARAMS); break; // illegal - case 0x1f: size = arcompact_handle04_2f_1f_dasm(DASM_PARAMS); break; // illegal - case 0x20: size = arcompact_handle04_2f_20_dasm(DASM_PARAMS); break; // illegal - case 0x21: size = arcompact_handle04_2f_21_dasm(DASM_PARAMS); break; // illegal - case 0x22: size = arcompact_handle04_2f_22_dasm(DASM_PARAMS); break; // illegal - case 0x23: size = arcompact_handle04_2f_23_dasm(DASM_PARAMS); break; // illegal - case 0x24: size = arcompact_handle04_2f_24_dasm(DASM_PARAMS); break; // illegal - case 0x25: size = arcompact_handle04_2f_25_dasm(DASM_PARAMS); break; // illegal - case 0x26: size = arcompact_handle04_2f_26_dasm(DASM_PARAMS); break; // illegal - case 0x27: size = arcompact_handle04_2f_27_dasm(DASM_PARAMS); break; // illegal - case 0x28: size = arcompact_handle04_2f_28_dasm(DASM_PARAMS); break; // illegal - case 0x29: size = arcompact_handle04_2f_29_dasm(DASM_PARAMS); break; // illegal - case 0x2a: size = arcompact_handle04_2f_2a_dasm(DASM_PARAMS); break; // illegal - case 0x2b: size = arcompact_handle04_2f_2b_dasm(DASM_PARAMS); break; // illegal - case 0x2c: size = arcompact_handle04_2f_2c_dasm(DASM_PARAMS); break; // illegal - case 0x2d: size = arcompact_handle04_2f_2d_dasm(DASM_PARAMS); break; // illegal - case 0x2e: size = arcompact_handle04_2f_2e_dasm(DASM_PARAMS); break; // illegal - case 0x2f: size = arcompact_handle04_2f_2f_dasm(DASM_PARAMS); break; // illegal - case 0x30: size = arcompact_handle04_2f_30_dasm(DASM_PARAMS); break; // illegal - case 0x31: size = arcompact_handle04_2f_31_dasm(DASM_PARAMS); break; // illegal - case 0x32: size = arcompact_handle04_2f_32_dasm(DASM_PARAMS); break; // illegal - case 0x33: size = arcompact_handle04_2f_33_dasm(DASM_PARAMS); break; // illegal - case 0x34: size = arcompact_handle04_2f_34_dasm(DASM_PARAMS); break; // illegal - case 0x35: size = arcompact_handle04_2f_35_dasm(DASM_PARAMS); break; // illegal - case 0x36: size = arcompact_handle04_2f_36_dasm(DASM_PARAMS); break; // illegal - case 0x37: size = arcompact_handle04_2f_37_dasm(DASM_PARAMS); break; // illegal - case 0x38: size = arcompact_handle04_2f_38_dasm(DASM_PARAMS); break; // illegal - case 0x39: size = arcompact_handle04_2f_39_dasm(DASM_PARAMS); break; // illegal - case 0x3a: size = arcompact_handle04_2f_3a_dasm(DASM_PARAMS); break; // illegal - case 0x3b: size = arcompact_handle04_2f_3b_dasm(DASM_PARAMS); break; // illegal - case 0x3c: size = arcompact_handle04_2f_3c_dasm(DASM_PARAMS); break; // illegal - case 0x3d: size = arcompact_handle04_2f_3d_dasm(DASM_PARAMS); break; // illegal - case 0x3e: size = arcompact_handle04_2f_3e_dasm(DASM_PARAMS); break; // illegal - case 0x3f: size = arcompact_handle04_2f_3f_dasm(DASM_PARAMS); break; // ZOPs (Zero Operand Opcodes) + case 0x00:size = handle04_2f_00_dasm(stream, pc, op, opcodes); break; // ASL + case 0x01:size = handle04_2f_01_dasm(stream, pc, op, opcodes); break; // ASR + case 0x02:size = handle04_2f_02_dasm(stream, pc, op, opcodes); break; // LSR + case 0x03:size = handle04_2f_03_dasm(stream, pc, op, opcodes); break; // ROR + case 0x04:size = handle04_2f_04_dasm(stream, pc, op, opcodes); break; // RCC + case 0x05:size = handle04_2f_05_dasm(stream, pc, op, opcodes); break; // SEXB + case 0x06:size = handle04_2f_06_dasm(stream, pc, op, opcodes); break; // SEXW + case 0x07:size = handle04_2f_07_dasm(stream, pc, op, opcodes); break; // EXTB + case 0x08:size = handle04_2f_08_dasm(stream, pc, op, opcodes); break; // EXTW + case 0x09:size = handle04_2f_09_dasm(stream, pc, op, opcodes); break; // ABS + case 0x0a:size = handle04_2f_0a_dasm(stream, pc, op, opcodes); break; // NOT + case 0x0b:size = handle04_2f_0b_dasm(stream, pc, op, opcodes); break; // RLC + case 0x0c:size = handle04_2f_0c_dasm(stream, pc, op, opcodes); break; // EX + case 0x0d:size = handle04_2f_0d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0e:size = handle04_2f_0e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0f:size = handle04_2f_0f_dasm(stream, pc, op, opcodes); break; // illegal + case 0x10:size = handle04_2f_10_dasm(stream, pc, op, opcodes); break; // illegal + case 0x11:size = handle04_2f_11_dasm(stream, pc, op, opcodes); break; // illegal + case 0x12:size = handle04_2f_12_dasm(stream, pc, op, opcodes); break; // illegal + case 0x13:size = handle04_2f_13_dasm(stream, pc, op, opcodes); break; // illegal + case 0x14:size = handle04_2f_14_dasm(stream, pc, op, opcodes); break; // illegal + case 0x15:size = handle04_2f_15_dasm(stream, pc, op, opcodes); break; // illegal + case 0x16:size = handle04_2f_16_dasm(stream, pc, op, opcodes); break; // illegal + case 0x17:size = handle04_2f_17_dasm(stream, pc, op, opcodes); break; // illegal + case 0x18:size = handle04_2f_18_dasm(stream, pc, op, opcodes); break; // illegal + case 0x19:size = handle04_2f_19_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1a:size = handle04_2f_1a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1b:size = handle04_2f_1b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1c:size = handle04_2f_1c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1d:size = handle04_2f_1d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1e:size = handle04_2f_1e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1f:size = handle04_2f_1f_dasm(stream, pc, op, opcodes); break; // illegal + case 0x20:size = handle04_2f_20_dasm(stream, pc, op, opcodes); break; // illegal + case 0x21:size = handle04_2f_21_dasm(stream, pc, op, opcodes); break; // illegal + case 0x22:size = handle04_2f_22_dasm(stream, pc, op, opcodes); break; // illegal + case 0x23:size = handle04_2f_23_dasm(stream, pc, op, opcodes); break; // illegal + case 0x24:size = handle04_2f_24_dasm(stream, pc, op, opcodes); break; // illegal + case 0x25:size = handle04_2f_25_dasm(stream, pc, op, opcodes); break; // illegal + case 0x26:size = handle04_2f_26_dasm(stream, pc, op, opcodes); break; // illegal + case 0x27:size = handle04_2f_27_dasm(stream, pc, op, opcodes); break; // illegal + case 0x28:size = handle04_2f_28_dasm(stream, pc, op, opcodes); break; // illegal + case 0x29:size = handle04_2f_29_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2a:size = handle04_2f_2a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2b:size = handle04_2f_2b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2c:size = handle04_2f_2c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2d:size = handle04_2f_2d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2e:size = handle04_2f_2e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2f:size = handle04_2f_2f_dasm(stream, pc, op, opcodes); break; // illegal + case 0x30:size = handle04_2f_30_dasm(stream, pc, op, opcodes); break; // illegal + case 0x31:size = handle04_2f_31_dasm(stream, pc, op, opcodes); break; // illegal + case 0x32:size = handle04_2f_32_dasm(stream, pc, op, opcodes); break; // illegal + case 0x33:size = handle04_2f_33_dasm(stream, pc, op, opcodes); break; // illegal + case 0x34:size = handle04_2f_34_dasm(stream, pc, op, opcodes); break; // illegal + case 0x35:size = handle04_2f_35_dasm(stream, pc, op, opcodes); break; // illegal + case 0x36:size = handle04_2f_36_dasm(stream, pc, op, opcodes); break; // illegal + case 0x37:size = handle04_2f_37_dasm(stream, pc, op, opcodes); break; // illegal + case 0x38:size = handle04_2f_38_dasm(stream, pc, op, opcodes); break; // illegal + case 0x39:size = handle04_2f_39_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3a:size = handle04_2f_3a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3b:size = handle04_2f_3b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3c:size = handle04_2f_3c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3d:size = handle04_2f_3d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3e:size = handle04_2f_3e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3f:size = handle04_2f_3f_dasm(stream, pc, op, opcodes); break; // ZOPs (Zero Operand Opcodes) } return size; } -int arcompact_handle05_2f_dasm(DASM_OPS_32) +int arcompact_disassembler::handle05_2f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { int size = 4; uint8_t subinstr2 = (op & 0x0000003f) >> 0; @@ -306,76 +303,76 @@ int arcompact_handle05_2f_dasm(DASM_OPS_32) switch (subinstr2) { - case 0x00: size = arcompact_handle05_2f_00_dasm(DASM_PARAMS); break; // SWAP - case 0x01: size = arcompact_handle05_2f_01_dasm(DASM_PARAMS); break; // NORM - case 0x02: size = arcompact_handle05_2f_02_dasm(DASM_PARAMS); break; // SAT16 - case 0x03: size = arcompact_handle05_2f_03_dasm(DASM_PARAMS); break; // RND16 - case 0x04: size = arcompact_handle05_2f_04_dasm(DASM_PARAMS); break; // ABSSW - case 0x05: size = arcompact_handle05_2f_05_dasm(DASM_PARAMS); break; // ABSS - case 0x06: size = arcompact_handle05_2f_06_dasm(DASM_PARAMS); break; // NEGSW - case 0x07: size = arcompact_handle05_2f_07_dasm(DASM_PARAMS); break; // NEGS - case 0x08: size = arcompact_handle05_2f_08_dasm(DASM_PARAMS); break; // NORMW - case 0x09: size = arcompact_handle05_2f_09_dasm(DASM_PARAMS); break; // illegal - case 0x0a: size = arcompact_handle05_2f_0a_dasm(DASM_PARAMS); break; // illegal - case 0x0b: size = arcompact_handle05_2f_0b_dasm(DASM_PARAMS); break; // illegal - case 0x0c: size = arcompact_handle05_2f_0c_dasm(DASM_PARAMS); break; // illegal - case 0x0d: size = arcompact_handle05_2f_0d_dasm(DASM_PARAMS); break; // illegal - case 0x0e: size = arcompact_handle05_2f_0e_dasm(DASM_PARAMS); break; // illegal - case 0x0f: size = arcompact_handle05_2f_0f_dasm(DASM_PARAMS); break; // illegal - case 0x10: size = arcompact_handle05_2f_10_dasm(DASM_PARAMS); break; // illegal - case 0x11: size = arcompact_handle05_2f_11_dasm(DASM_PARAMS); break; // illegal - case 0x12: size = arcompact_handle05_2f_12_dasm(DASM_PARAMS); break; // illegal - case 0x13: size = arcompact_handle05_2f_13_dasm(DASM_PARAMS); break; // illegal - case 0x14: size = arcompact_handle05_2f_14_dasm(DASM_PARAMS); break; // illegal - case 0x15: size = arcompact_handle05_2f_15_dasm(DASM_PARAMS); break; // illegal - case 0x16: size = arcompact_handle05_2f_16_dasm(DASM_PARAMS); break; // illegal - case 0x17: size = arcompact_handle05_2f_17_dasm(DASM_PARAMS); break; // illegal - case 0x18: size = arcompact_handle05_2f_18_dasm(DASM_PARAMS); break; // illegal - case 0x19: size = arcompact_handle05_2f_19_dasm(DASM_PARAMS); break; // illegal - case 0x1a: size = arcompact_handle05_2f_1a_dasm(DASM_PARAMS); break; // illegal - case 0x1b: size = arcompact_handle05_2f_1b_dasm(DASM_PARAMS); break; // illegal - case 0x1c: size = arcompact_handle05_2f_1c_dasm(DASM_PARAMS); break; // illegal - case 0x1d: size = arcompact_handle05_2f_1d_dasm(DASM_PARAMS); break; // illegal - case 0x1e: size = arcompact_handle05_2f_1e_dasm(DASM_PARAMS); break; // illegal - case 0x1f: size = arcompact_handle05_2f_1f_dasm(DASM_PARAMS); break; // illegal - case 0x20: size = arcompact_handle05_2f_20_dasm(DASM_PARAMS); break; // illegal - case 0x21: size = arcompact_handle05_2f_21_dasm(DASM_PARAMS); break; // illegal - case 0x22: size = arcompact_handle05_2f_22_dasm(DASM_PARAMS); break; // illegal - case 0x23: size = arcompact_handle05_2f_23_dasm(DASM_PARAMS); break; // illegal - case 0x24: size = arcompact_handle05_2f_24_dasm(DASM_PARAMS); break; // illegal - case 0x25: size = arcompact_handle05_2f_25_dasm(DASM_PARAMS); break; // illegal - case 0x26: size = arcompact_handle05_2f_26_dasm(DASM_PARAMS); break; // illegal - case 0x27: size = arcompact_handle05_2f_27_dasm(DASM_PARAMS); break; // illegal - case 0x28: size = arcompact_handle05_2f_28_dasm(DASM_PARAMS); break; // illegal - case 0x29: size = arcompact_handle05_2f_29_dasm(DASM_PARAMS); break; // illegal - case 0x2a: size = arcompact_handle05_2f_2a_dasm(DASM_PARAMS); break; // illegal - case 0x2b: size = arcompact_handle05_2f_2b_dasm(DASM_PARAMS); break; // illegal - case 0x2c: size = arcompact_handle05_2f_2c_dasm(DASM_PARAMS); break; // illegal - case 0x2d: size = arcompact_handle05_2f_2d_dasm(DASM_PARAMS); break; // illegal - case 0x2e: size = arcompact_handle05_2f_2e_dasm(DASM_PARAMS); break; // illegal - case 0x2f: size = arcompact_handle05_2f_2f_dasm(DASM_PARAMS); break; // illegal - case 0x30: size = arcompact_handle05_2f_30_dasm(DASM_PARAMS); break; // illegal - case 0x31: size = arcompact_handle05_2f_31_dasm(DASM_PARAMS); break; // illegal - case 0x32: size = arcompact_handle05_2f_32_dasm(DASM_PARAMS); break; // illegal - case 0x33: size = arcompact_handle05_2f_33_dasm(DASM_PARAMS); break; // illegal - case 0x34: size = arcompact_handle05_2f_34_dasm(DASM_PARAMS); break; // illegal - case 0x35: size = arcompact_handle05_2f_35_dasm(DASM_PARAMS); break; // illegal - case 0x36: size = arcompact_handle05_2f_36_dasm(DASM_PARAMS); break; // illegal - case 0x37: size = arcompact_handle05_2f_37_dasm(DASM_PARAMS); break; // illegal - case 0x38: size = arcompact_handle05_2f_38_dasm(DASM_PARAMS); break; // illegal - case 0x39: size = arcompact_handle05_2f_39_dasm(DASM_PARAMS); break; // illegal - case 0x3a: size = arcompact_handle05_2f_3a_dasm(DASM_PARAMS); break; // illegal - case 0x3b: size = arcompact_handle05_2f_3b_dasm(DASM_PARAMS); break; // illegal - case 0x3c: size = arcompact_handle05_2f_3c_dasm(DASM_PARAMS); break; // illegal - case 0x3d: size = arcompact_handle05_2f_3d_dasm(DASM_PARAMS); break; // illegal - case 0x3e: size = arcompact_handle05_2f_3e_dasm(DASM_PARAMS); break; // illegal - case 0x3f: size = arcompact_handle05_2f_3f_dasm(DASM_PARAMS); break; // ZOPs (Zero Operand Opcodes) + case 0x00:size = handle05_2f_00_dasm(stream, pc, op, opcodes); break; // SWAP + case 0x01:size = handle05_2f_01_dasm(stream, pc, op, opcodes); break; // NORM + case 0x02:size = handle05_2f_02_dasm(stream, pc, op, opcodes); break; // SAT16 + case 0x03:size = handle05_2f_03_dasm(stream, pc, op, opcodes); break; // RND16 + case 0x04:size = handle05_2f_04_dasm(stream, pc, op, opcodes); break; // ABSSW + case 0x05:size = handle05_2f_05_dasm(stream, pc, op, opcodes); break; // ABSS + case 0x06:size = handle05_2f_06_dasm(stream, pc, op, opcodes); break; // NEGSW + case 0x07:size = handle05_2f_07_dasm(stream, pc, op, opcodes); break; // NEGS + case 0x08:size = handle05_2f_08_dasm(stream, pc, op, opcodes); break; // NORMW + case 0x09:size = handle05_2f_09_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0a:size = handle05_2f_0a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0b:size = handle05_2f_0b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0c:size = handle05_2f_0c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0d:size = handle05_2f_0d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0e:size = handle05_2f_0e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0f:size = handle05_2f_0f_dasm(stream, pc, op, opcodes); break; // illegal + case 0x10:size = handle05_2f_10_dasm(stream, pc, op, opcodes); break; // illegal + case 0x11:size = handle05_2f_11_dasm(stream, pc, op, opcodes); break; // illegal + case 0x12:size = handle05_2f_12_dasm(stream, pc, op, opcodes); break; // illegal + case 0x13:size = handle05_2f_13_dasm(stream, pc, op, opcodes); break; // illegal + case 0x14:size = handle05_2f_14_dasm(stream, pc, op, opcodes); break; // illegal + case 0x15:size = handle05_2f_15_dasm(stream, pc, op, opcodes); break; // illegal + case 0x16:size = handle05_2f_16_dasm(stream, pc, op, opcodes); break; // illegal + case 0x17:size = handle05_2f_17_dasm(stream, pc, op, opcodes); break; // illegal + case 0x18:size = handle05_2f_18_dasm(stream, pc, op, opcodes); break; // illegal + case 0x19:size = handle05_2f_19_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1a:size = handle05_2f_1a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1b:size = handle05_2f_1b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1c:size = handle05_2f_1c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1d:size = handle05_2f_1d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1e:size = handle05_2f_1e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1f:size = handle05_2f_1f_dasm(stream, pc, op, opcodes); break; // illegal + case 0x20:size = handle05_2f_20_dasm(stream, pc, op, opcodes); break; // illegal + case 0x21:size = handle05_2f_21_dasm(stream, pc, op, opcodes); break; // illegal + case 0x22:size = handle05_2f_22_dasm(stream, pc, op, opcodes); break; // illegal + case 0x23:size = handle05_2f_23_dasm(stream, pc, op, opcodes); break; // illegal + case 0x24:size = handle05_2f_24_dasm(stream, pc, op, opcodes); break; // illegal + case 0x25:size = handle05_2f_25_dasm(stream, pc, op, opcodes); break; // illegal + case 0x26:size = handle05_2f_26_dasm(stream, pc, op, opcodes); break; // illegal + case 0x27:size = handle05_2f_27_dasm(stream, pc, op, opcodes); break; // illegal + case 0x28:size = handle05_2f_28_dasm(stream, pc, op, opcodes); break; // illegal + case 0x29:size = handle05_2f_29_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2a:size = handle05_2f_2a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2b:size = handle05_2f_2b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2c:size = handle05_2f_2c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2d:size = handle05_2f_2d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2e:size = handle05_2f_2e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2f:size = handle05_2f_2f_dasm(stream, pc, op, opcodes); break; // illegal + case 0x30:size = handle05_2f_30_dasm(stream, pc, op, opcodes); break; // illegal + case 0x31:size = handle05_2f_31_dasm(stream, pc, op, opcodes); break; // illegal + case 0x32:size = handle05_2f_32_dasm(stream, pc, op, opcodes); break; // illegal + case 0x33:size = handle05_2f_33_dasm(stream, pc, op, opcodes); break; // illegal + case 0x34:size = handle05_2f_34_dasm(stream, pc, op, opcodes); break; // illegal + case 0x35:size = handle05_2f_35_dasm(stream, pc, op, opcodes); break; // illegal + case 0x36:size = handle05_2f_36_dasm(stream, pc, op, opcodes); break; // illegal + case 0x37:size = handle05_2f_37_dasm(stream, pc, op, opcodes); break; // illegal + case 0x38:size = handle05_2f_38_dasm(stream, pc, op, opcodes); break; // illegal + case 0x39:size = handle05_2f_39_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3a:size = handle05_2f_3a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3b:size = handle05_2f_3b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3c:size = handle05_2f_3c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3d:size = handle05_2f_3d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3e:size = handle05_2f_3e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3f:size = handle05_2f_3f_dasm(stream, pc, op, opcodes); break; // ZOPs (Zero Operand Opcodes) } return size; } -int arcompact_handle04_2f_3f_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_2f_3f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { int size = 4; uint8_t subinstr3 = (op & 0x07000000) >> 24; @@ -385,77 +382,77 @@ int arcompact_handle04_2f_3f_dasm(DASM_OPS_32) switch (subinstr3) { - case 0x00: size = arcompact_handle04_2f_3f_00_dasm(DASM_PARAMS); break; // illegal - case 0x01: size = arcompact_handle04_2f_3f_01_dasm(DASM_PARAMS); break; // SLEEP - case 0x02: size = arcompact_handle04_2f_3f_02_dasm(DASM_PARAMS); break; // SWI / TRAP9 - case 0x03: size = arcompact_handle04_2f_3f_03_dasm(DASM_PARAMS); break; // SYNC - case 0x04: size = arcompact_handle04_2f_3f_04_dasm(DASM_PARAMS); break; // RTIE - case 0x05: size = arcompact_handle04_2f_3f_05_dasm(DASM_PARAMS); break; // BRK - case 0x06: size = arcompact_handle04_2f_3f_06_dasm(DASM_PARAMS); break; // illegal - case 0x07: size = arcompact_handle04_2f_3f_07_dasm(DASM_PARAMS); break; // illegal - case 0x08: size = arcompact_handle04_2f_3f_08_dasm(DASM_PARAMS); break; // illegal - case 0x09: size = arcompact_handle04_2f_3f_09_dasm(DASM_PARAMS); break; // illegal - case 0x0a: size = arcompact_handle04_2f_3f_0a_dasm(DASM_PARAMS); break; // illegal - case 0x0b: size = arcompact_handle04_2f_3f_0b_dasm(DASM_PARAMS); break; // illegal - case 0x0c: size = arcompact_handle04_2f_3f_0c_dasm(DASM_PARAMS); break; // illegal - case 0x0d: size = arcompact_handle04_2f_3f_0d_dasm(DASM_PARAMS); break; // illegal - case 0x0e: size = arcompact_handle04_2f_3f_0e_dasm(DASM_PARAMS); break; // illegal - case 0x0f: size = arcompact_handle04_2f_3f_0f_dasm(DASM_PARAMS); break; // illegal - case 0x10: size = arcompact_handle04_2f_3f_10_dasm(DASM_PARAMS); break; // illegal - case 0x11: size = arcompact_handle04_2f_3f_11_dasm(DASM_PARAMS); break; // illegal - case 0x12: size = arcompact_handle04_2f_3f_12_dasm(DASM_PARAMS); break; // illegal - case 0x13: size = arcompact_handle04_2f_3f_13_dasm(DASM_PARAMS); break; // illegal - case 0x14: size = arcompact_handle04_2f_3f_14_dasm(DASM_PARAMS); break; // illegal - case 0x15: size = arcompact_handle04_2f_3f_15_dasm(DASM_PARAMS); break; // illegal - case 0x16: size = arcompact_handle04_2f_3f_16_dasm(DASM_PARAMS); break; // illegal - case 0x17: size = arcompact_handle04_2f_3f_17_dasm(DASM_PARAMS); break; // illegal - case 0x18: size = arcompact_handle04_2f_3f_18_dasm(DASM_PARAMS); break; // illegal - case 0x19: size = arcompact_handle04_2f_3f_19_dasm(DASM_PARAMS); break; // illegal - case 0x1a: size = arcompact_handle04_2f_3f_1a_dasm(DASM_PARAMS); break; // illegal - case 0x1b: size = arcompact_handle04_2f_3f_1b_dasm(DASM_PARAMS); break; // illegal - case 0x1c: size = arcompact_handle04_2f_3f_1c_dasm(DASM_PARAMS); break; // illegal - case 0x1d: size = arcompact_handle04_2f_3f_1d_dasm(DASM_PARAMS); break; // illegal - case 0x1e: size = arcompact_handle04_2f_3f_1e_dasm(DASM_PARAMS); break; // illegal - case 0x1f: size = arcompact_handle04_2f_3f_1f_dasm(DASM_PARAMS); break; // illegal - case 0x20: size = arcompact_handle04_2f_3f_20_dasm(DASM_PARAMS); break; // illegal - case 0x21: size = arcompact_handle04_2f_3f_21_dasm(DASM_PARAMS); break; // illegal - case 0x22: size = arcompact_handle04_2f_3f_22_dasm(DASM_PARAMS); break; // illegal - case 0x23: size = arcompact_handle04_2f_3f_23_dasm(DASM_PARAMS); break; // illegal - case 0x24: size = arcompact_handle04_2f_3f_24_dasm(DASM_PARAMS); break; // illegal - case 0x25: size = arcompact_handle04_2f_3f_25_dasm(DASM_PARAMS); break; // illegal - case 0x26: size = arcompact_handle04_2f_3f_26_dasm(DASM_PARAMS); break; // illegal - case 0x27: size = arcompact_handle04_2f_3f_27_dasm(DASM_PARAMS); break; // illegal - case 0x28: size = arcompact_handle04_2f_3f_28_dasm(DASM_PARAMS); break; // illegal - case 0x29: size = arcompact_handle04_2f_3f_29_dasm(DASM_PARAMS); break; // illegal - case 0x2a: size = arcompact_handle04_2f_3f_2a_dasm(DASM_PARAMS); break; // illegal - case 0x2b: size = arcompact_handle04_2f_3f_2b_dasm(DASM_PARAMS); break; // illegal - case 0x2c: size = arcompact_handle04_2f_3f_2c_dasm(DASM_PARAMS); break; // illegal - case 0x2d: size = arcompact_handle04_2f_3f_2d_dasm(DASM_PARAMS); break; // illegal - case 0x2e: size = arcompact_handle04_2f_3f_2e_dasm(DASM_PARAMS); break; // illegal - case 0x2f: size = arcompact_handle04_2f_3f_2f_dasm(DASM_PARAMS); break; // illegal - case 0x30: size = arcompact_handle04_2f_3f_30_dasm(DASM_PARAMS); break; // illegal - case 0x31: size = arcompact_handle04_2f_3f_31_dasm(DASM_PARAMS); break; // illegal - case 0x32: size = arcompact_handle04_2f_3f_32_dasm(DASM_PARAMS); break; // illegal - case 0x33: size = arcompact_handle04_2f_3f_33_dasm(DASM_PARAMS); break; // illegal - case 0x34: size = arcompact_handle04_2f_3f_34_dasm(DASM_PARAMS); break; // illegal - case 0x35: size = arcompact_handle04_2f_3f_35_dasm(DASM_PARAMS); break; // illegal - case 0x36: size = arcompact_handle04_2f_3f_36_dasm(DASM_PARAMS); break; // illegal - case 0x37: size = arcompact_handle04_2f_3f_37_dasm(DASM_PARAMS); break; // illegal - case 0x38: size = arcompact_handle04_2f_3f_38_dasm(DASM_PARAMS); break; // illegal - case 0x39: size = arcompact_handle04_2f_3f_39_dasm(DASM_PARAMS); break; // illegal - case 0x3a: size = arcompact_handle04_2f_3f_3a_dasm(DASM_PARAMS); break; // illegal - case 0x3b: size = arcompact_handle04_2f_3f_3b_dasm(DASM_PARAMS); break; // illegal - case 0x3c: size = arcompact_handle04_2f_3f_3c_dasm(DASM_PARAMS); break; // illegal - case 0x3d: size = arcompact_handle04_2f_3f_3d_dasm(DASM_PARAMS); break; // illegal - case 0x3e: size = arcompact_handle04_2f_3f_3e_dasm(DASM_PARAMS); break; // illegal - case 0x3f: size = arcompact_handle04_2f_3f_3f_dasm(DASM_PARAMS); break; // illegal + case 0x00:size = handle04_2f_3f_00_dasm(stream, pc, op, opcodes); break; // illegal + case 0x01:size = handle04_2f_3f_01_dasm(stream, pc, op, opcodes); break; // SLEEP + case 0x02:size = handle04_2f_3f_02_dasm(stream, pc, op, opcodes); break; // SWI / TRAP9 + case 0x03:size = handle04_2f_3f_03_dasm(stream, pc, op, opcodes); break; // SYNC + case 0x04:size = handle04_2f_3f_04_dasm(stream, pc, op, opcodes); break; // RTIE + case 0x05:size = handle04_2f_3f_05_dasm(stream, pc, op, opcodes); break; // BRK + case 0x06:size = handle04_2f_3f_06_dasm(stream, pc, op, opcodes); break; // illegal + case 0x07:size = handle04_2f_3f_07_dasm(stream, pc, op, opcodes); break; // illegal + case 0x08:size = handle04_2f_3f_08_dasm(stream, pc, op, opcodes); break; // illegal + case 0x09:size = handle04_2f_3f_09_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0a:size = handle04_2f_3f_0a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0b:size = handle04_2f_3f_0b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0c:size = handle04_2f_3f_0c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0d:size = handle04_2f_3f_0d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0e:size = handle04_2f_3f_0e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0f:size = handle04_2f_3f_0f_dasm(stream, pc, op, opcodes); break; // illegal + case 0x10:size = handle04_2f_3f_10_dasm(stream, pc, op, opcodes); break; // illegal + case 0x11:size = handle04_2f_3f_11_dasm(stream, pc, op, opcodes); break; // illegal + case 0x12:size = handle04_2f_3f_12_dasm(stream, pc, op, opcodes); break; // illegal + case 0x13:size = handle04_2f_3f_13_dasm(stream, pc, op, opcodes); break; // illegal + case 0x14:size = handle04_2f_3f_14_dasm(stream, pc, op, opcodes); break; // illegal + case 0x15:size = handle04_2f_3f_15_dasm(stream, pc, op, opcodes); break; // illegal + case 0x16:size = handle04_2f_3f_16_dasm(stream, pc, op, opcodes); break; // illegal + case 0x17:size = handle04_2f_3f_17_dasm(stream, pc, op, opcodes); break; // illegal + case 0x18:size = handle04_2f_3f_18_dasm(stream, pc, op, opcodes); break; // illegal + case 0x19:size = handle04_2f_3f_19_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1a:size = handle04_2f_3f_1a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1b:size = handle04_2f_3f_1b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1c:size = handle04_2f_3f_1c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1d:size = handle04_2f_3f_1d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1e:size = handle04_2f_3f_1e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1f:size = handle04_2f_3f_1f_dasm(stream, pc, op, opcodes); break; // illegal + case 0x20:size = handle04_2f_3f_20_dasm(stream, pc, op, opcodes); break; // illegal + case 0x21:size = handle04_2f_3f_21_dasm(stream, pc, op, opcodes); break; // illegal + case 0x22:size = handle04_2f_3f_22_dasm(stream, pc, op, opcodes); break; // illegal + case 0x23:size = handle04_2f_3f_23_dasm(stream, pc, op, opcodes); break; // illegal + case 0x24:size = handle04_2f_3f_24_dasm(stream, pc, op, opcodes); break; // illegal + case 0x25:size = handle04_2f_3f_25_dasm(stream, pc, op, opcodes); break; // illegal + case 0x26:size = handle04_2f_3f_26_dasm(stream, pc, op, opcodes); break; // illegal + case 0x27:size = handle04_2f_3f_27_dasm(stream, pc, op, opcodes); break; // illegal + case 0x28:size = handle04_2f_3f_28_dasm(stream, pc, op, opcodes); break; // illegal + case 0x29:size = handle04_2f_3f_29_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2a:size = handle04_2f_3f_2a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2b:size = handle04_2f_3f_2b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2c:size = handle04_2f_3f_2c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2d:size = handle04_2f_3f_2d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2e:size = handle04_2f_3f_2e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2f:size = handle04_2f_3f_2f_dasm(stream, pc, op, opcodes); break; // illegal + case 0x30:size = handle04_2f_3f_30_dasm(stream, pc, op, opcodes); break; // illegal + case 0x31:size = handle04_2f_3f_31_dasm(stream, pc, op, opcodes); break; // illegal + case 0x32:size = handle04_2f_3f_32_dasm(stream, pc, op, opcodes); break; // illegal + case 0x33:size = handle04_2f_3f_33_dasm(stream, pc, op, opcodes); break; // illegal + case 0x34:size = handle04_2f_3f_34_dasm(stream, pc, op, opcodes); break; // illegal + case 0x35:size = handle04_2f_3f_35_dasm(stream, pc, op, opcodes); break; // illegal + case 0x36:size = handle04_2f_3f_36_dasm(stream, pc, op, opcodes); break; // illegal + case 0x37:size = handle04_2f_3f_37_dasm(stream, pc, op, opcodes); break; // illegal + case 0x38:size = handle04_2f_3f_38_dasm(stream, pc, op, opcodes); break; // illegal + case 0x39:size = handle04_2f_3f_39_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3a:size = handle04_2f_3f_3a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3b:size = handle04_2f_3f_3b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3c:size = handle04_2f_3f_3c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3d:size = handle04_2f_3f_3d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3e:size = handle04_2f_3f_3e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3f:size = handle04_2f_3f_3f_dasm(stream, pc, op, opcodes); break; // illegal } return size; } -int arcompact_handle05_2f_3f_dasm(DASM_OPS_32) // useless ZOP group, no actual opcodes +int arcompact_disassembler::handle05_2f_3f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) // useless ZOP group, no actual opcodes { int size = 4; uint8_t subinstr3 = (op & 0x07000000) >> 24; @@ -465,70 +462,70 @@ int arcompact_handle05_2f_3f_dasm(DASM_OPS_32) // useless ZOP group, no actual o switch (subinstr3) { - case 0x00: size = arcompact_handle05_2f_3f_00_dasm(DASM_PARAMS); break; // illegal - case 0x01: size = arcompact_handle05_2f_3f_01_dasm(DASM_PARAMS); break; // illegal - case 0x02: size = arcompact_handle05_2f_3f_02_dasm(DASM_PARAMS); break; // illegal - case 0x03: size = arcompact_handle05_2f_3f_03_dasm(DASM_PARAMS); break; // illegal - case 0x04: size = arcompact_handle05_2f_3f_04_dasm(DASM_PARAMS); break; // illegal - case 0x05: size = arcompact_handle05_2f_3f_05_dasm(DASM_PARAMS); break; // illegal - case 0x06: size = arcompact_handle05_2f_3f_06_dasm(DASM_PARAMS); break; // illegal - case 0x07: size = arcompact_handle05_2f_3f_07_dasm(DASM_PARAMS); break; // illegal - case 0x08: size = arcompact_handle05_2f_3f_08_dasm(DASM_PARAMS); break; // illegal - case 0x09: size = arcompact_handle05_2f_3f_09_dasm(DASM_PARAMS); break; // illegal - case 0x0a: size = arcompact_handle05_2f_3f_0a_dasm(DASM_PARAMS); break; // illegal - case 0x0b: size = arcompact_handle05_2f_3f_0b_dasm(DASM_PARAMS); break; // illegal - case 0x0c: size = arcompact_handle05_2f_3f_0c_dasm(DASM_PARAMS); break; // illegal - case 0x0d: size = arcompact_handle05_2f_3f_0d_dasm(DASM_PARAMS); break; // illegal - case 0x0e: size = arcompact_handle05_2f_3f_0e_dasm(DASM_PARAMS); break; // illegal - case 0x0f: size = arcompact_handle05_2f_3f_0f_dasm(DASM_PARAMS); break; // illegal - case 0x10: size = arcompact_handle05_2f_3f_10_dasm(DASM_PARAMS); break; // illegal - case 0x11: size = arcompact_handle05_2f_3f_11_dasm(DASM_PARAMS); break; // illegal - case 0x12: size = arcompact_handle05_2f_3f_12_dasm(DASM_PARAMS); break; // illegal - case 0x13: size = arcompact_handle05_2f_3f_13_dasm(DASM_PARAMS); break; // illegal - case 0x14: size = arcompact_handle05_2f_3f_14_dasm(DASM_PARAMS); break; // illegal - case 0x15: size = arcompact_handle05_2f_3f_15_dasm(DASM_PARAMS); break; // illegal - case 0x16: size = arcompact_handle05_2f_3f_16_dasm(DASM_PARAMS); break; // illegal - case 0x17: size = arcompact_handle05_2f_3f_17_dasm(DASM_PARAMS); break; // illegal - case 0x18: size = arcompact_handle05_2f_3f_18_dasm(DASM_PARAMS); break; // illegal - case 0x19: size = arcompact_handle05_2f_3f_19_dasm(DASM_PARAMS); break; // illegal - case 0x1a: size = arcompact_handle05_2f_3f_1a_dasm(DASM_PARAMS); break; // illegal - case 0x1b: size = arcompact_handle05_2f_3f_1b_dasm(DASM_PARAMS); break; // illegal - case 0x1c: size = arcompact_handle05_2f_3f_1c_dasm(DASM_PARAMS); break; // illegal - case 0x1d: size = arcompact_handle05_2f_3f_1d_dasm(DASM_PARAMS); break; // illegal - case 0x1e: size = arcompact_handle05_2f_3f_1e_dasm(DASM_PARAMS); break; // illegal - case 0x1f: size = arcompact_handle05_2f_3f_1f_dasm(DASM_PARAMS); break; // illegal - case 0x20: size = arcompact_handle05_2f_3f_20_dasm(DASM_PARAMS); break; // illegal - case 0x21: size = arcompact_handle05_2f_3f_21_dasm(DASM_PARAMS); break; // illegal - case 0x22: size = arcompact_handle05_2f_3f_22_dasm(DASM_PARAMS); break; // illegal - case 0x23: size = arcompact_handle05_2f_3f_23_dasm(DASM_PARAMS); break; // illegal - case 0x24: size = arcompact_handle05_2f_3f_24_dasm(DASM_PARAMS); break; // illegal - case 0x25: size = arcompact_handle05_2f_3f_25_dasm(DASM_PARAMS); break; // illegal - case 0x26: size = arcompact_handle05_2f_3f_26_dasm(DASM_PARAMS); break; // illegal - case 0x27: size = arcompact_handle05_2f_3f_27_dasm(DASM_PARAMS); break; // illegal - case 0x28: size = arcompact_handle05_2f_3f_28_dasm(DASM_PARAMS); break; // illegal - case 0x29: size = arcompact_handle05_2f_3f_29_dasm(DASM_PARAMS); break; // illegal - case 0x2a: size = arcompact_handle05_2f_3f_2a_dasm(DASM_PARAMS); break; // illegal - case 0x2b: size = arcompact_handle05_2f_3f_2b_dasm(DASM_PARAMS); break; // illegal - case 0x2c: size = arcompact_handle05_2f_3f_2c_dasm(DASM_PARAMS); break; // illegal - case 0x2d: size = arcompact_handle05_2f_3f_2d_dasm(DASM_PARAMS); break; // illegal - case 0x2e: size = arcompact_handle05_2f_3f_2e_dasm(DASM_PARAMS); break; // illegal - case 0x2f: size = arcompact_handle05_2f_3f_2f_dasm(DASM_PARAMS); break; // illegal - case 0x30: size = arcompact_handle05_2f_3f_30_dasm(DASM_PARAMS); break; // illegal - case 0x31: size = arcompact_handle05_2f_3f_31_dasm(DASM_PARAMS); break; // illegal - case 0x32: size = arcompact_handle05_2f_3f_32_dasm(DASM_PARAMS); break; // illegal - case 0x33: size = arcompact_handle05_2f_3f_33_dasm(DASM_PARAMS); break; // illegal - case 0x34: size = arcompact_handle05_2f_3f_34_dasm(DASM_PARAMS); break; // illegal - case 0x35: size = arcompact_handle05_2f_3f_35_dasm(DASM_PARAMS); break; // illegal - case 0x36: size = arcompact_handle05_2f_3f_36_dasm(DASM_PARAMS); break; // illegal - case 0x37: size = arcompact_handle05_2f_3f_37_dasm(DASM_PARAMS); break; // illegal - case 0x38: size = arcompact_handle05_2f_3f_38_dasm(DASM_PARAMS); break; // illegal - case 0x39: size = arcompact_handle05_2f_3f_39_dasm(DASM_PARAMS); break; // illegal - case 0x3a: size = arcompact_handle05_2f_3f_3a_dasm(DASM_PARAMS); break; // illegal - case 0x3b: size = arcompact_handle05_2f_3f_3b_dasm(DASM_PARAMS); break; // illegal - case 0x3c: size = arcompact_handle05_2f_3f_3c_dasm(DASM_PARAMS); break; // illegal - case 0x3d: size = arcompact_handle05_2f_3f_3d_dasm(DASM_PARAMS); break; // illegal - case 0x3e: size = arcompact_handle05_2f_3f_3e_dasm(DASM_PARAMS); break; // illegal - case 0x3f: size = arcompact_handle05_2f_3f_3f_dasm(DASM_PARAMS); break; // illegal + case 0x00:size = handle05_2f_3f_00_dasm(stream, pc, op, opcodes); break; // illegal + case 0x01:size = handle05_2f_3f_01_dasm(stream, pc, op, opcodes); break; // illegal + case 0x02:size = handle05_2f_3f_02_dasm(stream, pc, op, opcodes); break; // illegal + case 0x03:size = handle05_2f_3f_03_dasm(stream, pc, op, opcodes); break; // illegal + case 0x04:size = handle05_2f_3f_04_dasm(stream, pc, op, opcodes); break; // illegal + case 0x05:size = handle05_2f_3f_05_dasm(stream, pc, op, opcodes); break; // illegal + case 0x06:size = handle05_2f_3f_06_dasm(stream, pc, op, opcodes); break; // illegal + case 0x07:size = handle05_2f_3f_07_dasm(stream, pc, op, opcodes); break; // illegal + case 0x08:size = handle05_2f_3f_08_dasm(stream, pc, op, opcodes); break; // illegal + case 0x09:size = handle05_2f_3f_09_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0a:size = handle05_2f_3f_0a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0b:size = handle05_2f_3f_0b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0c:size = handle05_2f_3f_0c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0d:size = handle05_2f_3f_0d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0e:size = handle05_2f_3f_0e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0f:size = handle05_2f_3f_0f_dasm(stream, pc, op, opcodes); break; // illegal + case 0x10:size = handle05_2f_3f_10_dasm(stream, pc, op, opcodes); break; // illegal + case 0x11:size = handle05_2f_3f_11_dasm(stream, pc, op, opcodes); break; // illegal + case 0x12:size = handle05_2f_3f_12_dasm(stream, pc, op, opcodes); break; // illegal + case 0x13:size = handle05_2f_3f_13_dasm(stream, pc, op, opcodes); break; // illegal + case 0x14:size = handle05_2f_3f_14_dasm(stream, pc, op, opcodes); break; // illegal + case 0x15:size = handle05_2f_3f_15_dasm(stream, pc, op, opcodes); break; // illegal + case 0x16:size = handle05_2f_3f_16_dasm(stream, pc, op, opcodes); break; // illegal + case 0x17:size = handle05_2f_3f_17_dasm(stream, pc, op, opcodes); break; // illegal + case 0x18:size = handle05_2f_3f_18_dasm(stream, pc, op, opcodes); break; // illegal + case 0x19:size = handle05_2f_3f_19_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1a:size = handle05_2f_3f_1a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1b:size = handle05_2f_3f_1b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1c:size = handle05_2f_3f_1c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1d:size = handle05_2f_3f_1d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1e:size = handle05_2f_3f_1e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1f:size = handle05_2f_3f_1f_dasm(stream, pc, op, opcodes); break; // illegal + case 0x20:size = handle05_2f_3f_20_dasm(stream, pc, op, opcodes); break; // illegal + case 0x21:size = handle05_2f_3f_21_dasm(stream, pc, op, opcodes); break; // illegal + case 0x22:size = handle05_2f_3f_22_dasm(stream, pc, op, opcodes); break; // illegal + case 0x23:size = handle05_2f_3f_23_dasm(stream, pc, op, opcodes); break; // illegal + case 0x24:size = handle05_2f_3f_24_dasm(stream, pc, op, opcodes); break; // illegal + case 0x25:size = handle05_2f_3f_25_dasm(stream, pc, op, opcodes); break; // illegal + case 0x26:size = handle05_2f_3f_26_dasm(stream, pc, op, opcodes); break; // illegal + case 0x27:size = handle05_2f_3f_27_dasm(stream, pc, op, opcodes); break; // illegal + case 0x28:size = handle05_2f_3f_28_dasm(stream, pc, op, opcodes); break; // illegal + case 0x29:size = handle05_2f_3f_29_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2a:size = handle05_2f_3f_2a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2b:size = handle05_2f_3f_2b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2c:size = handle05_2f_3f_2c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2d:size = handle05_2f_3f_2d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2e:size = handle05_2f_3f_2e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2f:size = handle05_2f_3f_2f_dasm(stream, pc, op, opcodes); break; // illegal + case 0x30:size = handle05_2f_3f_30_dasm(stream, pc, op, opcodes); break; // illegal + case 0x31:size = handle05_2f_3f_31_dasm(stream, pc, op, opcodes); break; // illegal + case 0x32:size = handle05_2f_3f_32_dasm(stream, pc, op, opcodes); break; // illegal + case 0x33:size = handle05_2f_3f_33_dasm(stream, pc, op, opcodes); break; // illegal + case 0x34:size = handle05_2f_3f_34_dasm(stream, pc, op, opcodes); break; // illegal + case 0x35:size = handle05_2f_3f_35_dasm(stream, pc, op, opcodes); break; // illegal + case 0x36:size = handle05_2f_3f_36_dasm(stream, pc, op, opcodes); break; // illegal + case 0x37:size = handle05_2f_3f_37_dasm(stream, pc, op, opcodes); break; // illegal + case 0x38:size = handle05_2f_3f_38_dasm(stream, pc, op, opcodes); break; // illegal + case 0x39:size = handle05_2f_3f_39_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3a:size = handle05_2f_3f_3a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3b:size = handle05_2f_3f_3b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3c:size = handle05_2f_3f_3c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3d:size = handle05_2f_3f_3d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3e:size = handle05_2f_3f_3e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3f:size = handle05_2f_3f_3f_dasm(stream, pc, op, opcodes); break; // illegal } return size; @@ -536,7 +533,7 @@ int arcompact_handle05_2f_3f_dasm(DASM_OPS_32) // useless ZOP group, no actual o // this is an Extension ALU group, maybe optional on some CPUs? -int arcompact_handle05_dasm(DASM_OPS_32) +int arcompact_disassembler::handle05_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { int size = 4; uint8_t subinstr = (op & 0x003f0000) >> 16; @@ -544,76 +541,76 @@ int arcompact_handle05_dasm(DASM_OPS_32) switch (subinstr) { - case 0x00: size = arcompact_handle05_00_dasm(DASM_PARAMS); break; // ASL - case 0x01: size = arcompact_handle05_01_dasm(DASM_PARAMS); break; // LSR - case 0x02: size = arcompact_handle05_02_dasm(DASM_PARAMS); break; // ASR - case 0x03: size = arcompact_handle05_03_dasm(DASM_PARAMS); break; // ROR - case 0x04: size = arcompact_handle05_04_dasm(DASM_PARAMS); break; // MUL64 - case 0x05: size = arcompact_handle05_05_dasm(DASM_PARAMS); break; // MULU64 - case 0x06: size = arcompact_handle05_06_dasm(DASM_PARAMS); break; // ADDS - case 0x07: size = arcompact_handle05_07_dasm(DASM_PARAMS); break; // SUBS - case 0x08: size = arcompact_handle05_08_dasm(DASM_PARAMS); break; // DIVAW - case 0x09: size = arcompact_handle05_09_dasm(DASM_PARAMS); break; // illegal - case 0x0a: size = arcompact_handle05_0a_dasm(DASM_PARAMS); break; // ASLS - case 0x0b: size = arcompact_handle05_0b_dasm(DASM_PARAMS); break; // ASRS - case 0x0c: size = arcompact_handle05_0c_dasm(DASM_PARAMS); break; // illegal - case 0x0d: size = arcompact_handle05_0d_dasm(DASM_PARAMS); break; // illegal - case 0x0e: size = arcompact_handle05_0e_dasm(DASM_PARAMS); break; // illegal - case 0x0f: size = arcompact_handle05_0f_dasm(DASM_PARAMS); break; // illegal - case 0x10: size = arcompact_handle05_10_dasm(DASM_PARAMS); break; // illegal - case 0x11: size = arcompact_handle05_11_dasm(DASM_PARAMS); break; // illegal - case 0x12: size = arcompact_handle05_12_dasm(DASM_PARAMS); break; // illegal - case 0x13: size = arcompact_handle05_13_dasm(DASM_PARAMS); break; // illegal - case 0x14: size = arcompact_handle05_14_dasm(DASM_PARAMS); break; // illegal - case 0x15: size = arcompact_handle05_15_dasm(DASM_PARAMS); break; // illegal - case 0x16: size = arcompact_handle05_16_dasm(DASM_PARAMS); break; // illegal - case 0x17: size = arcompact_handle05_17_dasm(DASM_PARAMS); break; // illegal - case 0x18: size = arcompact_handle05_18_dasm(DASM_PARAMS); break; // illegal - case 0x19: size = arcompact_handle05_19_dasm(DASM_PARAMS); break; // illegal - case 0x1a: size = arcompact_handle05_1a_dasm(DASM_PARAMS); break; // illegal - case 0x1b: size = arcompact_handle05_1b_dasm(DASM_PARAMS); break; // illegal - case 0x1c: size = arcompact_handle05_1c_dasm(DASM_PARAMS); break; // illegal - case 0x1d: size = arcompact_handle05_1d_dasm(DASM_PARAMS); break; // illegal - case 0x1e: size = arcompact_handle05_1e_dasm(DASM_PARAMS); break; // illegal - case 0x1f: size = arcompact_handle05_1f_dasm(DASM_PARAMS); break; // illegal - case 0x20: size = arcompact_handle05_20_dasm(DASM_PARAMS); break; // illegal - case 0x21: size = arcompact_handle05_21_dasm(DASM_PARAMS); break; // illegal - case 0x22: size = arcompact_handle05_22_dasm(DASM_PARAMS); break; // illegal - case 0x23: size = arcompact_handle05_23_dasm(DASM_PARAMS); break; // illegal - case 0x24: size = arcompact_handle05_24_dasm(DASM_PARAMS); break; // illegal - case 0x25: size = arcompact_handle05_25_dasm(DASM_PARAMS); break; // illegal - case 0x26: size = arcompact_handle05_26_dasm(DASM_PARAMS); break; // illegal - case 0x27: size = arcompact_handle05_27_dasm(DASM_PARAMS); break; // illegal - case 0x28: size = arcompact_handle05_28_dasm(DASM_PARAMS); break; // ADDSDW - case 0x29: size = arcompact_handle05_29_dasm(DASM_PARAMS); break; // SUBSDW - case 0x2a: size = arcompact_handle05_2a_dasm(DASM_PARAMS); break; // illegal - case 0x2b: size = arcompact_handle05_2b_dasm(DASM_PARAMS); break; // illegal - case 0x2c: size = arcompact_handle05_2c_dasm(DASM_PARAMS); break; // illegal - case 0x2d: size = arcompact_handle05_2d_dasm(DASM_PARAMS); break; // illegal - case 0x2e: size = arcompact_handle05_2e_dasm(DASM_PARAMS); break; // illegal - case 0x2f: size = arcompact_handle05_2f_dasm(DASM_PARAMS); break; // SOPs - case 0x30: size = arcompact_handle05_30_dasm(DASM_PARAMS); break; // illegal - case 0x31: size = arcompact_handle05_31_dasm(DASM_PARAMS); break; // illegal - case 0x32: size = arcompact_handle05_32_dasm(DASM_PARAMS); break; // illegal - case 0x33: size = arcompact_handle05_33_dasm(DASM_PARAMS); break; // illegal - case 0x34: size = arcompact_handle05_34_dasm(DASM_PARAMS); break; // illegal - case 0x35: size = arcompact_handle05_35_dasm(DASM_PARAMS); break; // illegal - case 0x36: size = arcompact_handle05_36_dasm(DASM_PARAMS); break; // illegal - case 0x37: size = arcompact_handle05_37_dasm(DASM_PARAMS); break; // illegal - case 0x38: size = arcompact_handle05_38_dasm(DASM_PARAMS); break; // illegal - case 0x39: size = arcompact_handle05_39_dasm(DASM_PARAMS); break; // illegal - case 0x3a: size = arcompact_handle05_3a_dasm(DASM_PARAMS); break; // illegal - case 0x3b: size = arcompact_handle05_3b_dasm(DASM_PARAMS); break; // illegal - case 0x3c: size = arcompact_handle05_3c_dasm(DASM_PARAMS); break; // illegal - case 0x3d: size = arcompact_handle05_3d_dasm(DASM_PARAMS); break; // illegal - case 0x3e: size = arcompact_handle05_3e_dasm(DASM_PARAMS); break; // illegal - case 0x3f: size = arcompact_handle05_3f_dasm(DASM_PARAMS); break; // illegal + case 0x00:size = handle05_00_dasm(stream, pc, op, opcodes); break; // ASL + case 0x01:size = handle05_01_dasm(stream, pc, op, opcodes); break; // LSR + case 0x02:size = handle05_02_dasm(stream, pc, op, opcodes); break; // ASR + case 0x03:size = handle05_03_dasm(stream, pc, op, opcodes); break; // ROR + case 0x04:size = handle05_04_dasm(stream, pc, op, opcodes); break; // MUL64 + case 0x05:size = handle05_05_dasm(stream, pc, op, opcodes); break; // MULU64 + case 0x06:size = handle05_06_dasm(stream, pc, op, opcodes); break; // ADDS + case 0x07:size = handle05_07_dasm(stream, pc, op, opcodes); break; // SUBS + case 0x08:size = handle05_08_dasm(stream, pc, op, opcodes); break; // DIVAW + case 0x09:size = handle05_09_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0a:size = handle05_0a_dasm(stream, pc, op, opcodes); break; // ASLS + case 0x0b:size = handle05_0b_dasm(stream, pc, op, opcodes); break; // ASRS + case 0x0c:size = handle05_0c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0d:size = handle05_0d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0e:size = handle05_0e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x0f:size = handle05_0f_dasm(stream, pc, op, opcodes); break; // illegal + case 0x10:size = handle05_10_dasm(stream, pc, op, opcodes); break; // illegal + case 0x11:size = handle05_11_dasm(stream, pc, op, opcodes); break; // illegal + case 0x12:size = handle05_12_dasm(stream, pc, op, opcodes); break; // illegal + case 0x13:size = handle05_13_dasm(stream, pc, op, opcodes); break; // illegal + case 0x14:size = handle05_14_dasm(stream, pc, op, opcodes); break; // illegal + case 0x15:size = handle05_15_dasm(stream, pc, op, opcodes); break; // illegal + case 0x16:size = handle05_16_dasm(stream, pc, op, opcodes); break; // illegal + case 0x17:size = handle05_17_dasm(stream, pc, op, opcodes); break; // illegal + case 0x18:size = handle05_18_dasm(stream, pc, op, opcodes); break; // illegal + case 0x19:size = handle05_19_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1a:size = handle05_1a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1b:size = handle05_1b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1c:size = handle05_1c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1d:size = handle05_1d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1e:size = handle05_1e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x1f:size = handle05_1f_dasm(stream, pc, op, opcodes); break; // illegal + case 0x20:size = handle05_20_dasm(stream, pc, op, opcodes); break; // illegal + case 0x21:size = handle05_21_dasm(stream, pc, op, opcodes); break; // illegal + case 0x22:size = handle05_22_dasm(stream, pc, op, opcodes); break; // illegal + case 0x23:size = handle05_23_dasm(stream, pc, op, opcodes); break; // illegal + case 0x24:size = handle05_24_dasm(stream, pc, op, opcodes); break; // illegal + case 0x25:size = handle05_25_dasm(stream, pc, op, opcodes); break; // illegal + case 0x26:size = handle05_26_dasm(stream, pc, op, opcodes); break; // illegal + case 0x27:size = handle05_27_dasm(stream, pc, op, opcodes); break; // illegal + case 0x28:size = handle05_28_dasm(stream, pc, op, opcodes); break; // ADDSDW + case 0x29:size = handle05_29_dasm(stream, pc, op, opcodes); break; // SUBSDW + case 0x2a:size = handle05_2a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2b:size = handle05_2b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2c:size = handle05_2c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2d:size = handle05_2d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2e:size = handle05_2e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x2f:size = handle05_2f_dasm(stream, pc, op, opcodes); break; // SOPs + case 0x30:size = handle05_30_dasm(stream, pc, op, opcodes); break; // illegal + case 0x31:size = handle05_31_dasm(stream, pc, op, opcodes); break; // illegal + case 0x32:size = handle05_32_dasm(stream, pc, op, opcodes); break; // illegal + case 0x33:size = handle05_33_dasm(stream, pc, op, opcodes); break; // illegal + case 0x34:size = handle05_34_dasm(stream, pc, op, opcodes); break; // illegal + case 0x35:size = handle05_35_dasm(stream, pc, op, opcodes); break; // illegal + case 0x36:size = handle05_36_dasm(stream, pc, op, opcodes); break; // illegal + case 0x37:size = handle05_37_dasm(stream, pc, op, opcodes); break; // illegal + case 0x38:size = handle05_38_dasm(stream, pc, op, opcodes); break; // illegal + case 0x39:size = handle05_39_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3a:size = handle05_3a_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3b:size = handle05_3b_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3c:size = handle05_3c_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3d:size = handle05_3d_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3e:size = handle05_3e_dasm(stream, pc, op, opcodes); break; // illegal + case 0x3f:size = handle05_3f_dasm(stream, pc, op, opcodes); break; // illegal } return size; } -int arcompact_handle0c_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0c_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int size = 2; uint8_t subinstr = (op & 0x0018) >> 3; @@ -621,15 +618,15 @@ int arcompact_handle0c_dasm(DASM_OPS_16) switch (subinstr) { - case 0x00: size = arcompact_handle0c_00_dasm(DASM_PARAMS); break; // LD_S - case 0x01: size = arcompact_handle0c_01_dasm(DASM_PARAMS); break; // LDB_S - case 0x02: size = arcompact_handle0c_02_dasm(DASM_PARAMS); break; // LDW_S - case 0x03: size = arcompact_handle0c_03_dasm(DASM_PARAMS); break; // ADD_S + case 0x00:size = handle0c_00_dasm(stream, pc, op, opcodes); break; // LD_S + case 0x01:size = handle0c_01_dasm(stream, pc, op, opcodes); break; // LDB_S + case 0x02:size = handle0c_02_dasm(stream, pc, op, opcodes); break; // LDW_S + case 0x03:size = handle0c_03_dasm(stream, pc, op, opcodes); break; // ADD_S } return size; } -int arcompact_handle0d_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0d_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int size = 2; uint8_t subinstr = (op & 0x0018) >> 3; @@ -637,15 +634,15 @@ int arcompact_handle0d_dasm(DASM_OPS_16) switch (subinstr) { - case 0x00: size = arcompact_handle0d_00_dasm(DASM_PARAMS); break; // ADD_S - case 0x01: size = arcompact_handle0d_01_dasm(DASM_PARAMS); break; // SUB_S - case 0x02: size = arcompact_handle0d_02_dasm(DASM_PARAMS); break; // ASL_S - case 0x03: size = arcompact_handle0d_03_dasm(DASM_PARAMS); break; // ASR_S + case 0x00:size = handle0d_00_dasm(stream, pc, op, opcodes); break; // ADD_S + case 0x01:size = handle0d_01_dasm(stream, pc, op, opcodes); break; // SUB_S + case 0x02:size = handle0d_02_dasm(stream, pc, op, opcodes); break; // ASL_S + case 0x03:size = handle0d_03_dasm(stream, pc, op, opcodes); break; // ASR_S } return size; } -int arcompact_handle0e_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0e_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int size = 2; uint8_t subinstr = (op & 0x0018) >> 3; @@ -653,15 +650,15 @@ int arcompact_handle0e_dasm(DASM_OPS_16) switch (subinstr) { - case 0x00: size = arcompact_handle0e_00_dasm(DASM_PARAMS); break; // ADD_S - case 0x01: size = arcompact_handle0e_01_dasm(DASM_PARAMS); break; // MOV_S - case 0x02: size = arcompact_handle0e_02_dasm(DASM_PARAMS); break; // CMP_S - case 0x03: size = arcompact_handle0e_03_dasm(DASM_PARAMS); break; // MOV_S + case 0x00:size = handle0e_00_dasm(stream, pc, op, opcodes); break; // ADD_S + case 0x01:size = handle0e_01_dasm(stream, pc, op, opcodes); break; // MOV_S + case 0x02:size = handle0e_02_dasm(stream, pc, op, opcodes); break; // CMP_S + case 0x03:size = handle0e_03_dasm(stream, pc, op, opcodes); break; // MOV_S } return size; } -int arcompact_handle0f_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0f_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int size = 2; // General Register Instructions (16-bit) @@ -671,44 +668,44 @@ int arcompact_handle0f_dasm(DASM_OPS_16) switch (subinstr) { - case 0x00: size = arcompact_handle0f_00_dasm(DASM_PARAMS); break; // SOPs - case 0x01: size = arcompact_handle0f_01_dasm(DASM_PARAMS); break; // 0x01 - case 0x02: size = arcompact_handle0f_02_dasm(DASM_PARAMS); break; // SUB_S - case 0x03: size = arcompact_handle0f_03_dasm(DASM_PARAMS); break; // 0x03 - case 0x04: size = arcompact_handle0f_04_dasm(DASM_PARAMS); break; // AND_S - case 0x05: size = arcompact_handle0f_05_dasm(DASM_PARAMS); break; // OR_S - case 0x06: size = arcompact_handle0f_06_dasm(DASM_PARAMS); break; // BIC_S - case 0x07: size = arcompact_handle0f_07_dasm(DASM_PARAMS); break; // XOR_S - case 0x08: size = arcompact_handle0f_08_dasm(DASM_PARAMS); break; // 0x08 - case 0x09: size = arcompact_handle0f_09_dasm(DASM_PARAMS); break; // 0x09 - case 0x0a: size = arcompact_handle0f_0a_dasm(DASM_PARAMS); break; // 0x0a - case 0x0b: size = arcompact_handle0f_0b_dasm(DASM_PARAMS); break; // TST_S - case 0x0c: size = arcompact_handle0f_0c_dasm(DASM_PARAMS); break; // MUL64_S - case 0x0d: size = arcompact_handle0f_0d_dasm(DASM_PARAMS); break; // SEXB_S - case 0x0e: size = arcompact_handle0f_0e_dasm(DASM_PARAMS); break; // SEXW_S - case 0x0f: size = arcompact_handle0f_0f_dasm(DASM_PARAMS); break; // EXTB_S - case 0x10: size = arcompact_handle0f_10_dasm(DASM_PARAMS); break; // EXTW_S - case 0x11: size = arcompact_handle0f_11_dasm(DASM_PARAMS); break; // ABS_S - case 0x12: size = arcompact_handle0f_12_dasm(DASM_PARAMS); break; // NOT_S - case 0x13: size = arcompact_handle0f_13_dasm(DASM_PARAMS); break; // NEG_S - case 0x14: size = arcompact_handle0f_14_dasm(DASM_PARAMS); break; // ADD1_S - case 0x15: size = arcompact_handle0f_15_dasm(DASM_PARAMS); break; // ADD2_S - case 0x16: size = arcompact_handle0f_16_dasm(DASM_PARAMS); break; // ADD3_S - case 0x17: size = arcompact_handle0f_17_dasm(DASM_PARAMS); break; // 0x17 - case 0x18: size = arcompact_handle0f_18_dasm(DASM_PARAMS); break; // ASL_S (multiple) - case 0x19: size = arcompact_handle0f_19_dasm(DASM_PARAMS); break; // LSR_S (multiple) - case 0x1a: size = arcompact_handle0f_1a_dasm(DASM_PARAMS); break; // ASR_S (multiple) - case 0x1b: size = arcompact_handle0f_1b_dasm(DASM_PARAMS); break; // ASL_S (single) - case 0x1c: size = arcompact_handle0f_1c_dasm(DASM_PARAMS); break; // LSR_S (single) - case 0x1d: size = arcompact_handle0f_1d_dasm(DASM_PARAMS); break; // ASR_S (single) - case 0x1e: size = arcompact_handle0f_1e_dasm(DASM_PARAMS); break; // TRAP (not a5?) - case 0x1f: size = arcompact_handle0f_1f_dasm(DASM_PARAMS); break; // BRK_S ( 0x7fff only? ) + case 0x00:size = handle0f_00_dasm(stream, pc, op, opcodes); break; // SOPs + case 0x01:size = handle0f_01_dasm(stream, pc, op, opcodes); break; // 0x01 + case 0x02:size = handle0f_02_dasm(stream, pc, op, opcodes); break; // SUB_S + case 0x03:size = handle0f_03_dasm(stream, pc, op, opcodes); break; // 0x03 + case 0x04:size = handle0f_04_dasm(stream, pc, op, opcodes); break; // AND_S + case 0x05:size = handle0f_05_dasm(stream, pc, op, opcodes); break; // OR_S + case 0x06:size = handle0f_06_dasm(stream, pc, op, opcodes); break; // BIC_S + case 0x07:size = handle0f_07_dasm(stream, pc, op, opcodes); break; // XOR_S + case 0x08:size = handle0f_08_dasm(stream, pc, op, opcodes); break; // 0x08 + case 0x09:size = handle0f_09_dasm(stream, pc, op, opcodes); break; // 0x09 + case 0x0a:size = handle0f_0a_dasm(stream, pc, op, opcodes); break; // 0x0a + case 0x0b:size = handle0f_0b_dasm(stream, pc, op, opcodes); break; // TST_S + case 0x0c:size = handle0f_0c_dasm(stream, pc, op, opcodes); break; // MUL64_S + case 0x0d:size = handle0f_0d_dasm(stream, pc, op, opcodes); break; // SEXB_S + case 0x0e:size = handle0f_0e_dasm(stream, pc, op, opcodes); break; // SEXW_S + case 0x0f:size = handle0f_0f_dasm(stream, pc, op, opcodes); break; // EXTB_S + case 0x10:size = handle0f_10_dasm(stream, pc, op, opcodes); break; // EXTW_S + case 0x11:size = handle0f_11_dasm(stream, pc, op, opcodes); break; // ABS_S + case 0x12:size = handle0f_12_dasm(stream, pc, op, opcodes); break; // NOT_S + case 0x13:size = handle0f_13_dasm(stream, pc, op, opcodes); break; // NEG_S + case 0x14:size = handle0f_14_dasm(stream, pc, op, opcodes); break; // ADD1_S + case 0x15:size = handle0f_15_dasm(stream, pc, op, opcodes); break; // ADD2_S + case 0x16:size = handle0f_16_dasm(stream, pc, op, opcodes); break; // ADD3_S + case 0x17:size = handle0f_17_dasm(stream, pc, op, opcodes); break; // 0x17 + case 0x18:size = handle0f_18_dasm(stream, pc, op, opcodes); break; // ASL_S (multiple) + case 0x19:size = handle0f_19_dasm(stream, pc, op, opcodes); break; // LSR_S (multiple) + case 0x1a:size = handle0f_1a_dasm(stream, pc, op, opcodes); break; // ASR_S (multiple) + case 0x1b:size = handle0f_1b_dasm(stream, pc, op, opcodes); break; // ASL_S (single) + case 0x1c:size = handle0f_1c_dasm(stream, pc, op, opcodes); break; // LSR_S (single) + case 0x1d:size = handle0f_1d_dasm(stream, pc, op, opcodes); break; // ASR_S (single) + case 0x1e:size = handle0f_1e_dasm(stream, pc, op, opcodes); break; // TRAP (not a5?) + case 0x1f:size = handle0f_1f_dasm(stream, pc, op, opcodes); break; // BRK_S ( 0x7fff only? ) } return size; } -int arcompact_handle0f_00_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0f_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int size = 2; uint8_t subinstr = (op & 0x00e0) >> 5; @@ -716,21 +713,21 @@ int arcompact_handle0f_00_dasm(DASM_OPS_16) switch (subinstr) { - case 0x00: size = arcompact_handle0f_00_00_dasm(DASM_PARAMS); break; // J_S - case 0x01: size = arcompact_handle0f_00_01_dasm(DASM_PARAMS); break; // J_S.D - case 0x02: size = arcompact_handle0f_00_02_dasm(DASM_PARAMS); break; // JL_S - case 0x03: size = arcompact_handle0f_00_03_dasm(DASM_PARAMS); break; // JL_S.D - case 0x04: size = arcompact_handle0f_00_04_dasm(DASM_PARAMS); break; // 0x04 - case 0x05: size = arcompact_handle0f_00_05_dasm(DASM_PARAMS); break; // 0x05 - case 0x06: size = arcompact_handle0f_00_06_dasm(DASM_PARAMS); break; // SUB_S.NE - case 0x07: size = arcompact_handle0f_00_07_dasm(DASM_PARAMS); break; // ZOPs + case 0x00:size = handle0f_00_00_dasm(stream, pc, op, opcodes); break; // J_S + case 0x01:size = handle0f_00_01_dasm(stream, pc, op, opcodes); break; // J_S.D + case 0x02:size = handle0f_00_02_dasm(stream, pc, op, opcodes); break; // JL_S + case 0x03:size = handle0f_00_03_dasm(stream, pc, op, opcodes); break; // JL_S.D + case 0x04:size = handle0f_00_04_dasm(stream, pc, op, opcodes); break; // 0x04 + case 0x05:size = handle0f_00_05_dasm(stream, pc, op, opcodes); break; // 0x05 + case 0x06:size = handle0f_00_06_dasm(stream, pc, op, opcodes); break; // SUB_S.NE + case 0x07:size = handle0f_00_07_dasm(stream, pc, op, opcodes); break; // ZOPs } return size; } -int arcompact_handle0f_00_07_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0f_00_07_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int size = 2; // General Operations w/o Register @@ -740,20 +737,20 @@ int arcompact_handle0f_00_07_dasm(DASM_OPS_16) switch (subinstr3) { - case 0x00: size = arcompact_handle0f_00_07_00_dasm(DASM_PARAMS); break; // NOP_S - case 0x01: size = arcompact_handle0f_00_07_01_dasm(DASM_PARAMS); break; // UNIMP_S - case 0x02: size = arcompact_handle0f_00_07_02_dasm(DASM_PARAMS); break; // 0x02 - case 0x03: size = arcompact_handle0f_00_07_03_dasm(DASM_PARAMS); break; // 0x03 - case 0x04: size = arcompact_handle0f_00_07_04_dasm(DASM_PARAMS); break; // JEQ_S [BLINK] - case 0x05: size = arcompact_handle0f_00_07_05_dasm(DASM_PARAMS); break; // JNE_S [BLINK] - case 0x06: size = arcompact_handle0f_00_07_06_dasm(DASM_PARAMS); break; // J_S [BLINK] - case 0x07: size = arcompact_handle0f_00_07_07_dasm(DASM_PARAMS); break; // J_S.D [BLINK] + case 0x00:size = handle0f_00_07_00_dasm(stream, pc, op, opcodes); break; // NOP_S + case 0x01:size = handle0f_00_07_01_dasm(stream, pc, op, opcodes); break; // UNIMP_S + case 0x02:size = handle0f_00_07_02_dasm(stream, pc, op, opcodes); break; // 0x02 + case 0x03:size = handle0f_00_07_03_dasm(stream, pc, op, opcodes); break; // 0x03 + case 0x04:size = handle0f_00_07_04_dasm(stream, pc, op, opcodes); break; // JEQ_S [BLINK] + case 0x05:size = handle0f_00_07_05_dasm(stream, pc, op, opcodes); break; // JNE_S [BLINK] + case 0x06:size = handle0f_00_07_06_dasm(stream, pc, op, opcodes); break; // J_S [BLINK] + case 0x07:size = handle0f_00_07_07_dasm(stream, pc, op, opcodes); break; // J_S.D [BLINK] } return size; } -int arcompact_handle17_dasm(DASM_OPS_16) +int arcompact_disassembler::handle17_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int size = 2; uint8_t subinstr = (op & 0x00e0) >> 5; @@ -761,20 +758,20 @@ int arcompact_handle17_dasm(DASM_OPS_16) switch (subinstr) { - case 0x00: size = arcompact_handle17_00_dasm(DASM_PARAMS); break; // ASL_S - case 0x01: size = arcompact_handle17_01_dasm(DASM_PARAMS); break; // LSR_S - case 0x02: size = arcompact_handle17_02_dasm(DASM_PARAMS); break; // ASR_S - case 0x03: size = arcompact_handle17_03_dasm(DASM_PARAMS); break; // SUB_S - case 0x04: size = arcompact_handle17_04_dasm(DASM_PARAMS); break; // BSET_S - case 0x05: size = arcompact_handle17_05_dasm(DASM_PARAMS); break; // BCLR_S - case 0x06: size = arcompact_handle17_06_dasm(DASM_PARAMS); break; // BMSK_S - case 0x07: size = arcompact_handle17_07_dasm(DASM_PARAMS); break; // BTST_S + case 0x00:size = handle17_00_dasm(stream, pc, op, opcodes); break; // ASL_S + case 0x01:size = handle17_01_dasm(stream, pc, op, opcodes); break; // LSR_S + case 0x02:size = handle17_02_dasm(stream, pc, op, opcodes); break; // ASR_S + case 0x03:size = handle17_03_dasm(stream, pc, op, opcodes); break; // SUB_S + case 0x04:size = handle17_04_dasm(stream, pc, op, opcodes); break; // BSET_S + case 0x05:size = handle17_05_dasm(stream, pc, op, opcodes); break; // BCLR_S + case 0x06:size = handle17_06_dasm(stream, pc, op, opcodes); break; // BMSK_S + case 0x07:size = handle17_07_dasm(stream, pc, op, opcodes); break; // BTST_S } return size; } -int arcompact_handle18_dasm(DASM_OPS_16) +int arcompact_disassembler::handle18_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int size = 2; // Stack Pointer Based Instructions (16-bit) @@ -784,20 +781,20 @@ int arcompact_handle18_dasm(DASM_OPS_16) switch (subinstr) { - case 0x00: size = arcompact_handle18_00_dasm(DASM_PARAMS); break; // LD_S (SP) - case 0x01: size = arcompact_handle18_01_dasm(DASM_PARAMS); break; // LDB_S (SP) - case 0x02: size = arcompact_handle18_02_dasm(DASM_PARAMS); break; // ST_S (SP) - case 0x03: size = arcompact_handle18_03_dasm(DASM_PARAMS); break; // STB_S (SP) - case 0x04: size = arcompact_handle18_04_dasm(DASM_PARAMS); break; // ADD_S (SP) - case 0x05: size = arcompact_handle18_05_dasm(DASM_PARAMS); break; // subtable 18_05 - case 0x06: size = arcompact_handle18_06_dasm(DASM_PARAMS); break; // subtable 18_06 - case 0x07: size = arcompact_handle18_07_dasm(DASM_PARAMS); break; // subtable 18_07 + case 0x00:size = handle18_00_dasm(stream, pc, op, opcodes); break; // LD_S (SP) + case 0x01:size = handle18_01_dasm(stream, pc, op, opcodes); break; // LDB_S (SP) + case 0x02:size = handle18_02_dasm(stream, pc, op, opcodes); break; // ST_S (SP) + case 0x03:size = handle18_03_dasm(stream, pc, op, opcodes); break; // STB_S (SP) + case 0x04:size = handle18_04_dasm(stream, pc, op, opcodes); break; // ADD_S (SP) + case 0x05:size = handle18_05_dasm(stream, pc, op, opcodes); break; // subtable 18_05 + case 0x06:size = handle18_06_dasm(stream, pc, op, opcodes); break; // subtable 18_06 + case 0x07:size = handle18_07_dasm(stream, pc, op, opcodes); break; // subtable 18_07 } return size; } -int arcompact_handle18_05_dasm(DASM_OPS_16) +int arcompact_disassembler::handle18_05_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int size = 2; uint8_t subinstr2 = (op & 0x0700) >> 8; @@ -805,20 +802,20 @@ int arcompact_handle18_05_dasm(DASM_OPS_16) switch (subinstr2) { - case 0x00: size = arcompact_handle18_05_00_dasm(DASM_PARAMS); break; // ADD_S (SP) - case 0x01: size = arcompact_handle18_05_01_dasm(DASM_PARAMS); break; // SUB_S (SP) - case 0x02: size = arcompact_handle18_05_02_dasm(DASM_PARAMS); break; // - case 0x03: size = arcompact_handle18_05_03_dasm(DASM_PARAMS); break; // - case 0x04: size = arcompact_handle18_05_04_dasm(DASM_PARAMS); break; // - case 0x05: size = arcompact_handle18_05_05_dasm(DASM_PARAMS); break; // - case 0x06: size = arcompact_handle18_05_06_dasm(DASM_PARAMS); break; // - case 0x07: size = arcompact_handle18_05_07_dasm(DASM_PARAMS); break; // + case 0x00:size = handle18_05_00_dasm(stream, pc, op, opcodes); break; // ADD_S (SP) + case 0x01:size = handle18_05_01_dasm(stream, pc, op, opcodes); break; // SUB_S (SP) + case 0x02:size = handle18_05_02_dasm(stream, pc, op, opcodes); break; // + case 0x03:size = handle18_05_03_dasm(stream, pc, op, opcodes); break; // + case 0x04:size = handle18_05_04_dasm(stream, pc, op, opcodes); break; // + case 0x05:size = handle18_05_05_dasm(stream, pc, op, opcodes); break; // + case 0x06:size = handle18_05_06_dasm(stream, pc, op, opcodes); break; // + case 0x07:size = handle18_05_07_dasm(stream, pc, op, opcodes); break; // } return size; } -int arcompact_handle18_06_dasm(DASM_OPS_16) +int arcompact_disassembler::handle18_06_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int size = 2; uint8_t subinstr2 = (op & 0x001f) >> 0; @@ -826,44 +823,44 @@ int arcompact_handle18_06_dasm(DASM_OPS_16) switch (subinstr2) { - case 0x00: size = arcompact_handle18_06_00_dasm(DASM_PARAMS); break; // - case 0x01: size = arcompact_handle18_06_01_dasm(DASM_PARAMS); break; // POP_S b - case 0x02: size = arcompact_handle18_06_02_dasm(DASM_PARAMS); break; // - case 0x03: size = arcompact_handle18_06_03_dasm(DASM_PARAMS); break; // - case 0x04: size = arcompact_handle18_06_04_dasm(DASM_PARAMS); break; // - case 0x05: size = arcompact_handle18_06_05_dasm(DASM_PARAMS); break; // - case 0x06: size = arcompact_handle18_06_06_dasm(DASM_PARAMS); break; // - case 0x07: size = arcompact_handle18_06_07_dasm(DASM_PARAMS); break; // - case 0x08: size = arcompact_handle18_06_08_dasm(DASM_PARAMS); break; // - case 0x09: size = arcompact_handle18_06_09_dasm(DASM_PARAMS); break; // - case 0x0a: size = arcompact_handle18_06_0a_dasm(DASM_PARAMS); break; // - case 0x0b: size = arcompact_handle18_06_0b_dasm(DASM_PARAMS); break; // - case 0x0c: size = arcompact_handle18_06_0c_dasm(DASM_PARAMS); break; // - case 0x0d: size = arcompact_handle18_06_0d_dasm(DASM_PARAMS); break; // - case 0x0e: size = arcompact_handle18_06_0e_dasm(DASM_PARAMS); break; // - case 0x0f: size = arcompact_handle18_06_0f_dasm(DASM_PARAMS); break; // - case 0x10: size = arcompact_handle18_06_10_dasm(DASM_PARAMS); break; // - case 0x11: size = arcompact_handle18_06_11_dasm(DASM_PARAMS); break; // POP_S blink - case 0x12: size = arcompact_handle18_06_12_dasm(DASM_PARAMS); break; // - case 0x13: size = arcompact_handle18_06_13_dasm(DASM_PARAMS); break; // - case 0x14: size = arcompact_handle18_06_14_dasm(DASM_PARAMS); break; // - case 0x15: size = arcompact_handle18_06_15_dasm(DASM_PARAMS); break; // - case 0x16: size = arcompact_handle18_06_16_dasm(DASM_PARAMS); break; // - case 0x17: size = arcompact_handle18_06_17_dasm(DASM_PARAMS); break; // - case 0x18: size = arcompact_handle18_06_18_dasm(DASM_PARAMS); break; // - case 0x19: size = arcompact_handle18_06_19_dasm(DASM_PARAMS); break; // - case 0x1a: size = arcompact_handle18_06_1a_dasm(DASM_PARAMS); break; // - case 0x1b: size = arcompact_handle18_06_1b_dasm(DASM_PARAMS); break; // - case 0x1c: size = arcompact_handle18_06_1c_dasm(DASM_PARAMS); break; // - case 0x1d: size = arcompact_handle18_06_1d_dasm(DASM_PARAMS); break; // - case 0x1e: size = arcompact_handle18_06_1e_dasm(DASM_PARAMS); break; // - case 0x1f: size = arcompact_handle18_06_1f_dasm(DASM_PARAMS); break; // + case 0x00:size = handle18_06_00_dasm(stream, pc, op, opcodes); break; // + case 0x01:size = handle18_06_01_dasm(stream, pc, op, opcodes); break; // POP_S b + case 0x02:size = handle18_06_02_dasm(stream, pc, op, opcodes); break; // + case 0x03:size = handle18_06_03_dasm(stream, pc, op, opcodes); break; // + case 0x04:size = handle18_06_04_dasm(stream, pc, op, opcodes); break; // + case 0x05:size = handle18_06_05_dasm(stream, pc, op, opcodes); break; // + case 0x06:size = handle18_06_06_dasm(stream, pc, op, opcodes); break; // + case 0x07:size = handle18_06_07_dasm(stream, pc, op, opcodes); break; // + case 0x08:size = handle18_06_08_dasm(stream, pc, op, opcodes); break; // + case 0x09:size = handle18_06_09_dasm(stream, pc, op, opcodes); break; // + case 0x0a:size = handle18_06_0a_dasm(stream, pc, op, opcodes); break; // + case 0x0b:size = handle18_06_0b_dasm(stream, pc, op, opcodes); break; // + case 0x0c:size = handle18_06_0c_dasm(stream, pc, op, opcodes); break; // + case 0x0d:size = handle18_06_0d_dasm(stream, pc, op, opcodes); break; // + case 0x0e:size = handle18_06_0e_dasm(stream, pc, op, opcodes); break; // + case 0x0f:size = handle18_06_0f_dasm(stream, pc, op, opcodes); break; // + case 0x10:size = handle18_06_10_dasm(stream, pc, op, opcodes); break; // + case 0x11:size = handle18_06_11_dasm(stream, pc, op, opcodes); break; // POP_S blink + case 0x12:size = handle18_06_12_dasm(stream, pc, op, opcodes); break; // + case 0x13:size = handle18_06_13_dasm(stream, pc, op, opcodes); break; // + case 0x14:size = handle18_06_14_dasm(stream, pc, op, opcodes); break; // + case 0x15:size = handle18_06_15_dasm(stream, pc, op, opcodes); break; // + case 0x16:size = handle18_06_16_dasm(stream, pc, op, opcodes); break; // + case 0x17:size = handle18_06_17_dasm(stream, pc, op, opcodes); break; // + case 0x18:size = handle18_06_18_dasm(stream, pc, op, opcodes); break; // + case 0x19:size = handle18_06_19_dasm(stream, pc, op, opcodes); break; // + case 0x1a:size = handle18_06_1a_dasm(stream, pc, op, opcodes); break; // + case 0x1b:size = handle18_06_1b_dasm(stream, pc, op, opcodes); break; // + case 0x1c:size = handle18_06_1c_dasm(stream, pc, op, opcodes); break; // + case 0x1d:size = handle18_06_1d_dasm(stream, pc, op, opcodes); break; // + case 0x1e:size = handle18_06_1e_dasm(stream, pc, op, opcodes); break; // + case 0x1f:size = handle18_06_1f_dasm(stream, pc, op, opcodes); break; // } return size; } -int arcompact_handle18_07_dasm(DASM_OPS_16) +int arcompact_disassembler::handle18_07_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int size = 2; uint8_t subinstr2 = (op & 0x001f) >> 0; @@ -871,44 +868,44 @@ int arcompact_handle18_07_dasm(DASM_OPS_16) switch (subinstr2) { - case 0x00: size = arcompact_handle18_07_00_dasm(DASM_PARAMS); break; // - case 0x01: size = arcompact_handle18_07_01_dasm(DASM_PARAMS); break; // PUSH_S b - case 0x02: size = arcompact_handle18_07_02_dasm(DASM_PARAMS); break; // - case 0x03: size = arcompact_handle18_07_03_dasm(DASM_PARAMS); break; // - case 0x04: size = arcompact_handle18_07_04_dasm(DASM_PARAMS); break; // - case 0x05: size = arcompact_handle18_07_05_dasm(DASM_PARAMS); break; // - case 0x06: size = arcompact_handle18_07_06_dasm(DASM_PARAMS); break; // - case 0x07: size = arcompact_handle18_07_07_dasm(DASM_PARAMS); break; // - case 0x08: size = arcompact_handle18_07_08_dasm(DASM_PARAMS); break; // - case 0x09: size = arcompact_handle18_07_09_dasm(DASM_PARAMS); break; // - case 0x0a: size = arcompact_handle18_07_0a_dasm(DASM_PARAMS); break; // - case 0x0b: size = arcompact_handle18_07_0b_dasm(DASM_PARAMS); break; // - case 0x0c: size = arcompact_handle18_07_0c_dasm(DASM_PARAMS); break; // - case 0x0d: size = arcompact_handle18_07_0d_dasm(DASM_PARAMS); break; // - case 0x0e: size = arcompact_handle18_07_0e_dasm(DASM_PARAMS); break; // - case 0x0f: size = arcompact_handle18_07_0f_dasm(DASM_PARAMS); break; // - case 0x10: size = arcompact_handle18_07_10_dasm(DASM_PARAMS); break; // - case 0x11: size = arcompact_handle18_07_11_dasm(DASM_PARAMS); break; // PUSH_S blink - case 0x12: size = arcompact_handle18_07_12_dasm(DASM_PARAMS); break; // - case 0x13: size = arcompact_handle18_07_13_dasm(DASM_PARAMS); break; // - case 0x14: size = arcompact_handle18_07_14_dasm(DASM_PARAMS); break; // - case 0x15: size = arcompact_handle18_07_15_dasm(DASM_PARAMS); break; // - case 0x16: size = arcompact_handle18_07_16_dasm(DASM_PARAMS); break; // - case 0x17: size = arcompact_handle18_07_17_dasm(DASM_PARAMS); break; // - case 0x18: size = arcompact_handle18_07_18_dasm(DASM_PARAMS); break; // - case 0x19: size = arcompact_handle18_07_19_dasm(DASM_PARAMS); break; // - case 0x1a: size = arcompact_handle18_07_1a_dasm(DASM_PARAMS); break; // - case 0x1b: size = arcompact_handle18_07_1b_dasm(DASM_PARAMS); break; // - case 0x1c: size = arcompact_handle18_07_1c_dasm(DASM_PARAMS); break; // - case 0x1d: size = arcompact_handle18_07_1d_dasm(DASM_PARAMS); break; // - case 0x1e: size = arcompact_handle18_07_1e_dasm(DASM_PARAMS); break; // - case 0x1f: size = arcompact_handle18_07_1f_dasm(DASM_PARAMS); break; // + case 0x00:size = handle18_07_00_dasm(stream, pc, op, opcodes); break; // + case 0x01:size = handle18_07_01_dasm(stream, pc, op, opcodes); break; // PUSH_S b + case 0x02:size = handle18_07_02_dasm(stream, pc, op, opcodes); break; // + case 0x03:size = handle18_07_03_dasm(stream, pc, op, opcodes); break; // + case 0x04:size = handle18_07_04_dasm(stream, pc, op, opcodes); break; // + case 0x05:size = handle18_07_05_dasm(stream, pc, op, opcodes); break; // + case 0x06:size = handle18_07_06_dasm(stream, pc, op, opcodes); break; // + case 0x07:size = handle18_07_07_dasm(stream, pc, op, opcodes); break; // + case 0x08:size = handle18_07_08_dasm(stream, pc, op, opcodes); break; // + case 0x09:size = handle18_07_09_dasm(stream, pc, op, opcodes); break; // + case 0x0a:size = handle18_07_0a_dasm(stream, pc, op, opcodes); break; // + case 0x0b:size = handle18_07_0b_dasm(stream, pc, op, opcodes); break; // + case 0x0c:size = handle18_07_0c_dasm(stream, pc, op, opcodes); break; // + case 0x0d:size = handle18_07_0d_dasm(stream, pc, op, opcodes); break; // + case 0x0e:size = handle18_07_0e_dasm(stream, pc, op, opcodes); break; // + case 0x0f:size = handle18_07_0f_dasm(stream, pc, op, opcodes); break; // + case 0x10:size = handle18_07_10_dasm(stream, pc, op, opcodes); break; // + case 0x11:size = handle18_07_11_dasm(stream, pc, op, opcodes); break; // PUSH_S blink + case 0x12:size = handle18_07_12_dasm(stream, pc, op, opcodes); break; // + case 0x13:size = handle18_07_13_dasm(stream, pc, op, opcodes); break; // + case 0x14:size = handle18_07_14_dasm(stream, pc, op, opcodes); break; // + case 0x15:size = handle18_07_15_dasm(stream, pc, op, opcodes); break; // + case 0x16:size = handle18_07_16_dasm(stream, pc, op, opcodes); break; // + case 0x17:size = handle18_07_17_dasm(stream, pc, op, opcodes); break; // + case 0x18:size = handle18_07_18_dasm(stream, pc, op, opcodes); break; // + case 0x19:size = handle18_07_19_dasm(stream, pc, op, opcodes); break; // + case 0x1a:size = handle18_07_1a_dasm(stream, pc, op, opcodes); break; // + case 0x1b:size = handle18_07_1b_dasm(stream, pc, op, opcodes); break; // + case 0x1c:size = handle18_07_1c_dasm(stream, pc, op, opcodes); break; // + case 0x1d:size = handle18_07_1d_dasm(stream, pc, op, opcodes); break; // + case 0x1e:size = handle18_07_1e_dasm(stream, pc, op, opcodes); break; // + case 0x1f:size = handle18_07_1f_dasm(stream, pc, op, opcodes); break; // } return size; } -int arcompact_handle19_dasm(DASM_OPS_16) +int arcompact_disassembler::handle19_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int size = 2; uint8_t subinstr = (op & 0x0600) >> 9; @@ -916,15 +913,15 @@ int arcompact_handle19_dasm(DASM_OPS_16) switch (subinstr) { - case 0x00: size = arcompact_handle19_00_dasm(DASM_PARAMS); break; // LD_S (GP) - case 0x01: size = arcompact_handle19_01_dasm(DASM_PARAMS); break; // LDB_S (GP) - case 0x02: size = arcompact_handle19_02_dasm(DASM_PARAMS); break; // LDW_S (GP) - case 0x03: size = arcompact_handle19_03_dasm(DASM_PARAMS); break; // ADD_S (GP) + case 0x00:size = handle19_00_dasm(stream, pc, op, opcodes); break; // LD_S (GP) + case 0x01:size = handle19_01_dasm(stream, pc, op, opcodes); break; // LDB_S (GP) + case 0x02:size = handle19_02_dasm(stream, pc, op, opcodes); break; // LDW_S (GP) + case 0x03:size = handle19_03_dasm(stream, pc, op, opcodes); break; // ADD_S (GP) } return size; } -int arcompact_handle1c_dasm(DASM_OPS_16) +int arcompact_disassembler::handle1c_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int size = 2; uint8_t subinstr = (op & 0x0080) >> 7; @@ -932,13 +929,13 @@ int arcompact_handle1c_dasm(DASM_OPS_16) switch (subinstr) { - case 0x00: size = arcompact_handle1c_00_dasm(DASM_PARAMS); break; // ADD_S - case 0x01: size = arcompact_handle1c_01_dasm(DASM_PARAMS); break; // CMP_S + case 0x00:size = handle1c_00_dasm(stream, pc, op, opcodes); break; // ADD_S + case 0x01:size = handle1c_01_dasm(stream, pc, op, opcodes); break; // CMP_S } return size; } -int arcompact_handle1d_dasm(DASM_OPS_16) +int arcompact_disassembler::handle1d_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int size = 2; uint8_t subinstr = (op & 0x0080) >> 7; @@ -946,13 +943,13 @@ int arcompact_handle1d_dasm(DASM_OPS_16) switch (subinstr) { - case 0x00: size = arcompact_handle1d_00_dasm(DASM_PARAMS); break; // BREQ_S - case 0x01: size = arcompact_handle1d_01_dasm(DASM_PARAMS); break; // BRNE_S + case 0x00:size = handle1d_00_dasm(stream, pc, op, opcodes); break; // BREQ_S + case 0x01:size = handle1d_01_dasm(stream, pc, op, opcodes); break; // BRNE_S } return size; } -int arcompact_handle1e_dasm(DASM_OPS_16) +int arcompact_disassembler::handle1e_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int size = 2; uint8_t subinstr = (op & 0x0600) >> 9; @@ -960,15 +957,15 @@ int arcompact_handle1e_dasm(DASM_OPS_16) switch (subinstr) { - case 0x00: size = arcompact_handle1e_00_dasm(DASM_PARAMS); break; // B_S - case 0x01: size = arcompact_handle1e_01_dasm(DASM_PARAMS); break; // BEQ_S - case 0x02: size = arcompact_handle1e_02_dasm(DASM_PARAMS); break; // BNE_S - case 0x03: size = arcompact_handle1e_03_dasm(DASM_PARAMS); break; // Bcc_S + case 0x00:size = handle1e_00_dasm(stream, pc, op, opcodes); break; // B_S + case 0x01:size = handle1e_01_dasm(stream, pc, op, opcodes); break; // BEQ_S + case 0x02:size = handle1e_02_dasm(stream, pc, op, opcodes); break; // BNE_S + case 0x03:size = handle1e_03_dasm(stream, pc, op, opcodes); break; // Bcc_S } return size; } -int arcompact_handle1e_03_dasm(DASM_OPS_16) +int arcompact_disassembler::handle1e_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int size = 2; uint8_t subinstr2 = (op & 0x01c0) >> 6; @@ -976,14 +973,14 @@ int arcompact_handle1e_03_dasm(DASM_OPS_16) switch (subinstr2) { - case 0x00: size = arcompact_handle1e_03_00_dasm(DASM_PARAMS); break; // BGT_S - case 0x01: size = arcompact_handle1e_03_01_dasm(DASM_PARAMS); break; // BGE_S - case 0x02: size = arcompact_handle1e_03_02_dasm(DASM_PARAMS); break; // BLT_S - case 0x03: size = arcompact_handle1e_03_03_dasm(DASM_PARAMS); break; // BLE_S - case 0x04: size = arcompact_handle1e_03_04_dasm(DASM_PARAMS); break; // BHI_S - case 0x05: size = arcompact_handle1e_03_05_dasm(DASM_PARAMS); break; // BHS_S - case 0x06: size = arcompact_handle1e_03_06_dasm(DASM_PARAMS); break; // BLO_S - case 0x07: size = arcompact_handle1e_03_07_dasm(DASM_PARAMS); break; // BLS_S + case 0x00:size = handle1e_03_00_dasm(stream, pc, op, opcodes); break; // BGT_S + case 0x01:size = handle1e_03_01_dasm(stream, pc, op, opcodes); break; // BGE_S + case 0x02:size = handle1e_03_02_dasm(stream, pc, op, opcodes); break; // BLT_S + case 0x03:size = handle1e_03_03_dasm(stream, pc, op, opcodes); break; // BLE_S + case 0x04:size = handle1e_03_04_dasm(stream, pc, op, opcodes); break; // BHI_S + case 0x05:size = handle1e_03_05_dasm(stream, pc, op, opcodes); break; // BHS_S + case 0x06:size = handle1e_03_06_dasm(stream, pc, op, opcodes); break; // BLO_S + case 0x07:size = handle1e_03_07_dasm(stream, pc, op, opcodes); break; // BLS_S } return size; diff --git a/src/devices/cpu/arcompact/arcompactdasm_dispatch.h b/src/devices/cpu/arcompact/arcompactdasm_dispatch.h deleted file mode 100644 index 519f4b7ae4e..00000000000 --- a/src/devices/cpu/arcompact/arcompactdasm_dispatch.h +++ /dev/null @@ -1,50 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:David Haywood -/*********************************\ - - ARCompact disassembler - -\*********************************/ - -#define DASM_OPS_16 std::ostream &stream, offs_t pc, uint16_t op, const uint8_t* oprom -#define DASM_OPS_32 std::ostream &stream, offs_t pc, uint32_t op, const uint8_t* oprom -#define DASM_PARAMS stream, pc, op, oprom - -#define LIMM_REG 62 - -#define GET_LIMM_32 \ - limm = oprom[6] | (oprom[7] << 8); \ - limm |= (oprom[4] << 16) | (oprom[5] << 24); - - -int arcompact_handle00_dasm(DASM_OPS_32); -int arcompact_handle01_dasm(DASM_OPS_32); -int arcompact_handle01_00_dasm(DASM_OPS_32); -int arcompact_handle01_01_dasm(DASM_OPS_32); -int arcompact_handle01_01_00_dasm(DASM_OPS_32); -int arcompact_handle01_01_01_dasm(DASM_OPS_32); -int arcompact_handle04_dasm(DASM_OPS_32); -int arcompact_handle04_2f_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_dasm(DASM_OPS_32); -int arcompact_handle05_dasm(DASM_OPS_32); - -int arcompact_handle05_2f_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_dasm(DASM_OPS_32); - - -int arcompact_handle0c_dasm(DASM_OPS_16); -int arcompact_handle0d_dasm(DASM_OPS_16); -int arcompact_handle0e_dasm(DASM_OPS_16); -int arcompact_handle0f_dasm(DASM_OPS_16); -int arcompact_handle0f_00_dasm(DASM_OPS_16); -int arcompact_handle0f_00_07_dasm(DASM_OPS_16); -int arcompact_handle17_dasm(DASM_OPS_16); -int arcompact_handle18_dasm(DASM_OPS_16); -int arcompact_handle18_05_dasm(DASM_OPS_16); -int arcompact_handle18_06_dasm(DASM_OPS_16); -int arcompact_handle18_07_dasm(DASM_OPS_16); -int arcompact_handle19_dasm(DASM_OPS_16); -int arcompact_handle1c_dasm(DASM_OPS_16); -int arcompact_handle1d_dasm(DASM_OPS_16); -int arcompact_handle1e_dasm(DASM_OPS_16); -int arcompact_handle1e_03_dasm(DASM_OPS_16); diff --git a/src/devices/cpu/arcompact/arcompactdasm_ops.cpp b/src/devices/cpu/arcompact/arcompactdasm_ops.cpp index dd214e0cb02..dadc0f856a4 100644 --- a/src/devices/cpu/arcompact/arcompactdasm_ops.cpp +++ b/src/devices/cpu/arcompact/arcompactdasm_ops.cpp @@ -7,9 +7,8 @@ \*********************************/ #include "emu.h" -#include -#include "arcompactdasm_ops.h" +#include "arcompactdasm.h" #define GET_01_01_01_BRANCH_ADDR \ int32_t address = (op & 0x00fe0000) >> 17; \ @@ -79,9 +78,9 @@ // this is as messed up as the rest of the 16-bit alignment in LE mode... +#define LIMM_REG 62 #define GET_LIMM \ - limm = oprom[4] | (oprom[5] << 8); \ - limm |= (oprom[2] << 16) | (oprom[3] << 24); + limm = opcodes.r32(pc+2); #define PC_ALIGNED32 \ (pc&0xfffffffc) @@ -92,7 +91,7 @@ * * ************************************************************************************************************************************/ -int arcompact_handle00_00_dasm(DASM_OPS_32) +int arcompact_disassembler::handle00_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { int size = 4; // Branch Conditionally @@ -107,7 +106,7 @@ int arcompact_handle00_00_dasm(DASM_OPS_32) return size; } -int arcompact_handle00_01_dasm(DASM_OPS_32) +int arcompact_disassembler::handle00_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { int size = 4; // Branch Unconditionally Far @@ -125,7 +124,7 @@ int arcompact_handle00_01_dasm(DASM_OPS_32) return size; } -int arcompact_handle01_00_00dasm(DASM_OPS_32) +int arcompact_disassembler::handle01_00_00dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { int size = 4; @@ -142,7 +141,7 @@ int arcompact_handle01_00_00dasm(DASM_OPS_32) return size; } -int arcompact_handle01_00_01dasm(DASM_OPS_32) +int arcompact_disassembler::handle01_00_01dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { int size = 4; // Branch and Link Unconditionally Far @@ -162,7 +161,7 @@ int arcompact_handle01_00_01dasm(DASM_OPS_32) -int arcompact_01_01_00_helper(DASM_OPS_32, const char* optext) +int arcompact_disassembler::handle01_01_00_helper(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext) { int size = 4; @@ -184,7 +183,7 @@ int arcompact_01_01_00_helper(DASM_OPS_32, const char* optext) else { uint32_t limm; - GET_LIMM_32; + GET_LIMM; size = 8; if ((breg == LIMM_REG) && (creg != LIMM_REG)) @@ -208,16 +207,48 @@ int arcompact_01_01_00_helper(DASM_OPS_32, const char* optext) // register - register cases -int arcompact_handle01_01_00_00_dasm(DASM_OPS_32) { return arcompact_01_01_00_helper( DASM_PARAMS, "BREQ"); } -int arcompact_handle01_01_00_01_dasm(DASM_OPS_32) { return arcompact_01_01_00_helper( DASM_PARAMS, "BRNE"); } -int arcompact_handle01_01_00_02_dasm(DASM_OPS_32) { return arcompact_01_01_00_helper( DASM_PARAMS, "BRLT"); } -int arcompact_handle01_01_00_03_dasm(DASM_OPS_32) { return arcompact_01_01_00_helper( DASM_PARAMS, "BRGE"); } -int arcompact_handle01_01_00_04_dasm(DASM_OPS_32) { return arcompact_01_01_00_helper( DASM_PARAMS, "BRLO"); } -int arcompact_handle01_01_00_05_dasm(DASM_OPS_32) { return arcompact_01_01_00_helper( DASM_PARAMS, "BRHS"); } -int arcompact_handle01_01_00_0e_dasm(DASM_OPS_32) { return arcompact_01_01_00_helper( DASM_PARAMS, "BBIT0");} -int arcompact_handle01_01_00_0f_dasm(DASM_OPS_32) { return arcompact_01_01_00_helper( DASM_PARAMS, "BBIT1");} +int arcompact_disassembler::handle01_01_00_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle01_01_00_helper( stream, pc, op, opcodes, "BREQ"); +} + +int arcompact_disassembler::handle01_01_00_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle01_01_00_helper( stream, pc, op, opcodes, "BRNE"); +} + +int arcompact_disassembler::handle01_01_00_02_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle01_01_00_helper( stream, pc, op, opcodes, "BRLT"); +} + +int arcompact_disassembler::handle01_01_00_03_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle01_01_00_helper( stream, pc, op, opcodes, "BRGE"); +} + +int arcompact_disassembler::handle01_01_00_04_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle01_01_00_helper( stream, pc, op, opcodes, "BRLO"); +} + +int arcompact_disassembler::handle01_01_00_05_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle01_01_00_helper( stream, pc, op, opcodes, "BRHS"); +} + +int arcompact_disassembler::handle01_01_00_0e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle01_01_00_helper( stream, pc, op, opcodes, "BBIT0"); +} + +int arcompact_disassembler::handle01_01_00_0f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle01_01_00_helper( stream, pc, op, opcodes, "BBIT1"); +} -int arcompact_01_01_01_helper(DASM_OPS_32, const char* optext) + +int arcompact_disassembler::handle01_01_01_helper(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext) { int size = 4; @@ -240,17 +271,48 @@ int arcompact_01_01_01_helper(DASM_OPS_32, const char* optext) } // register -immediate cases -int arcompact_handle01_01_01_00_dasm(DASM_OPS_32) { return arcompact_01_01_01_helper(DASM_PARAMS, "BREQ"); } -int arcompact_handle01_01_01_01_dasm(DASM_OPS_32) { return arcompact_01_01_01_helper(DASM_PARAMS, "BRNE"); } -int arcompact_handle01_01_01_02_dasm(DASM_OPS_32) { return arcompact_01_01_01_helper(DASM_PARAMS, "BRLT"); } -int arcompact_handle01_01_01_03_dasm(DASM_OPS_32) { return arcompact_01_01_01_helper(DASM_PARAMS, "BRGE"); } -int arcompact_handle01_01_01_04_dasm(DASM_OPS_32) { return arcompact_01_01_01_helper(DASM_PARAMS, "BRLO"); } -int arcompact_handle01_01_01_05_dasm(DASM_OPS_32) { return arcompact_01_01_01_helper(DASM_PARAMS, "BRHS"); } -int arcompact_handle01_01_01_0e_dasm(DASM_OPS_32) { return arcompact_01_01_01_helper(DASM_PARAMS, "BBIT0"); } -int arcompact_handle01_01_01_0f_dasm(DASM_OPS_32) { return arcompact_01_01_01_helper(DASM_PARAMS, "BBIT1"); } +int arcompact_disassembler::handle01_01_01_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle01_01_01_helper(stream, pc, op, opcodes, "BREQ"); +} + +int arcompact_disassembler::handle01_01_01_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle01_01_01_helper(stream, pc, op, opcodes, "BRNE"); +} + +int arcompact_disassembler::handle01_01_01_02_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle01_01_01_helper(stream, pc, op, opcodes, "BRLT"); +} + +int arcompact_disassembler::handle01_01_01_03_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle01_01_01_helper(stream, pc, op, opcodes, "BRGE"); +} + +int arcompact_disassembler::handle01_01_01_04_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle01_01_01_helper(stream, pc, op, opcodes, "BRLO"); +} + +int arcompact_disassembler::handle01_01_01_05_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle01_01_01_helper(stream, pc, op, opcodes, "BRHS"); +} + +int arcompact_disassembler::handle01_01_01_0e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle01_01_01_helper(stream, pc, op, opcodes, "BBIT0"); +} + +int arcompact_disassembler::handle01_01_01_0f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle01_01_01_helper(stream, pc, op, opcodes, "BBIT1"); +} -int arcompact_handle02_dasm(DASM_OPS_32) +int arcompact_disassembler::handle02_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { // bitpos // 1111 1111 1111 1111 0000 0000 0000 0000 @@ -273,7 +335,7 @@ int arcompact_handle02_dasm(DASM_OPS_32) uint32_t limm = 0; if (breg == LIMM_REG) { - GET_LIMM_32; + GET_LIMM; size = 8; } @@ -293,7 +355,7 @@ int arcompact_handle02_dasm(DASM_OPS_32) return size; } -int arcompact_handle03_dasm(DASM_OPS_32) +int arcompact_disassembler::handle03_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { int size = 4; uint32_t limm = 0; @@ -317,7 +379,7 @@ int arcompact_handle03_dasm(DASM_OPS_32) if (breg == LIMM_REG) { - GET_LIMM_32; + GET_LIMM; size = 8; got_limm = 1; } @@ -339,7 +401,7 @@ int arcompact_handle03_dasm(DASM_OPS_32) { if (!got_limm) { - GET_LIMM_32; + GET_LIMM; size = 8; } util::stream_format(stream, "(%08x)", limm); @@ -356,7 +418,7 @@ int arcompact_handle03_dasm(DASM_OPS_32) return size; } -int arcompact_handle04_p00_helper_dasm(DASM_OPS_32, const char* optext, int ignore_dst, int b_reserved) +int arcompact_disassembler::handle04_p00_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext, int ignore_dst, int b_reserved) { // PP // 0010 0bbb 00ii iiii FBBB CCCC CCAA AAAA @@ -376,7 +438,7 @@ int arcompact_handle04_p00_helper_dasm(DASM_OPS_32, const char* optext, int igno if ((!b_reserved) && (breg == LIMM_REG)) { - GET_LIMM_32; + GET_LIMM; size = 8; got_limm = 1; } @@ -385,7 +447,7 @@ int arcompact_handle04_p00_helper_dasm(DASM_OPS_32, const char* optext, int igno { if (!got_limm) { - GET_LIMM_32; + GET_LIMM; size = 8; } } @@ -428,7 +490,7 @@ int arcompact_handle04_p00_helper_dasm(DASM_OPS_32, const char* optext, int igno } // like p00 but with 'u6' istead of C -int arcompact_handle04_p01_helper_dasm(DASM_OPS_32, const char* optext, int ignore_dst, int b_reserved) +int arcompact_disassembler::handle04_p01_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext, int ignore_dst, int b_reserved) { // PP // 0010 0bbb 01ii iiii FBBB uuuu uuAA AAAA @@ -448,7 +510,7 @@ int arcompact_handle04_p01_helper_dasm(DASM_OPS_32, const char* optext, int igno if ((!b_reserved) && (breg == LIMM_REG)) { - GET_LIMM_32; + GET_LIMM; size = 8; // got_limm = 1; } @@ -488,7 +550,7 @@ int arcompact_handle04_p01_helper_dasm(DASM_OPS_32, const char* optext, int igno } -int arcompact_handle04_p10_helper_dasm(DASM_OPS_32, const char* optext, int b_reserved) +int arcompact_disassembler::handle04_p10_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext, int b_reserved) { int size = 4; uint32_t limm; @@ -507,7 +569,7 @@ int arcompact_handle04_p10_helper_dasm(DASM_OPS_32, const char* optext, int b_re { if (breg == LIMM_REG) { - GET_LIMM_32; + GET_LIMM; size = 8; //got_limm = 1; util::stream_format(stream, " 0x%08x ", limm); @@ -527,7 +589,7 @@ int arcompact_handle04_p10_helper_dasm(DASM_OPS_32, const char* optext, int b_re return size; } -int arcompact_handle04_p11_m0_helper_dasm(DASM_OPS_32, const char* optext, int b_reserved) +int arcompact_disassembler::handle04_p11_m0_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext, int b_reserved) { int size = 4; uint32_t limm = 0; @@ -546,7 +608,7 @@ int arcompact_handle04_p11_m0_helper_dasm(DASM_OPS_32, const char* optext, int b { if (breg == LIMM_REG) { - GET_LIMM_32; + GET_LIMM; size = 8; got_limm = 1; util::stream_format(stream, " 0x%08x ", limm); @@ -570,7 +632,7 @@ int arcompact_handle04_p11_m0_helper_dasm(DASM_OPS_32, const char* optext, int b { if (!got_limm) { - GET_LIMM_32; + GET_LIMM; size = 8; } util::stream_format(stream, " 0x%08x ", limm); @@ -583,7 +645,7 @@ int arcompact_handle04_p11_m0_helper_dasm(DASM_OPS_32, const char* optext, int b return size; } -int arcompact_handle04_p11_m1_helper_dasm(DASM_OPS_32, const char* optext, int b_reserved) +int arcompact_disassembler::handle04_p11_m1_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext, int b_reserved) { int size = 4; uint32_t limm; @@ -602,7 +664,7 @@ int arcompact_handle04_p11_m1_helper_dasm(DASM_OPS_32, const char* optext, int b { if (breg == LIMM_REG) { - GET_LIMM_32; + GET_LIMM; size = 8; //got_limm = 1; util::stream_format(stream, " 0x%08x ", limm); @@ -627,213 +689,213 @@ int arcompact_handle04_p11_m1_helper_dasm(DASM_OPS_32, const char* optext, int b return size; } -int arcompact_handle04_p11_helper_dasm(DASM_OPS_32, const char* optext, int b_reserved) +int arcompact_disassembler::handle04_p11_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext, int b_reserved) { int M = (op & 0x00000020) >> 5; op &= ~0x00000020; switch (M) { - case 0x00: return arcompact_handle04_p11_m0_helper_dasm(DASM_PARAMS, optext, b_reserved); - case 0x01: return arcompact_handle04_p11_m1_helper_dasm(DASM_PARAMS, optext, b_reserved); + case 0x00: return handle04_p11_m0_helper_dasm(stream, pc, op, opcodes, optext, b_reserved); + case 0x01: return handle04_p11_m1_helper_dasm(stream, pc, op, opcodes, optext, b_reserved); } return 0; } -int arcompact_handle04_helper_dasm(DASM_OPS_32, const char* optext, int ignore_dst, int b_reserved) +int arcompact_disassembler::handle04_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext, int ignore_dst, int b_reserved) { COMMON32_GET_p; switch (p) { - case 0x00: return arcompact_handle04_p00_helper_dasm(DASM_PARAMS, optext, ignore_dst, b_reserved); - case 0x01: return arcompact_handle04_p01_helper_dasm(DASM_PARAMS, optext, ignore_dst, b_reserved); - case 0x02: return arcompact_handle04_p10_helper_dasm(DASM_PARAMS, optext, b_reserved); - case 0x03: return arcompact_handle04_p11_helper_dasm(DASM_PARAMS, optext, b_reserved); + case 0x00: return handle04_p00_helper_dasm(stream, pc, op, opcodes, optext, ignore_dst, b_reserved); + case 0x01: return handle04_p01_helper_dasm(stream, pc, op, opcodes, optext, ignore_dst, b_reserved); + case 0x02: return handle04_p10_helper_dasm(stream, pc, op, opcodes, optext, b_reserved); + case 0x03: return handle04_p11_helper_dasm(stream, pc, op, opcodes, optext, b_reserved); } return 0; } -int arcompact_handle04_00_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "ADD", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "ADD", 0,0); } -int arcompact_handle04_01_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "ADC", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "ADC", 0,0); } -int arcompact_handle04_02_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_02_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "SUB", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "SUB", 0,0); } -int arcompact_handle04_03_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_03_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "SBC", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "SBC", 0,0); } -int arcompact_handle04_04_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_04_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "AND", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "AND", 0,0); } -int arcompact_handle04_05_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_05_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "OR", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "OR", 0,0); } -int arcompact_handle04_06_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_06_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "BIC", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "BIC", 0,0); } -int arcompact_handle04_07_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_07_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "XOR", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "XOR", 0,0); } -int arcompact_handle04_08_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_08_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "MAX", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "MAX", 0,0); } -int arcompact_handle04_09_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_09_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "MIN", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "MIN", 0,0); } -int arcompact_handle04_0a_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_0a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "MOV", 1,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "MOV", 1,0); } -int arcompact_handle04_0b_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_0b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "TST", 1,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "TST", 1,0); } -int arcompact_handle04_0c_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_0c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "CMP", 1,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "CMP", 1,0); } -int arcompact_handle04_0d_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_0d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "RCMP", 1,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "RCMP", 1,0); } -int arcompact_handle04_0e_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_0e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "RSUB", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "RSUB", 0,0); } -int arcompact_handle04_0f_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_0f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "BSET", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "BSET", 0,0); } -int arcompact_handle04_10_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_10_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "BCLR", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "BCLR", 0,0); } -int arcompact_handle04_11_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_11_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "BTST", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "BTST", 0,0); } -int arcompact_handle04_12_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_12_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "BXOR", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "BXOR", 0,0); } -int arcompact_handle04_13_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_13_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "BMSK", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "BMSK", 0,0); } -int arcompact_handle04_14_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_14_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "ADD1", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "ADD1", 0,0); } -int arcompact_handle04_15_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_15_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "ADD2", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "ADD2", 0,0); } -int arcompact_handle04_16_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_16_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "ADD3", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "ADD3", 0,0); } -int arcompact_handle04_17_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_17_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "SUB1", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "SUB1", 0,0); } -int arcompact_handle04_18_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_18_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "SUB2", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "SUB2", 0,0); } -int arcompact_handle04_19_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_19_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "SUB3", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "SUB3", 0,0); } -int arcompact_handle04_1a_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_1a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "MPY", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "MPY", 0,0); } // * -int arcompact_handle04_1b_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_1b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "MPYH", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "MPYH", 0,0); } // * -int arcompact_handle04_1c_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_1c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "MPYHU", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "MPYHU", 0,0); } // * -int arcompact_handle04_1d_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_1d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "MPYU", 0,0); + return handle04_helper_dasm(stream, pc, op, opcodes, "MPYU", 0,0); } // * -int arcompact_handle04_20_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_20_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "J", 1,1); + return handle04_helper_dasm(stream, pc, op, opcodes, "J", 1,1); } -int arcompact_handle04_21_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_21_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "J.D", 1,1); + return handle04_helper_dasm(stream, pc, op, opcodes, "J.D", 1,1); } -int arcompact_handle04_22_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_22_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "JL", 1,1); + return handle04_helper_dasm(stream, pc, op, opcodes, "JL", 1,1); } -int arcompact_handle04_23_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_23_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { - return arcompact_handle04_helper_dasm(DASM_PARAMS, "JL.D", 1,1); + return handle04_helper_dasm(stream, pc, op, opcodes, "JL.D", 1,1); } -int arcompact_handle04_28_dasm(DASM_OPS_32) // LPcc (loop setup) +int arcompact_disassembler::handle04_28_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) // LPcc (loop setup) { COMMON32_GET_breg; // breg is reserved COMMON32_GET_p; @@ -879,7 +941,8 @@ int arcompact_handle04_28_dasm(DASM_OPS_32) // LPcc (loop setup) } \ else \ util::stream_format(stream, "[%03x]", auxreg); -int arcompact_handle04_2a_dasm(DASM_OPS_32) // Load FROM Auxiliary register TO register + +int arcompact_disassembler::handle04_2a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) // Load FROM Auxiliary register TO register { // pp F // 0010 0bbb 0010 1010 0BBB CCCC CCRR RRRR @@ -922,7 +985,7 @@ int arcompact_handle04_2a_dasm(DASM_OPS_32) // Load FROM Auxiliary register TO { if (!got_limm) { - GET_LIMM_32; + GET_LIMM; size = 8; } @@ -962,7 +1025,7 @@ int arcompact_handle04_2a_dasm(DASM_OPS_32) // Load FROM Auxiliary register TO return size; } -int arcompact_handle04_2b_dasm(DASM_OPS_32) // Store TO Auxiliary register FROM register +int arcompact_disassembler::handle04_2b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) // Store TO Auxiliary register FROM register { // code at ~ 40073DFE in leapster bios is manually setting up a loop this way // rather than using the lPcc opcode @@ -983,7 +1046,7 @@ int arcompact_handle04_2b_dasm(DASM_OPS_32) // Store TO Auxiliary register FROM if (breg == LIMM_REG) { - GET_LIMM_32; + GET_LIMM; size = 8; got_limm = 1; util::stream_format(stream, " %08x -> ", limm); @@ -1005,7 +1068,7 @@ int arcompact_handle04_2b_dasm(DASM_OPS_32) // Store TO Auxiliary register FROM { if (!got_limm) { - GET_LIMM_32; + GET_LIMM; size = 8; } @@ -1052,14 +1115,14 @@ int arcompact_handle04_2b_dasm(DASM_OPS_32) // Store TO Auxiliary register FROM return size;} -int arcompact_handle04_29_dasm(DASM_OPS_32) +int arcompact_disassembler::handle04_29_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { // leapster bios uses formats for FLAG that are not defined, bug I guess work anyway (P modes 0 / 1) - return arcompact_handle04_helper_dasm(DASM_PARAMS, "FLAG", 1,1); + return handle04_helper_dasm(stream, pc, op, opcodes, "FLAG", 1,1); } -int arcompact_handle04_2f_helper_dasm(DASM_OPS_32, const char* optext) +int arcompact_disassembler::handle04_2f_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext) { // // 0010 0bbb pp10 1111 FBBB CCCC CCII IIII @@ -1090,7 +1153,7 @@ int arcompact_handle04_2f_helper_dasm(DASM_OPS_32, const char* optext) if (creg == LIMM_REG) { uint32_t limm; - GET_LIMM_32; + GET_LIMM; size = 8; util::stream_format(stream, "(%08x) ", limm); @@ -1119,29 +1182,106 @@ int arcompact_handle04_2f_helper_dasm(DASM_OPS_32, const char* optext) } -int arcompact_handle04_2f_00_dasm(DASM_OPS_32) { return arcompact_handle04_2f_helper_dasm(DASM_PARAMS, "ASL"); } // ASL -int arcompact_handle04_2f_01_dasm(DASM_OPS_32) { return arcompact_handle04_2f_helper_dasm(DASM_PARAMS, "ASR"); } // ASR -int arcompact_handle04_2f_02_dasm(DASM_OPS_32) { return arcompact_handle04_2f_helper_dasm(DASM_PARAMS, "LSR"); } // LSR -int arcompact_handle04_2f_03_dasm(DASM_OPS_32) { return arcompact_handle04_2f_helper_dasm(DASM_PARAMS, "ROR"); } // ROR -int arcompact_handle04_2f_04_dasm(DASM_OPS_32) { return arcompact_handle04_2f_helper_dasm(DASM_PARAMS, "RCC"); } // RCC -int arcompact_handle04_2f_05_dasm(DASM_OPS_32) { return arcompact_handle04_2f_helper_dasm(DASM_PARAMS, "SEXB"); } // SEXB -int arcompact_handle04_2f_06_dasm(DASM_OPS_32) { return arcompact_handle04_2f_helper_dasm(DASM_PARAMS, "SEXW"); } // SEXW -int arcompact_handle04_2f_07_dasm(DASM_OPS_32) { return arcompact_handle04_2f_helper_dasm(DASM_PARAMS, "EXTB"); } // EXTB +int arcompact_disassembler::handle04_2f_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_2f_helper_dasm(stream, pc, op, opcodes, "ASL"); +} // ASL + +int arcompact_disassembler::handle04_2f_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_2f_helper_dasm(stream, pc, op, opcodes, "ASR"); +} // ASR + +int arcompact_disassembler::handle04_2f_02_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_2f_helper_dasm(stream, pc, op, opcodes, "LSR"); +} // LSR + +int arcompact_disassembler::handle04_2f_03_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_2f_helper_dasm(stream, pc, op, opcodes, "ROR"); +} // ROR + +int arcompact_disassembler::handle04_2f_04_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_2f_helper_dasm(stream, pc, op, opcodes, "RCC"); +} // RCC + +int arcompact_disassembler::handle04_2f_05_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_2f_helper_dasm(stream, pc, op, opcodes, "SEXB"); +} // SEXB + +int arcompact_disassembler::handle04_2f_06_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_2f_helper_dasm(stream, pc, op, opcodes, "SEXW"); +} // SEXW + +int arcompact_disassembler::handle04_2f_07_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_2f_helper_dasm(stream, pc, op, opcodes, "EXTB"); +} // EXTB + + +int arcompact_disassembler::handle04_2f_08_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_2f_helper_dasm(stream, pc, op, opcodes, "EXTW"); +} // EXTW + + + +int arcompact_disassembler::handle04_2f_09_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_2f_helper_dasm(stream, pc, op, opcodes, "ABS"); +} // ABS + +int arcompact_disassembler::handle04_2f_0a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_2f_helper_dasm(stream, pc, op, opcodes, "NOT"); +} // NOT + +int arcompact_disassembler::handle04_2f_0b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_2f_helper_dasm(stream, pc, op, opcodes, "RCL"); +} // RLC + +int arcompact_disassembler::handle04_2f_0c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_2f_helper_dasm(stream, pc, op, opcodes, "EX"); +} // EX + + + +int arcompact_disassembler::handle04_2f_3f_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format( stream, "SLEEP (%08x)", op); + return 4; +} -int arcompact_handle04_2f_08_dasm(DASM_OPS_32) { return arcompact_handle04_2f_helper_dasm(DASM_PARAMS, "EXTW"); } // EXTW +int arcompact_disassembler::handle04_2f_3f_02_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format( stream, "SWI / TRAP0 (%08x)", op); + return 4; +} +int arcompact_disassembler::handle04_2f_3f_03_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format( stream, "SYNC (%08x)", op); + return 4; +} -int arcompact_handle04_2f_09_dasm(DASM_OPS_32) { return arcompact_handle04_2f_helper_dasm(DASM_PARAMS, "ABS"); } // ABS -int arcompact_handle04_2f_0a_dasm(DASM_OPS_32) { return arcompact_handle04_2f_helper_dasm(DASM_PARAMS, "NOT"); } // NOT -int arcompact_handle04_2f_0b_dasm(DASM_OPS_32) { return arcompact_handle04_2f_helper_dasm(DASM_PARAMS, "RCL"); } // RLC -int arcompact_handle04_2f_0c_dasm(DASM_OPS_32) { return arcompact_handle04_2f_helper_dasm(DASM_PARAMS, "EX"); } // EX +int arcompact_disassembler::handle04_2f_3f_04_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format( stream, "RTIE (%08x)", op); + return 4; +} +int arcompact_disassembler::handle04_2f_3f_05_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format( stream, "BRK (%08x)", op); + return 4; +} -int arcompact_handle04_2f_3f_01_dasm(DASM_OPS_32) { util::stream_format( stream, "SLEEP (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_02_dasm(DASM_OPS_32) { util::stream_format( stream, "SWI / TRAP0 (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_03_dasm(DASM_OPS_32) { util::stream_format( stream, "SYNC (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_04_dasm(DASM_OPS_32) { util::stream_format( stream, "RTIE (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_05_dasm(DASM_OPS_32) { util::stream_format( stream, "BRK (%08x)", op); return 4; } @@ -1151,7 +1291,7 @@ int arcompact_handle04_2f_3f_05_dasm(DASM_OPS_32) { util::stream_format( stream // 0010 0bbb aa11 0ZZX DBBB CCCC CCAA AAAA // note, bits 11 0ZZX are part of the sub-opcode # already - this is a special encoding -int arcompact_handle04_3x_helper_dasm(DASM_OPS_32, int dsize, int extend) +int arcompact_disassembler::handle04_3x_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, int dsize, int extend) { int size = 4; uint32_t limm=0; @@ -1174,7 +1314,7 @@ int arcompact_handle04_3x_helper_dasm(DASM_OPS_32, int dsize, int extend) if (breg == LIMM_REG) { - GET_LIMM_32; + GET_LIMM; size = 8; got_limm = 1; util::stream_format(stream, "[%08x, ", limm); @@ -1189,7 +1329,7 @@ int arcompact_handle04_3x_helper_dasm(DASM_OPS_32, int dsize, int extend) { if (!got_limm) { - GET_LIMM_32; + GET_LIMM; size = 8; } util::stream_format(stream, "(%08x)]", limm); @@ -1207,43 +1347,127 @@ int arcompact_handle04_3x_helper_dasm(DASM_OPS_32, int dsize, int extend) } -int arcompact_handle04_30_dasm(DASM_OPS_32) { return arcompact_handle04_3x_helper_dasm(DASM_PARAMS,0,0); } +int arcompact_disassembler::handle04_30_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_3x_helper_dasm(stream, pc, op, opcodes,0,0); +} + // ZZ value of 0x0 with X of 1 is illegal -int arcompact_handle04_31_dasm(DASM_OPS_32) { return arcompact_handle04_3x_helper_dasm(DASM_PARAMS,0,1); } -int arcompact_handle04_32_dasm(DASM_OPS_32) { return arcompact_handle04_3x_helper_dasm(DASM_PARAMS,1,0); } -int arcompact_handle04_33_dasm(DASM_OPS_32) { return arcompact_handle04_3x_helper_dasm(DASM_PARAMS,1,1); } -int arcompact_handle04_34_dasm(DASM_OPS_32) { return arcompact_handle04_3x_helper_dasm(DASM_PARAMS,2,0); } -int arcompact_handle04_35_dasm(DASM_OPS_32) { return arcompact_handle04_3x_helper_dasm(DASM_PARAMS,2,1); } +int arcompact_disassembler::handle04_31_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_3x_helper_dasm(stream, pc, op, opcodes,0,1); +} + +int arcompact_disassembler::handle04_32_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_3x_helper_dasm(stream, pc, op, opcodes,1,0); +} + +int arcompact_disassembler::handle04_33_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_3x_helper_dasm(stream, pc, op, opcodes,1,1); +} + +int arcompact_disassembler::handle04_34_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_3x_helper_dasm(stream, pc, op, opcodes,2,0); +} + +int arcompact_disassembler::handle04_35_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_3x_helper_dasm(stream, pc, op, opcodes,2,1); +} + // ZZ value of 0x3 is illegal -int arcompact_handle04_36_dasm(DASM_OPS_32) { return arcompact_handle04_3x_helper_dasm(DASM_PARAMS,3,0); } -int arcompact_handle04_37_dasm(DASM_OPS_32) { return arcompact_handle04_3x_helper_dasm(DASM_PARAMS,3,1); } +int arcompact_disassembler::handle04_36_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_3x_helper_dasm(stream, pc, op, opcodes,3,0); +} + +int arcompact_disassembler::handle04_37_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_3x_helper_dasm(stream, pc, op, opcodes,3,1); +} + + + + +int arcompact_disassembler::handle05_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_helper_dasm(stream, pc, op, opcodes, "ASL", 0,0); +} + +int arcompact_disassembler::handle05_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_helper_dasm(stream, pc, op, opcodes, "LSR", 0,0); +} + +int arcompact_disassembler::handle05_02_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_helper_dasm(stream, pc, op, opcodes, "ASR", 0,0); +} + +int arcompact_disassembler::handle05_03_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_helper_dasm(stream, pc, op, opcodes, "ROR", 0,0); +} + +int arcompact_disassembler::handle05_04_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_helper_dasm(stream, pc, op, opcodes, "MUL64", 2,0); +} // special + +int arcompact_disassembler::handle05_05_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_helper_dasm(stream, pc, op, opcodes, "MULU64", 2,0); +} // special + +int arcompact_disassembler::handle05_06_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_helper_dasm(stream, pc, op, opcodes, "ADDS", 0,0); +} + +int arcompact_disassembler::handle05_07_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_helper_dasm(stream, pc, op, opcodes, "SUBS", 0,0); +} + +int arcompact_disassembler::handle05_08_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_helper_dasm(stream, pc, op, opcodes, "DIVAW", 0,0); +} -int arcompact_handle05_00_dasm(DASM_OPS_32) { return arcompact_handle04_helper_dasm(DASM_PARAMS, "ASL", 0,0); } -int arcompact_handle05_01_dasm(DASM_OPS_32) { return arcompact_handle04_helper_dasm(DASM_PARAMS, "LSR", 0,0); } -int arcompact_handle05_02_dasm(DASM_OPS_32) { return arcompact_handle04_helper_dasm(DASM_PARAMS, "ASR", 0,0); } -int arcompact_handle05_03_dasm(DASM_OPS_32) { return arcompact_handle04_helper_dasm(DASM_PARAMS, "ROR", 0,0); } -int arcompact_handle05_04_dasm(DASM_OPS_32) { return arcompact_handle04_helper_dasm(DASM_PARAMS, "MUL64", 2,0); } // special -int arcompact_handle05_05_dasm(DASM_OPS_32) { return arcompact_handle04_helper_dasm(DASM_PARAMS, "MULU64", 2,0);} // special -int arcompact_handle05_06_dasm(DASM_OPS_32) { return arcompact_handle04_helper_dasm(DASM_PARAMS, "ADDS", 0,0); } -int arcompact_handle05_07_dasm(DASM_OPS_32) { return arcompact_handle04_helper_dasm(DASM_PARAMS, "SUBS", 0,0); } -int arcompact_handle05_08_dasm(DASM_OPS_32) { return arcompact_handle04_helper_dasm(DASM_PARAMS, "DIVAW", 0,0); } + +int arcompact_disassembler::handle05_0a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_helper_dasm(stream, pc, op, opcodes, "ASLS", 0,0); +} + +int arcompact_disassembler::handle05_0b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_helper_dasm(stream, pc, op, opcodes, "ASRS", 0,0); +} +int arcompact_disassembler::handle05_28_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_helper_dasm(stream, pc, op, opcodes, "ADDSDW", 0,0); +} -int arcompact_handle05_0a_dasm(DASM_OPS_32) { return arcompact_handle04_helper_dasm(DASM_PARAMS, "ASLS", 0,0); } -int arcompact_handle05_0b_dasm(DASM_OPS_32) { return arcompact_handle04_helper_dasm(DASM_PARAMS, "ASRS", 0,0); } +int arcompact_disassembler::handle05_29_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle04_helper_dasm(stream, pc, op, opcodes, "SUBSDW", 0,0); +} -int arcompact_handle05_28_dasm(DASM_OPS_32) { return arcompact_handle04_helper_dasm(DASM_PARAMS, "ADDSDW", 0,0); } -int arcompact_handle05_29_dasm(DASM_OPS_32) { return arcompact_handle04_helper_dasm(DASM_PARAMS, "SUBSDW", 0,0); } -int arcompact_handle05_2f_0x_helper_dasm(DASM_OPS_32, const char* optext) +int arcompact_disassembler::handle05_2f_0x_helper_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes, const char* optext) { // // 0010 1bbb pp10 1111 FBBB CCCC CCII IIII when pp == 0x00 @@ -1271,7 +1495,7 @@ int arcompact_handle05_2f_0x_helper_dasm(DASM_OPS_32, const char* optext) if (creg == LIMM_REG) { uint32_t limm; - GET_LIMM_32; + GET_LIMM; size = 8; util::stream_format(stream, "(%08x) ", limm); @@ -1299,48 +1523,84 @@ int arcompact_handle05_2f_0x_helper_dasm(DASM_OPS_32, const char* optext) } -int arcompact_handle05_2f_00_dasm(DASM_OPS_32) { return arcompact_handle05_2f_0x_helper_dasm(DASM_PARAMS, "SWAP"); } -int arcompact_handle05_2f_01_dasm(DASM_OPS_32) { return arcompact_handle05_2f_0x_helper_dasm(DASM_PARAMS, "NORM"); } -int arcompact_handle05_2f_02_dasm(DASM_OPS_32) { return arcompact_handle05_2f_0x_helper_dasm(DASM_PARAMS, "SAT16"); } -int arcompact_handle05_2f_03_dasm(DASM_OPS_32) { return arcompact_handle05_2f_0x_helper_dasm(DASM_PARAMS, "RND16"); } -int arcompact_handle05_2f_04_dasm(DASM_OPS_32) { return arcompact_handle05_2f_0x_helper_dasm(DASM_PARAMS, "ABSSW"); } -int arcompact_handle05_2f_05_dasm(DASM_OPS_32) { return arcompact_handle05_2f_0x_helper_dasm(DASM_PARAMS, "ABSS"); } -int arcompact_handle05_2f_06_dasm(DASM_OPS_32) { return arcompact_handle05_2f_0x_helper_dasm(DASM_PARAMS, "NEGSW"); } -int arcompact_handle05_2f_07_dasm(DASM_OPS_32) { return arcompact_handle05_2f_0x_helper_dasm(DASM_PARAMS, "NEGS"); } -int arcompact_handle05_2f_08_dasm(DASM_OPS_32) { return arcompact_handle05_2f_0x_helper_dasm(DASM_PARAMS, "NORMW"); } +int arcompact_disassembler::handle05_2f_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle05_2f_0x_helper_dasm(stream, pc, op, opcodes, "SWAP"); +} + +int arcompact_disassembler::handle05_2f_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle05_2f_0x_helper_dasm(stream, pc, op, opcodes, "NORM"); +} + +int arcompact_disassembler::handle05_2f_02_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle05_2f_0x_helper_dasm(stream, pc, op, opcodes, "SAT16"); +} + +int arcompact_disassembler::handle05_2f_03_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle05_2f_0x_helper_dasm(stream, pc, op, opcodes, "RND16"); +} + +int arcompact_disassembler::handle05_2f_04_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle05_2f_0x_helper_dasm(stream, pc, op, opcodes, "ABSSW"); +} + +int arcompact_disassembler::handle05_2f_05_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle05_2f_0x_helper_dasm(stream, pc, op, opcodes, "ABSS"); +} + +int arcompact_disassembler::handle05_2f_06_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle05_2f_0x_helper_dasm(stream, pc, op, opcodes, "NEGSW"); +} + +int arcompact_disassembler::handle05_2f_07_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle05_2f_0x_helper_dasm(stream, pc, op, opcodes, "NEGS"); +} + +int arcompact_disassembler::handle05_2f_08_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + return handle05_2f_0x_helper_dasm(stream, pc, op, opcodes, "NORMW"); +} + -int arcompact_handle06_dasm(DASM_OPS_32) +int arcompact_disassembler::handle06_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { util::stream_format( stream, "op a,b,c (06 ARC ext) (%08x)", op ); return 4; } -int arcompact_handle07_dasm(DASM_OPS_32) +int arcompact_disassembler::handle07_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { util::stream_format( stream, "op a,b,c (07 User ext) (%08x)", op ); return 4; } -int arcompact_handle08_dasm(DASM_OPS_32) +int arcompact_disassembler::handle08_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { util::stream_format( stream, "op a,b,c (08 User ext) (%08x)", op ); return 4; } -int arcompact_handle09_dasm(DASM_OPS_32) +int arcompact_disassembler::handle09_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { util::stream_format( stream, "op a,b,c (09 Market ext) (%08x)", op ); return 4; } -int arcompact_handle0a_dasm(DASM_OPS_32) +int arcompact_disassembler::handle0a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { util::stream_format( stream, "op a,b,c (0a Market ext) (%08x)", op ); return 4; } -int arcompact_handle0b_dasm(DASM_OPS_32) +int arcompact_disassembler::handle0b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) { util::stream_format( stream, "op a,b,c (0b Market ext) (%08x)", op ); return 4; @@ -1348,7 +1608,7 @@ int arcompact_handle0b_dasm(DASM_OPS_32) -int arcompact_handle0c_helper_dasm(DASM_OPS_16, const char* optext, int format) +int arcompact_disassembler::handle0c_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext, int format) { int areg, breg, creg; @@ -1368,28 +1628,28 @@ int arcompact_handle0c_helper_dasm(DASM_OPS_16, const char* optext, int format) } -int arcompact_handle0c_00_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0c_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle0c_helper_dasm(DASM_PARAMS, "LD_S", 0); + return handle0c_helper_dasm(stream, pc, op, opcodes, "LD_S", 0); } -int arcompact_handle0c_01_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0c_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle0c_helper_dasm(DASM_PARAMS, "LDB_S", 0); + return handle0c_helper_dasm(stream, pc, op, opcodes, "LDB_S", 0); } -int arcompact_handle0c_02_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0c_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle0c_helper_dasm(DASM_PARAMS, "LDW_S", 0); + return handle0c_helper_dasm(stream, pc, op, opcodes, "LDW_S", 0); } -int arcompact_handle0c_03_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0c_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle0c_helper_dasm(DASM_PARAMS, "ADD_S", 1); + return handle0c_helper_dasm(stream, pc, op, opcodes, "ADD_S", 1); } -int arcompact_handle0d_helper_dasm(DASM_OPS_16, const char* optext) +int arcompact_disassembler::handle0d_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext) { int u, breg, creg; @@ -1405,29 +1665,29 @@ int arcompact_handle0d_helper_dasm(DASM_OPS_16, const char* optext) } -int arcompact_handle0d_00_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0d_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle0d_helper_dasm(DASM_PARAMS, "ADD_S"); + return handle0d_helper_dasm(stream, pc, op, opcodes, "ADD_S"); } -int arcompact_handle0d_01_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0d_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle0d_helper_dasm(DASM_PARAMS, "SUB_S"); + return handle0d_helper_dasm(stream, pc, op, opcodes, "SUB_S"); } -int arcompact_handle0d_02_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0d_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle0d_helper_dasm(DASM_PARAMS, "ASL_S"); + return handle0d_helper_dasm(stream, pc, op, opcodes, "ASL_S"); } -int arcompact_handle0d_03_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0d_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle0d_helper_dasm(DASM_PARAMS, "ASR_S"); + return handle0d_helper_dasm(stream, pc, op, opcodes, "ASR_S"); } -int arcompact_handle0e_0x_helper_dasm(DASM_OPS_16, const char* optext, int revop) +int arcompact_disassembler::handle0e_0x_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext, int revop) { int h,breg; int size = 2; @@ -1455,29 +1715,29 @@ int arcompact_handle0e_0x_helper_dasm(DASM_OPS_16, const char* optext, int revop } -int arcompact_handle0e_00_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0e_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle0e_0x_helper_dasm(DASM_PARAMS, "ADD_S", 0); + return handle0e_0x_helper_dasm(stream, pc, op, opcodes, "ADD_S", 0); } -int arcompact_handle0e_01_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0e_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle0e_0x_helper_dasm(DASM_PARAMS, "MOV_S", 0); + return handle0e_0x_helper_dasm(stream, pc, op, opcodes, "MOV_S", 0); } -int arcompact_handle0e_02_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0e_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle0e_0x_helper_dasm(DASM_PARAMS, "CMP_S", 0); + return handle0e_0x_helper_dasm(stream, pc, op, opcodes, "CMP_S", 0); } -int arcompact_handle0e_03_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0e_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle0e_0x_helper_dasm(DASM_PARAMS, "MOV_S", 1); + return handle0e_0x_helper_dasm(stream, pc, op, opcodes, "MOV_S", 1); } -int arcompact_handle0f_00_0x_helper_dasm(DASM_OPS_16, const char* optext) +int arcompact_disassembler::handle0f_00_0x_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext) { int breg; @@ -1492,153 +1752,289 @@ int arcompact_handle0f_00_0x_helper_dasm(DASM_OPS_16, const char* optext) -int arcompact_handle0f_00_00_dasm(DASM_OPS_16) { return arcompact_handle0f_00_0x_helper_dasm(DASM_PARAMS, "J_S"); } -int arcompact_handle0f_00_01_dasm(DASM_OPS_16) { return arcompact_handle0f_00_0x_helper_dasm(DASM_PARAMS, "J_S.D"); } -int arcompact_handle0f_00_02_dasm(DASM_OPS_16) { return arcompact_handle0f_00_0x_helper_dasm(DASM_PARAMS, "JL_S"); } -int arcompact_handle0f_00_03_dasm(DASM_OPS_16) { return arcompact_handle0f_00_0x_helper_dasm(DASM_PARAMS, "JL_S.D"); } -int arcompact_handle0f_00_06_dasm(DASM_OPS_16) { return arcompact_handle0f_00_0x_helper_dasm(DASM_PARAMS, "SUB_S.NE"); } +int arcompact_disassembler::handle0f_00_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_00_0x_helper_dasm(stream, pc, op, opcodes, "J_S"); +} +int arcompact_disassembler::handle0f_00_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_00_0x_helper_dasm(stream, pc, op, opcodes, "J_S.D"); +} +int arcompact_disassembler::handle0f_00_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_00_0x_helper_dasm(stream, pc, op, opcodes, "JL_S"); +} +int arcompact_disassembler::handle0f_00_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_00_0x_helper_dasm(stream, pc, op, opcodes, "JL_S.D"); +} -// Zero parameters (ZOP) -int arcompact_handle0f_00_07_00_dasm(DASM_OPS_16) { util::stream_format( stream, "NOP_S"); return 2; } -int arcompact_handle0f_00_07_01_dasm(DASM_OPS_16) { util::stream_format( stream, "UNIMP_S"); return 2; } // Unimplemented Instruction, same as illegal, but recommended to fill blank space -int arcompact_handle0f_00_07_04_dasm(DASM_OPS_16) { util::stream_format( stream, "JEQ_S [blink]"); return 2; } -int arcompact_handle0f_00_07_05_dasm(DASM_OPS_16) { util::stream_format( stream, "JNE_S [blink]"); return 2; } -int arcompact_handle0f_00_07_06_dasm(DASM_OPS_16) { util::stream_format( stream, "J_S [blink]"); return 2; } -int arcompact_handle0f_00_07_07_dasm(DASM_OPS_16) { util::stream_format( stream, "J_S.D [blink]"); return 2; } +int arcompact_disassembler::handle0f_00_06_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_00_0x_helper_dasm(stream, pc, op, opcodes, "SUB_S.NE"); +} -int arcompact_handle0f_0x_helper_dasm(DASM_OPS_16, const char* optext, int nodst) +// Zero parameters (ZOP) +int arcompact_disassembler::handle0f_00_07_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - int breg, creg; - - COMMON16_GET_breg; - COMMON16_GET_creg; - - REG_16BIT_RANGE(breg); - REG_16BIT_RANGE(creg); + util::stream_format( stream, "NOP_S"); return 2; +} - if (nodst==0) util::stream_format(stream, "%s %s <- %s", optext, regnames[breg], regnames[creg]); - else if (nodst==1) util::stream_format(stream, "%s , %s, %s", optext, regnames[breg], regnames[creg]); - else if (nodst==2) util::stream_format(stream, "%s , %s, %s", optext, regnames[breg], regnames[creg]); +int arcompact_disassembler::handle0f_00_07_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format( stream, "UNIMP_S"); return 2; +} // Unimplemented Instruction, same as illegal, but recommended to fill blank space - return 2; +int arcompact_disassembler::handle0f_00_07_04_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format( stream, "JEQ_S [blink]"); return 2; } -int arcompact_handle0f_02_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "SUB_S",0); } -int arcompact_handle0f_04_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "AND_S",0); } -int arcompact_handle0f_05_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "OR_S",0); } -int arcompact_handle0f_06_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "BIC_S",0); } -int arcompact_handle0f_07_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "XOR_S",0); } -int arcompact_handle0f_0b_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "TST_S",1); } -int arcompact_handle0f_0c_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "MUL64_S",2); } // actual destination is special multiply registers -int arcompact_handle0f_0d_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "SEXB_S",0); } -int arcompact_handle0f_0e_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "SEXW_S",0); } -int arcompact_handle0f_0f_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "EXTB_S",0); } -int arcompact_handle0f_10_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "EXTW_S",0); } -int arcompact_handle0f_11_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "ABS_S",0); } -int arcompact_handle0f_12_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "NOT_S",0); } -int arcompact_handle0f_13_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "NEG_S",0); } -int arcompact_handle0f_14_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "ADD1_S",0); } -int arcompact_handle0f_15_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "ADD2_S",0); } -int arcompact_handle0f_16_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "ADD3_S",0); } -int arcompact_handle0f_18_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "ASL_S",0); } -int arcompact_handle0f_19_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "LSR_S",0); } -int arcompact_handle0f_1a_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "ASR_S",0); } -int arcompact_handle0f_1b_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "ASL1_S",0); } -int arcompact_handle0f_1c_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "ASR1_S",0); } -int arcompact_handle0f_1d_dasm(DASM_OPS_16) { return arcompact_handle0f_0x_helper_dasm(DASM_PARAMS, "LSR1_S",0); } - - -int arcompact_handle0f_1e_dasm(DASM_OPS_16) // special -{ // 0111 1uuu uuu1 1110 - int u = (op & 0x07e0)>>5; - util::stream_format( stream, "TRAP_S %02x",u); - return 2; +int arcompact_disassembler::handle0f_00_07_05_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format( stream, "JNE_S [blink]"); return 2; } -int arcompact_handle0f_1f_dasm(DASM_OPS_16) // special +int arcompact_disassembler::handle0f_00_07_06_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - int u = (op & 0x07e0)>>5; op &= ~0x07e0; + util::stream_format( stream, "J_S [blink]"); return 2; +} - if (u == 0x003f) - { - util::stream_format(stream, "BRK_S"); - } - else - { - util::stream_format(stream, "",u); - } - return 2; +int arcompact_disassembler::handle0f_00_07_07_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format( stream, "J_S.D [blink]"); return 2; } -int arcompact_handle_ld_helper_dasm(DASM_OPS_16, const char* optext, int shift, int swap) + + + + +int arcompact_disassembler::handle0f_0x_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext, int nodst) { - int breg, creg, u; + int breg, creg; COMMON16_GET_breg; COMMON16_GET_creg; - COMMON16_GET_u5; REG_16BIT_RANGE(breg); REG_16BIT_RANGE(creg); - u <<= shift; + if (nodst==0) util::stream_format(stream, "%s %s <- %s", optext, regnames[breg], regnames[creg]); + else if (nodst==1) util::stream_format(stream, "%s , %s, %s", optext, regnames[breg], regnames[creg]); + else if (nodst==2) util::stream_format(stream, "%s , %s, %s", optext, regnames[breg], regnames[creg]); - if (!swap) util::stream_format(stream, "%s %s, [%s, 0x%02x] (%04x)", optext, regnames[creg], regnames[breg], u, op); - else util::stream_format(stream, "%s [%s, 0x%02x], %s (%04x)", optext, regnames[breg], u, regnames[creg], op); return 2; +} +int arcompact_disassembler::handle0f_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "SUB_S",0); } +int arcompact_disassembler::handle0f_04_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "AND_S",0); +} -int arcompact_handle10_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0f_05_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle_ld_helper_dasm(DASM_PARAMS, "LD_S", 2, 0); + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "OR_S",0); } -int arcompact_handle11_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0f_06_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle_ld_helper_dasm(DASM_PARAMS, "LDB_S", 0, 0); + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "BIC_S",0); } -int arcompact_handle12_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0f_07_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle_ld_helper_dasm(DASM_PARAMS, "LDW_S", 1, 0); + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "XOR_S",0); } -int arcompact_handle13_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0f_0b_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle_ld_helper_dasm(DASM_PARAMS, "LDW_S.X", 1, 0); + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "TST_S",1); } -int arcompact_handle14_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0f_0c_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "MUL64_S",2); +} // actual destination is special multiply registers + +int arcompact_disassembler::handle0f_0d_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle_ld_helper_dasm(DASM_PARAMS, "ST_S", 2, 1); + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "SEXB_S",0); } -int arcompact_handle15_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0f_0e_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle_ld_helper_dasm(DASM_PARAMS, "STB_S", 0, 1); + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "SEXW_S",0); } -int arcompact_handle16_dasm(DASM_OPS_16) +int arcompact_disassembler::handle0f_0f_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle_ld_helper_dasm(DASM_PARAMS, "STW_S", 1, 1); + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "EXTB_S",0); } +int arcompact_disassembler::handle0f_10_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "EXTW_S",0); +} -int arcompact_handle_l7_0x_helper_dasm(DASM_OPS_16, const char* optext) +int arcompact_disassembler::handle0f_11_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - int breg, u; + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "ABS_S",0); +} - COMMON16_GET_breg; +int arcompact_disassembler::handle0f_12_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "NOT_S",0); +} + +int arcompact_disassembler::handle0f_13_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "NEG_S",0); +} + +int arcompact_disassembler::handle0f_14_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "ADD1_S",0); +} + +int arcompact_disassembler::handle0f_15_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "ADD2_S",0); +} + +int arcompact_disassembler::handle0f_16_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "ADD3_S",0); +} + +int arcompact_disassembler::handle0f_18_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "ASL_S",0); +} + +int arcompact_disassembler::handle0f_19_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "LSR_S",0); +} + +int arcompact_disassembler::handle0f_1a_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "ASR_S",0); +} + +int arcompact_disassembler::handle0f_1b_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "ASL1_S",0); +} + +int arcompact_disassembler::handle0f_1c_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "ASR1_S",0); +} + +int arcompact_disassembler::handle0f_1d_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle0f_0x_helper_dasm(stream, pc, op, opcodes, "LSR1_S",0); +} + + + +int arcompact_disassembler::handle0f_1e_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) // special +{ // 0111 1uuu uuu1 1110 + int u = (op & 0x07e0)>>5; + util::stream_format( stream, "TRAP_S %02x",u); + return 2; +} + +int arcompact_disassembler::handle0f_1f_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) // special +{ + int u = (op & 0x07e0)>>5; op &= ~0x07e0; + + if (u == 0x003f) + { + util::stream_format(stream, "BRK_S"); + } + else + { + util::stream_format(stream, "",u); + } + return 2; +} + + +int arcompact_disassembler::handle_ld_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext, int shift, int swap) +{ + int breg, creg, u; + + COMMON16_GET_breg; + COMMON16_GET_creg; + COMMON16_GET_u5; + + REG_16BIT_RANGE(breg); + REG_16BIT_RANGE(creg); + + u <<= shift; + + if (!swap) util::stream_format(stream, "%s %s, [%s, 0x%02x] (%04x)", optext, regnames[creg], regnames[breg], u, op); + else util::stream_format(stream, "%s [%s, 0x%02x], %s (%04x)", optext, regnames[breg], u, regnames[creg], op); + return 2; + +} + + +int arcompact_disassembler::handle10_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle_ld_helper_dasm(stream, pc, op, opcodes, "LD_S", 2, 0); +} + +int arcompact_disassembler::handle11_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle_ld_helper_dasm(stream, pc, op, opcodes, "LDB_S", 0, 0); +} + +int arcompact_disassembler::handle12_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle_ld_helper_dasm(stream, pc, op, opcodes, "LDW_S", 1, 0); +} + +int arcompact_disassembler::handle13_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle_ld_helper_dasm(stream, pc, op, opcodes, "LDW_S.X", 1, 0); +} + +int arcompact_disassembler::handle14_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle_ld_helper_dasm(stream, pc, op, opcodes, "ST_S", 2, 1); +} + +int arcompact_disassembler::handle15_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle_ld_helper_dasm(stream, pc, op, opcodes, "STB_S", 0, 1); +} + +int arcompact_disassembler::handle16_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle_ld_helper_dasm(stream, pc, op, opcodes, "STW_S", 1, 1); +} + + +int arcompact_disassembler::handle_l7_0x_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext) +{ + int breg, u; + + COMMON16_GET_breg; COMMON16_GET_u5; REG_16BIT_RANGE(breg); @@ -1649,50 +2045,50 @@ int arcompact_handle_l7_0x_helper_dasm(DASM_OPS_16, const char* optext) } -int arcompact_handle17_00_dasm(DASM_OPS_16) +int arcompact_disassembler::handle17_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle_l7_0x_helper_dasm(DASM_PARAMS, "ASL_S"); + return handle_l7_0x_helper_dasm(stream, pc, op, opcodes, "ASL_S"); } -int arcompact_handle17_01_dasm(DASM_OPS_16) +int arcompact_disassembler::handle17_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle_l7_0x_helper_dasm(DASM_PARAMS, "LSR_S"); + return handle_l7_0x_helper_dasm(stream, pc, op, opcodes, "LSR_S"); } -int arcompact_handle17_02_dasm(DASM_OPS_16) +int arcompact_disassembler::handle17_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle_l7_0x_helper_dasm(DASM_PARAMS, "ASR_S"); + return handle_l7_0x_helper_dasm(stream, pc, op, opcodes, "ASR_S"); } -int arcompact_handle17_03_dasm(DASM_OPS_16) +int arcompact_disassembler::handle17_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle_l7_0x_helper_dasm(DASM_PARAMS, "SUB_S"); + return handle_l7_0x_helper_dasm(stream, pc, op, opcodes, "SUB_S"); } -int arcompact_handle17_04_dasm(DASM_OPS_16) +int arcompact_disassembler::handle17_04_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle_l7_0x_helper_dasm(DASM_PARAMS, "BSET_S"); + return handle_l7_0x_helper_dasm(stream, pc, op, opcodes, "BSET_S"); } -int arcompact_handle17_05_dasm(DASM_OPS_16) +int arcompact_disassembler::handle17_05_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle_l7_0x_helper_dasm(DASM_PARAMS, "BCLR_S"); + return handle_l7_0x_helper_dasm(stream, pc, op, opcodes, "BCLR_S"); } -int arcompact_handle17_06_dasm(DASM_OPS_16) +int arcompact_disassembler::handle17_06_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle_l7_0x_helper_dasm(DASM_PARAMS, "BSMK_S"); + return handle_l7_0x_helper_dasm(stream, pc, op, opcodes, "BSMK_S"); } -int arcompact_handle17_07_dasm(DASM_OPS_16) +int arcompact_disassembler::handle17_07_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle_l7_0x_helper_dasm(DASM_PARAMS, "BTST_S"); + return handle_l7_0x_helper_dasm(stream, pc, op, opcodes, "BTST_S"); } // op bits remaining for 0x18_xx subgroups 0x071f -int arcompact_handle18_0x_helper_dasm(DASM_OPS_16, const char* optext, int st, int format) +int arcompact_disassembler::handle18_0x_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext, int st, int format) { int breg, u; @@ -1712,33 +2108,33 @@ int arcompact_handle18_0x_helper_dasm(DASM_OPS_16, const char* optext, int st, i return 2; } -int arcompact_handle18_00_dasm(DASM_OPS_16) +int arcompact_disassembler::handle18_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle18_0x_helper_dasm(DASM_PARAMS, "LD_S", 0,0); + return handle18_0x_helper_dasm(stream, pc, op, opcodes, "LD_S", 0,0); } -int arcompact_handle18_01_dasm(DASM_OPS_16) +int arcompact_disassembler::handle18_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle18_0x_helper_dasm(DASM_PARAMS, "LDB_S", 0,0); + return handle18_0x_helper_dasm(stream, pc, op, opcodes, "LDB_S", 0,0); } -int arcompact_handle18_02_dasm(DASM_OPS_16) +int arcompact_disassembler::handle18_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle18_0x_helper_dasm(DASM_PARAMS, "ST_S", 1,0); + return handle18_0x_helper_dasm(stream, pc, op, opcodes, "ST_S", 1,0); } -int arcompact_handle18_03_dasm(DASM_OPS_16) +int arcompact_disassembler::handle18_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle18_0x_helper_dasm(DASM_PARAMS, "STB_S", 1,0); + return handle18_0x_helper_dasm(stream, pc, op, opcodes, "STB_S", 1,0); } -int arcompact_handle18_04_dasm(DASM_OPS_16) +int arcompact_disassembler::handle18_04_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { - return arcompact_handle18_0x_helper_dasm(DASM_PARAMS, "ADD_S", 1,1); // check format + return handle18_0x_helper_dasm(stream, pc, op, opcodes, "ADD_S", 1,1); // check format } // op bits remaining for 0x18_05_xx subgroups 0x001f -int arcompact_handle18_05_00_dasm(DASM_OPS_16) +int arcompact_disassembler::handle18_05_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int u; COMMON16_GET_u5; @@ -1748,7 +2144,7 @@ int arcompact_handle18_05_00_dasm(DASM_OPS_16) } -int arcompact_handle18_05_01_dasm(DASM_OPS_16) +int arcompact_disassembler::handle18_05_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int u; COMMON16_GET_u5; @@ -1758,7 +2154,7 @@ int arcompact_handle18_05_01_dasm(DASM_OPS_16) } // op bits remaining for 0x18_06_xx subgroups 0x0700 -int arcompact_handle18_06_01_dasm(DASM_OPS_16) +int arcompact_disassembler::handle18_06_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int breg; COMMON16_GET_breg @@ -1769,7 +2165,7 @@ int arcompact_handle18_06_01_dasm(DASM_OPS_16) return 2; } -int arcompact_handle18_06_11_dasm(DASM_OPS_16) +int arcompact_disassembler::handle18_06_11_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int res = (op & 0x0700) >> 8; op &= ~0x0700; // all bits now used @@ -1783,7 +2179,7 @@ int arcompact_handle18_06_11_dasm(DASM_OPS_16) } // op bits remaining for 0x18_07_xx subgroups 0x0700 -int arcompact_handle18_07_01_dasm(DASM_OPS_16) +int arcompact_disassembler::handle18_07_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int breg; COMMON16_GET_breg @@ -1795,7 +2191,7 @@ int arcompact_handle18_07_01_dasm(DASM_OPS_16) } -int arcompact_handle18_07_11_dasm(DASM_OPS_16) +int arcompact_disassembler::handle18_07_11_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int res = (op & 0x0700) >> 8; op &= ~0x0700; // all bits now used @@ -1809,7 +2205,7 @@ int arcompact_handle18_07_11_dasm(DASM_OPS_16) } -int arcompact_handle19_0x_helper_dasm(DASM_OPS_16, const char* optext, int shift, int format) +int arcompact_disassembler::handle19_0x_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext, int shift, int format) { int s; @@ -1831,12 +2227,28 @@ int arcompact_handle19_0x_helper_dasm(DASM_OPS_16, const char* optext, int shift return 2; } -int arcompact_handle19_00_dasm(DASM_OPS_16) { return arcompact_handle19_0x_helper_dasm(DASM_PARAMS, "LD_S", 2, 0); } -int arcompact_handle19_01_dasm(DASM_OPS_16) { return arcompact_handle19_0x_helper_dasm(DASM_PARAMS, "LDB_S", 0, 0); } -int arcompact_handle19_02_dasm(DASM_OPS_16) { return arcompact_handle19_0x_helper_dasm(DASM_PARAMS, "LDW_S", 1, 0); } -int arcompact_handle19_03_dasm(DASM_OPS_16) { return arcompact_handle19_0x_helper_dasm(DASM_PARAMS, "ADD_S", 2, 1); } +int arcompact_disassembler::handle19_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle19_0x_helper_dasm(stream, pc, op, opcodes, "LD_S", 2, 0); +} + +int arcompact_disassembler::handle19_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle19_0x_helper_dasm(stream, pc, op, opcodes, "LDB_S", 0, 0); +} + +int arcompact_disassembler::handle19_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle19_0x_helper_dasm(stream, pc, op, opcodes, "LDW_S", 1, 0); +} + +int arcompact_disassembler::handle19_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle19_0x_helper_dasm(stream, pc, op, opcodes, "ADD_S", 2, 1); +} + -int arcompact_handle1a_dasm(DASM_OPS_16) +int arcompact_disassembler::handle1a_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int breg, u; COMMON16_GET_breg; @@ -1848,7 +2260,7 @@ int arcompact_handle1a_dasm(DASM_OPS_16) return 2; } -int arcompact_handle1b_dasm(DASM_OPS_16) +int arcompact_disassembler::handle1b_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int breg, u; COMMON16_GET_breg; @@ -1859,7 +2271,7 @@ int arcompact_handle1b_dasm(DASM_OPS_16) return 2; } -int arcompact_handle1c_00_dasm(DASM_OPS_16) +int arcompact_disassembler::handle1c_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int breg, u; COMMON16_GET_breg; @@ -1870,7 +2282,7 @@ int arcompact_handle1c_00_dasm(DASM_OPS_16) return 2; } -int arcompact_handle1c_01_dasm(DASM_OPS_16) +int arcompact_disassembler::handle1c_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int breg, u; COMMON16_GET_breg; @@ -1881,7 +2293,7 @@ int arcompact_handle1c_01_dasm(DASM_OPS_16) return 2; } -int arcompact_handle1d_helper_dasm(DASM_OPS_16, const char* optext) +int arcompact_disassembler::handle1d_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext) { int breg; COMMON16_GET_breg; @@ -1895,11 +2307,19 @@ int arcompact_handle1d_helper_dasm(DASM_OPS_16, const char* optext) } -int arcompact_handle1d_00_dasm(DASM_OPS_16) { return arcompact_handle1d_helper_dasm(DASM_PARAMS,"BREQ_S"); } -int arcompact_handle1d_01_dasm(DASM_OPS_16) { return arcompact_handle1d_helper_dasm(DASM_PARAMS,"BRNE_S"); } +int arcompact_disassembler::handle1d_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle1d_helper_dasm(stream, pc, op, opcodes,"BREQ_S"); +} + +int arcompact_disassembler::handle1d_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle1d_helper_dasm(stream, pc, op, opcodes,"BRNE_S"); +} + -int arcompact_handle1e_0x_helper_dasm(DASM_OPS_16, const char* optext) +int arcompact_disassembler::handle1e_0x_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext) { int s = (op & 0x01ff) >> 0; op &= ~0x01ff; if (s & 0x100) s = -0x100 + (s & 0xff); @@ -1910,11 +2330,23 @@ int arcompact_handle1e_0x_helper_dasm(DASM_OPS_16, const char* optext) -int arcompact_handle1e_00_dasm(DASM_OPS_16) { return arcompact_handle1e_0x_helper_dasm(DASM_PARAMS, "B_S"); } -int arcompact_handle1e_01_dasm(DASM_OPS_16) { return arcompact_handle1e_0x_helper_dasm(DASM_PARAMS, "BEQ_S"); } -int arcompact_handle1e_02_dasm(DASM_OPS_16) { return arcompact_handle1e_0x_helper_dasm(DASM_PARAMS, "BNE_S"); } +int arcompact_disassembler::handle1e_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle1e_0x_helper_dasm(stream, pc, op, opcodes, "B_S"); +} + +int arcompact_disassembler::handle1e_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle1e_0x_helper_dasm(stream, pc, op, opcodes, "BEQ_S"); +} + +int arcompact_disassembler::handle1e_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle1e_0x_helper_dasm(stream, pc, op, opcodes, "BNE_S"); +} + -int arcompact_handle1e_03_0x_helper_dasm(DASM_OPS_16, const char* optext) +int arcompact_disassembler::handle1e_03_0x_helper_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes, const char* optext) { int s = (op & 0x003f) >> 0; op &= ~0x003f; if (s & 0x020) s = -0x20 + (s & 0x1f); @@ -1923,16 +2355,48 @@ int arcompact_handle1e_03_0x_helper_dasm(DASM_OPS_16, const char* optext) return 2; } -int arcompact_handle1e_03_00_dasm(DASM_OPS_16) { return arcompact_handle1e_03_0x_helper_dasm(DASM_PARAMS, "BGT_S"); } -int arcompact_handle1e_03_01_dasm(DASM_OPS_16) { return arcompact_handle1e_03_0x_helper_dasm(DASM_PARAMS, "BGE_S"); } -int arcompact_handle1e_03_02_dasm(DASM_OPS_16) { return arcompact_handle1e_03_0x_helper_dasm(DASM_PARAMS, "BLT_S"); } -int arcompact_handle1e_03_03_dasm(DASM_OPS_16) { return arcompact_handle1e_03_0x_helper_dasm(DASM_PARAMS, "BLE_S"); } -int arcompact_handle1e_03_04_dasm(DASM_OPS_16) { return arcompact_handle1e_03_0x_helper_dasm(DASM_PARAMS, "BHI_S"); } -int arcompact_handle1e_03_05_dasm(DASM_OPS_16) { return arcompact_handle1e_03_0x_helper_dasm(DASM_PARAMS, "BHS_S"); } -int arcompact_handle1e_03_06_dasm(DASM_OPS_16) { return arcompact_handle1e_03_0x_helper_dasm(DASM_PARAMS, "BLO_S"); } -int arcompact_handle1e_03_07_dasm(DASM_OPS_16) { return arcompact_handle1e_03_0x_helper_dasm(DASM_PARAMS, "BLS_S"); } +int arcompact_disassembler::handle1e_03_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle1e_03_0x_helper_dasm(stream, pc, op, opcodes, "BGT_S"); +} + +int arcompact_disassembler::handle1e_03_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle1e_03_0x_helper_dasm(stream, pc, op, opcodes, "BGE_S"); +} + +int arcompact_disassembler::handle1e_03_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle1e_03_0x_helper_dasm(stream, pc, op, opcodes, "BLT_S"); +} + +int arcompact_disassembler::handle1e_03_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle1e_03_0x_helper_dasm(stream, pc, op, opcodes, "BLE_S"); +} + +int arcompact_disassembler::handle1e_03_04_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle1e_03_0x_helper_dasm(stream, pc, op, opcodes, "BHI_S"); +} + +int arcompact_disassembler::handle1e_03_05_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle1e_03_0x_helper_dasm(stream, pc, op, opcodes, "BHS_S"); +} + +int arcompact_disassembler::handle1e_03_06_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle1e_03_0x_helper_dasm(stream, pc, op, opcodes, "BLO_S"); +} + +int arcompact_disassembler::handle1e_03_07_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + return handle1e_03_0x_helper_dasm(stream, pc, op, opcodes, "BLS_S"); +} + -int arcompact_handle1f_dasm(DASM_OPS_16) +int arcompact_disassembler::handle1f_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) { int s = (op & 0x07ff) >> 0; op &= ~0x07ff; if (s & 0x400) s = -0x400 + (s & 0x3ff); @@ -1947,411 +2411,2340 @@ int arcompact_handle1f_dasm(DASM_OPS_16) * * ************************************************************************************************************************************/ -int arcompact_handle01_01_00_06_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle01_01_00_07_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle01_01_00_08_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle01_01_00_09_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle01_01_00_0a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle01_01_00_0b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle01_01_00_0c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle01_01_00_0d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } - -int arcompact_handle01_01_01_06_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle01_01_01_07_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle01_01_01_08_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle01_01_01_09_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle01_01_01_0a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle01_01_01_0b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle01_01_01_0c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle01_01_01_0d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } - - -int arcompact_handle04_1e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_1f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } - -int arcompact_handle04_24_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_25_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_26_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_27_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } - -int arcompact_handle04_2c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } - -int arcompact_handle04_2f_0d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_0e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_0f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_10_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_11_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_12_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_13_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_14_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_15_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_16_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_17_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_18_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_19_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_1a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_1b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_1c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_1d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_1e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_1f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_20_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_21_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_22_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_23_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_24_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_25_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_26_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_27_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_28_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_29_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_2a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_2b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_2c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_2d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_2e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_2f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_30_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_31_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_32_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_33_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_34_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_35_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_36_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_37_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_38_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_39_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } - - - -int arcompact_handle05_2f_09_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_0a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_0b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_0c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_0d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_0e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_0f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_10_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_11_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_12_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_13_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_14_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_15_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_16_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_17_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_18_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_19_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_1a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_1b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_1c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_1d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_1e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_1f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_20_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_21_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_22_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_23_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_24_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_25_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_26_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_27_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_28_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_29_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_2a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_2b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_2c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_2d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_2e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_2f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_30_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_31_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_32_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_33_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_34_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_35_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_36_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_37_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_38_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_39_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } - - -int arcompact_handle04_2f_3f_00_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_06_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_07_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_08_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_09_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_0a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_0b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_0c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_0d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_0e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_0f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_10_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_11_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_12_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_13_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_14_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_15_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_16_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_17_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_18_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_19_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_1a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_1b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_1c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_1d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_1e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_1f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_20_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_21_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_22_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_23_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_24_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_25_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_26_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_27_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_28_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_29_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_2a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_2b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_2c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_2d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_2e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_2f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_30_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_31_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_32_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_33_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_34_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_35_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_36_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_37_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_38_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_39_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_3a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_3b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_3c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_3d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_3e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_2f_3f_3f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } - -int arcompact_handle05_2f_3f_00_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_01_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_02_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_03_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_04_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_05_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_06_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_07_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_08_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_09_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_0a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_0b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_0c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_0d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_0e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_0f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_10_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_11_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_12_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_13_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_14_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_15_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_16_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_17_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_18_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_19_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_1a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_1b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_1c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_1d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_1e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_1f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_20_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_21_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_22_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_23_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_24_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_25_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_26_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_27_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_28_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_29_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_2a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_2b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_2c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_2d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_2e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_2f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_30_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_31_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_32_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_33_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_34_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_35_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_36_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_37_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_38_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_39_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_3a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_3b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_3c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_3d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_3e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2f_3f_3f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } - - - - -int arcompact_handle04_38_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_39_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_3a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_3b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_3c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_3d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_3e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle04_3f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } - - -int arcompact_handle05_09_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_0c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_0d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_0e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_0f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_10_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_11_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_12_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_13_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_14_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_15_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_16_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_17_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_18_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_19_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_1a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_1b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_1c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_1d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_1e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_1f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_20_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_21_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_22_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_23_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_24_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_25_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_26_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_27_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } - -int arcompact_handle05_2a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_2e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } - -int arcompact_handle05_30_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_31_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_32_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_33_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_34_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_35_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_36_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_37_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_38_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_39_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_3a_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_3b_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_3c_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_3d_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_3e_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } -int arcompact_handle05_3f_dasm(DASM_OPS_32) { util::stream_format(stream, " (%08x)", op); return 4; } - -int arcompact_handle0f_00_04_dasm(DASM_OPS_16) { util::stream_format(stream, " (%08x)", op); return 2; } -int arcompact_handle0f_00_05_dasm(DASM_OPS_16) { util::stream_format(stream, " (%08x)", op); return 2; } -int arcompact_handle0f_00_07_02_dasm(DASM_OPS_16) { util::stream_format(stream, " (%08x)", op); return 2; } -int arcompact_handle0f_00_07_03_dasm(DASM_OPS_16) { util::stream_format(stream, " (%08x)", op); return 2; } -int arcompact_handle0f_01_dasm(DASM_OPS_16) { util::stream_format(stream, " (%08x)", op); return 2; } -int arcompact_handle0f_03_dasm(DASM_OPS_16) { util::stream_format(stream, " (%08x)", op); return 2; } -int arcompact_handle0f_08_dasm(DASM_OPS_16) { util::stream_format(stream, " (%08x)", op); return 2; } -int arcompact_handle0f_09_dasm(DASM_OPS_16) { util::stream_format(stream, " (%08x)", op); return 2; } -int arcompact_handle0f_0a_dasm(DASM_OPS_16) { util::stream_format(stream, " (%08x)", op); return 2; } -int arcompact_handle0f_17_dasm(DASM_OPS_16) { util::stream_format(stream, " (%08x)", op); return 2; } - -int arcompact_handle18_05_02_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_05_03_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_05_04_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_05_05_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_05_06_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_05_07_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_00_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_02_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_03_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_04_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_05_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_06_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_07_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_08_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_09_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_0a_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_0b_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_0c_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_0d_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_0e_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_0f_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_10_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_12_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_13_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_14_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_15_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_16_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_17_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_18_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_19_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_1a_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_1b_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_1c_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_1d_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_1e_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_06_1f_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_00_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_02_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_03_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_04_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_05_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_06_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_07_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_08_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_09_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_0a_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_0b_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_0c_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_0d_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_0e_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_0f_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_10_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_12_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_13_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_14_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_15_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_16_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_17_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_18_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_19_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_1a_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_1b_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_1c_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_1d_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_1e_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } -int arcompact_handle18_07_1f_dasm(DASM_OPS_16) { util::stream_format(stream, " (%04x)", op); return 2; } +int arcompact_disassembler::handle01_01_00_06_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle01_01_00_07_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle01_01_00_08_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle01_01_00_09_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle01_01_00_0a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle01_01_00_0b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle01_01_00_0c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle01_01_00_0d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + + +int arcompact_disassembler::handle01_01_01_06_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle01_01_01_07_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle01_01_01_08_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle01_01_01_09_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle01_01_01_0a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle01_01_01_0b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle01_01_01_0c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle01_01_01_0d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + + + +int arcompact_disassembler::handle04_1e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_1f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + + +int arcompact_disassembler::handle04_24_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_25_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_26_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_27_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + + +int arcompact_disassembler::handle04_2c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + + +int arcompact_disassembler::handle04_2f_0d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_0e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_0f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_10_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_11_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_12_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_13_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_14_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_15_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_16_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_17_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_18_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_19_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_1a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_1b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_1c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_1d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_1e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_1f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_20_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_21_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_22_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_23_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_24_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_25_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_26_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_27_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_28_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_29_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_2a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_2b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_2c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_2d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_2e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_2f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_30_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_31_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_32_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_33_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_34_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_35_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_36_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_37_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_38_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_39_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + + + + +int arcompact_disassembler::handle05_2f_09_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_0a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_0b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_0c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_0d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_0e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_0f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_10_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_11_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_12_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_13_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_14_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_15_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_16_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_17_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_18_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_19_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_1a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_1b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_1c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_1d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_1e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_1f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_20_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_21_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_22_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_23_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_24_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_25_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_26_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_27_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_28_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_29_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_2a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_2b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_2c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_2d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_2e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_2f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_30_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_31_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_32_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_33_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_34_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_35_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_36_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_37_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_38_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_39_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + + + +int arcompact_disassembler::handle04_2f_3f_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_06_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_07_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_08_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_09_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_0a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_0b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_0c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_0d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_0e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_0f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_10_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_11_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_12_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_13_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_14_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_15_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_16_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_17_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_18_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_19_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_1a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_1b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_1c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_1d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_1e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_1f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_20_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_21_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_22_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_23_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_24_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_25_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_26_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_27_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_28_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_29_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_2a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_2b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_2c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_2d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_2e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_2f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_30_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_31_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_32_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_33_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_34_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_35_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_36_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_37_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_38_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_39_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_3a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_3b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_3c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_3d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_3e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_2f_3f_3f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + + +int arcompact_disassembler::handle05_2f_3f_00_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_01_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_02_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_03_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_04_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_05_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_06_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_07_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_08_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_09_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_0a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_0b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_0c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_0d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_0e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_0f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_10_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_11_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_12_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_13_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_14_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_15_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_16_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_17_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_18_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_19_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_1a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_1b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_1c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_1d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_1e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_1f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_20_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_21_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_22_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_23_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_24_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_25_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_26_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_27_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_28_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_29_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_2a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_2b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_2c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_2d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_2e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_2f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_30_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_31_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_32_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_33_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_34_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_35_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_36_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_37_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_38_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_39_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_3a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_3b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_3c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_3d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_3e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2f_3f_3f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + + + + + +int arcompact_disassembler::handle04_38_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_39_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_3a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_3b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_3c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_3d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_3e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle04_3f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + + + +int arcompact_disassembler::handle05_09_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_0c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_0d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_0e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_0f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_10_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_11_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_12_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_13_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_14_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_15_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_16_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_17_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_18_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_19_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_1a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_1b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_1c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_1d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_1e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_1f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_20_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_21_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_22_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_23_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_24_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_25_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_26_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_27_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + + +int arcompact_disassembler::handle05_2a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_2e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + + +int arcompact_disassembler::handle05_30_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_31_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_32_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_33_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_34_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_35_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_36_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_37_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_38_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_39_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_3a_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_3b_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_3c_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_3d_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_3e_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + +int arcompact_disassembler::handle05_3f_dasm(std::ostream &stream, offs_t pc, uint32_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 4; +} + + +int arcompact_disassembler::handle0f_00_04_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 2; +} + +int arcompact_disassembler::handle0f_00_05_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 2; +} + +int arcompact_disassembler::handle0f_00_07_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 2; +} + +int arcompact_disassembler::handle0f_00_07_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 2; +} + +int arcompact_disassembler::handle0f_01_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 2; +} + +int arcompact_disassembler::handle0f_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 2; +} + +int arcompact_disassembler::handle0f_08_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 2; +} + +int arcompact_disassembler::handle0f_09_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 2; +} + +int arcompact_disassembler::handle0f_0a_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 2; +} + +int arcompact_disassembler::handle0f_17_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%08x)", op); + return 2; +} + + +int arcompact_disassembler::handle18_05_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_05_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_05_04_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_05_05_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_05_06_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_05_07_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_04_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_05_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_06_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_07_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_08_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_09_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_0a_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_0b_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_0c_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_0d_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_0e_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_0f_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_10_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_12_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_13_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_14_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_15_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_16_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_17_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_18_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_19_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_1a_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_1b_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_1c_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_1d_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_1e_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_06_1f_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_00_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_02_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_03_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_04_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_05_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_06_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_07_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_08_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_09_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_0a_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_0b_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_0c_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_0d_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_0e_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_0f_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_10_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_12_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_13_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_14_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_15_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_16_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_17_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_18_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_19_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_1a_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_1b_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_1c_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_1d_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_1e_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} + +int arcompact_disassembler::handle18_07_1f_dasm(std::ostream &stream, offs_t pc, uint16_t op, const data_buffer &opcodes) +{ + util::stream_format(stream, " (%04x)", op); + return 2; +} diff --git a/src/devices/cpu/arcompact/arcompactdasm_ops.h b/src/devices/cpu/arcompact/arcompactdasm_ops.h deleted file mode 100644 index 84b79e6e1e7..00000000000 --- a/src/devices/cpu/arcompact/arcompactdasm_ops.h +++ /dev/null @@ -1,642 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:David Haywood - -/************************************************************************************************************************************ -* * -* individual opcode handlers (disassembly) * -* * -************************************************************************************************************************************/ - -#include "arcompact_common.h" - -#define DASM_OPS_16 std::ostream &stream, offs_t pc, uint16_t op, const uint8_t* oprom -#define DASM_OPS_32 std::ostream &stream, offs_t pc, uint32_t op, const uint8_t* oprom -#define DASM_PARAMS stream, pc, op, oprom - -#define LIMM_REG 62 - -#define GET_LIMM_32 \ - limm = oprom[6] | (oprom[7] << 8); \ - limm |= (oprom[4] << 16) | (oprom[5] << 24); - -int arcompact_handle00_00_dasm(DASM_OPS_32); -int arcompact_handle00_01_dasm(DASM_OPS_32); -int arcompact_handle01_00_00dasm(DASM_OPS_32); -int arcompact_handle01_00_01dasm(DASM_OPS_32); -int arcompact_handle01_01_00_00_dasm(DASM_OPS_32); -int arcompact_handle01_01_00_01_dasm(DASM_OPS_32); -int arcompact_handle01_01_00_02_dasm(DASM_OPS_32); -int arcompact_handle01_01_00_03_dasm(DASM_OPS_32); -int arcompact_handle01_01_00_04_dasm(DASM_OPS_32); -int arcompact_handle01_01_00_05_dasm(DASM_OPS_32); -int arcompact_handle01_01_00_0e_dasm(DASM_OPS_32); -int arcompact_handle01_01_00_0f_dasm(DASM_OPS_32); -int arcompact_handle01_01_01_00_dasm(DASM_OPS_32); -int arcompact_handle01_01_01_01_dasm(DASM_OPS_32); -int arcompact_handle01_01_01_02_dasm(DASM_OPS_32); -int arcompact_handle01_01_01_03_dasm(DASM_OPS_32); -int arcompact_handle01_01_01_04_dasm(DASM_OPS_32); -int arcompact_handle01_01_01_05_dasm(DASM_OPS_32); -int arcompact_handle01_01_01_0e_dasm(DASM_OPS_32); -int arcompact_handle01_01_01_0f_dasm(DASM_OPS_32); -int arcompact_handle02_dasm(DASM_OPS_32); -int arcompact_handle03_dasm(DASM_OPS_32); -int arcompact_handle04_00_dasm(DASM_OPS_32); -int arcompact_handle04_01_dasm(DASM_OPS_32); -int arcompact_handle04_02_dasm(DASM_OPS_32); -int arcompact_handle04_03_dasm(DASM_OPS_32); -int arcompact_handle04_04_dasm(DASM_OPS_32); -int arcompact_handle04_05_dasm(DASM_OPS_32); -int arcompact_handle04_06_dasm(DASM_OPS_32); -int arcompact_handle04_07_dasm(DASM_OPS_32); -int arcompact_handle04_08_dasm(DASM_OPS_32); -int arcompact_handle04_09_dasm(DASM_OPS_32); -int arcompact_handle04_0a_dasm(DASM_OPS_32); -int arcompact_handle04_0b_dasm(DASM_OPS_32); -int arcompact_handle04_0c_dasm(DASM_OPS_32); -int arcompact_handle04_0d_dasm(DASM_OPS_32); -int arcompact_handle04_0e_dasm(DASM_OPS_32); -int arcompact_handle04_0f_dasm(DASM_OPS_32); -int arcompact_handle04_10_dasm(DASM_OPS_32); -int arcompact_handle04_11_dasm(DASM_OPS_32); -int arcompact_handle04_12_dasm(DASM_OPS_32); -int arcompact_handle04_13_dasm(DASM_OPS_32); -int arcompact_handle04_14_dasm(DASM_OPS_32); -int arcompact_handle04_15_dasm(DASM_OPS_32); -int arcompact_handle04_16_dasm(DASM_OPS_32); -int arcompact_handle04_17_dasm(DASM_OPS_32); -int arcompact_handle04_18_dasm(DASM_OPS_32); -int arcompact_handle04_19_dasm(DASM_OPS_32); -int arcompact_handle04_1a_dasm(DASM_OPS_32); -int arcompact_handle04_1b_dasm(DASM_OPS_32); -int arcompact_handle04_1c_dasm(DASM_OPS_32); -int arcompact_handle04_1d_dasm(DASM_OPS_32); -int arcompact_handle04_20_dasm(DASM_OPS_32); -int arcompact_handle04_21_dasm(DASM_OPS_32); -int arcompact_handle04_22_dasm(DASM_OPS_32); -int arcompact_handle04_23_dasm(DASM_OPS_32); -int arcompact_handle04_28_dasm(DASM_OPS_32); -int arcompact_handle04_29_dasm(DASM_OPS_32); -int arcompact_handle04_2a_dasm(DASM_OPS_32); -int arcompact_handle04_2b_dasm(DASM_OPS_32); -int arcompact_handle04_2f_00_dasm(DASM_OPS_32); -int arcompact_handle04_2f_01_dasm(DASM_OPS_32); -int arcompact_handle04_2f_02_dasm(DASM_OPS_32); -int arcompact_handle04_2f_03_dasm(DASM_OPS_32); -int arcompact_handle04_2f_04_dasm(DASM_OPS_32); -int arcompact_handle04_2f_05_dasm(DASM_OPS_32); -int arcompact_handle04_2f_06_dasm(DASM_OPS_32); -int arcompact_handle04_2f_07_dasm(DASM_OPS_32); -int arcompact_handle04_2f_08_dasm(DASM_OPS_32); -int arcompact_handle04_2f_09_dasm(DASM_OPS_32); -int arcompact_handle04_2f_0a_dasm(DASM_OPS_32); -int arcompact_handle04_2f_0b_dasm(DASM_OPS_32); -int arcompact_handle04_2f_0c_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_01_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_02_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_03_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_04_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_05_dasm(DASM_OPS_32); -int arcompact_handle04_30_dasm(DASM_OPS_32); -int arcompact_handle04_31_dasm(DASM_OPS_32); -int arcompact_handle04_32_dasm(DASM_OPS_32); -int arcompact_handle04_33_dasm(DASM_OPS_32); -int arcompact_handle04_34_dasm(DASM_OPS_32); -int arcompact_handle04_35_dasm(DASM_OPS_32); -int arcompact_handle04_36_dasm(DASM_OPS_32); -int arcompact_handle04_37_dasm(DASM_OPS_32); -int arcompact_handle05_00_dasm(DASM_OPS_32); -int arcompact_handle05_01_dasm(DASM_OPS_32); -int arcompact_handle05_02_dasm(DASM_OPS_32); -int arcompact_handle05_03_dasm(DASM_OPS_32); -int arcompact_handle05_04_dasm(DASM_OPS_32); -int arcompact_handle05_05_dasm(DASM_OPS_32); -int arcompact_handle05_06_dasm(DASM_OPS_32); -int arcompact_handle05_07_dasm(DASM_OPS_32); -int arcompact_handle05_08_dasm(DASM_OPS_32); -int arcompact_handle05_0a_dasm(DASM_OPS_32); -int arcompact_handle05_0b_dasm(DASM_OPS_32); -int arcompact_handle05_28_dasm(DASM_OPS_32); -int arcompact_handle05_29_dasm(DASM_OPS_32); - -int arcompact_handle06_dasm(DASM_OPS_32); -int arcompact_handle07_dasm(DASM_OPS_32); -int arcompact_handle08_dasm(DASM_OPS_32); -int arcompact_handle09_dasm(DASM_OPS_32); -int arcompact_handle0a_dasm(DASM_OPS_32); -int arcompact_handle0b_dasm(DASM_OPS_32); - -int arcompact_handle0c_00_dasm(DASM_OPS_16); -int arcompact_handle0c_01_dasm(DASM_OPS_16); -int arcompact_handle0c_02_dasm(DASM_OPS_16); -int arcompact_handle0c_03_dasm(DASM_OPS_16); -int arcompact_handle0d_00_dasm(DASM_OPS_16); -int arcompact_handle0d_01_dasm(DASM_OPS_16); -int arcompact_handle0d_02_dasm(DASM_OPS_16); -int arcompact_handle0d_03_dasm(DASM_OPS_16); -int arcompact_handle0e_00_dasm(DASM_OPS_16); -int arcompact_handle0e_01_dasm(DASM_OPS_16); -int arcompact_handle0e_02_dasm(DASM_OPS_16); -int arcompact_handle0e_03_dasm(DASM_OPS_16); -int arcompact_handle0f_00_00_dasm(DASM_OPS_16); -int arcompact_handle0f_00_01_dasm(DASM_OPS_16); -int arcompact_handle0f_00_02_dasm(DASM_OPS_16); -int arcompact_handle0f_00_03_dasm(DASM_OPS_16); -int arcompact_handle0f_00_06_dasm(DASM_OPS_16); -int arcompact_handle0f_00_07_00_dasm(DASM_OPS_16); -int arcompact_handle0f_00_07_01_dasm(DASM_OPS_16); -int arcompact_handle0f_00_07_04_dasm(DASM_OPS_16); -int arcompact_handle0f_00_07_05_dasm(DASM_OPS_16); -int arcompact_handle0f_00_07_06_dasm(DASM_OPS_16); -int arcompact_handle0f_00_07_07_dasm(DASM_OPS_16); -int arcompact_handle0f_02_dasm(DASM_OPS_16); -int arcompact_handle0f_04_dasm(DASM_OPS_16); -int arcompact_handle0f_05_dasm(DASM_OPS_16); -int arcompact_handle0f_06_dasm(DASM_OPS_16); -int arcompact_handle0f_07_dasm(DASM_OPS_16); -int arcompact_handle0f_0b_dasm(DASM_OPS_16); -int arcompact_handle0f_0c_dasm(DASM_OPS_16); -int arcompact_handle0f_0d_dasm(DASM_OPS_16); -int arcompact_handle0f_0e_dasm(DASM_OPS_16); -int arcompact_handle0f_0f_dasm(DASM_OPS_16); -int arcompact_handle0f_10_dasm(DASM_OPS_16); -int arcompact_handle0f_11_dasm(DASM_OPS_16); -int arcompact_handle0f_12_dasm(DASM_OPS_16); -int arcompact_handle0f_13_dasm(DASM_OPS_16); -int arcompact_handle0f_14_dasm(DASM_OPS_16); -int arcompact_handle0f_15_dasm(DASM_OPS_16); -int arcompact_handle0f_16_dasm(DASM_OPS_16); -int arcompact_handle0f_18_dasm(DASM_OPS_16); -int arcompact_handle0f_19_dasm(DASM_OPS_16); -int arcompact_handle0f_1a_dasm(DASM_OPS_16); -int arcompact_handle0f_1b_dasm(DASM_OPS_16); -int arcompact_handle0f_1c_dasm(DASM_OPS_16); -int arcompact_handle0f_1d_dasm(DASM_OPS_16); -int arcompact_handle0f_1e_dasm(DASM_OPS_16); -int arcompact_handle0f_1f_dasm(DASM_OPS_16); -int arcompact_handle10_dasm(DASM_OPS_16); -int arcompact_handle11_dasm(DASM_OPS_16); -int arcompact_handle12_dasm(DASM_OPS_16); -int arcompact_handle13_dasm(DASM_OPS_16); -int arcompact_handle14_dasm(DASM_OPS_16); -int arcompact_handle15_dasm(DASM_OPS_16); -int arcompact_handle16_dasm(DASM_OPS_16); -int arcompact_handle17_00_dasm(DASM_OPS_16); -int arcompact_handle17_01_dasm(DASM_OPS_16); -int arcompact_handle17_02_dasm(DASM_OPS_16); -int arcompact_handle17_03_dasm(DASM_OPS_16); -int arcompact_handle17_04_dasm(DASM_OPS_16); -int arcompact_handle17_05_dasm(DASM_OPS_16); -int arcompact_handle17_06_dasm(DASM_OPS_16); -int arcompact_handle17_07_dasm(DASM_OPS_16); -int arcompact_handle18_00_dasm(DASM_OPS_16); -int arcompact_handle18_01_dasm(DASM_OPS_16); -int arcompact_handle18_02_dasm(DASM_OPS_16); -int arcompact_handle18_03_dasm(DASM_OPS_16); -int arcompact_handle18_04_dasm(DASM_OPS_16); -int arcompact_handle18_05_00_dasm(DASM_OPS_16); -int arcompact_handle18_05_01_dasm(DASM_OPS_16); -int arcompact_handle18_06_01_dasm(DASM_OPS_16); -int arcompact_handle18_06_11_dasm(DASM_OPS_16); -int arcompact_handle18_07_01_dasm(DASM_OPS_16); -int arcompact_handle18_07_11_dasm(DASM_OPS_16); -int arcompact_handle19_00_dasm(DASM_OPS_16); -int arcompact_handle19_01_dasm(DASM_OPS_16); -int arcompact_handle19_02_dasm(DASM_OPS_16); -int arcompact_handle19_03_dasm(DASM_OPS_16); -int arcompact_handle1a_dasm(DASM_OPS_16); -int arcompact_handle1b_dasm(DASM_OPS_16); -int arcompact_handle1c_00_dasm(DASM_OPS_16); -int arcompact_handle1c_01_dasm(DASM_OPS_16); -int arcompact_handle1d_00_dasm(DASM_OPS_16); -int arcompact_handle1d_01_dasm(DASM_OPS_16); -int arcompact_handle1e_00_dasm(DASM_OPS_16); -int arcompact_handle1e_01_dasm(DASM_OPS_16); -int arcompact_handle1e_02_dasm(DASM_OPS_16); -int arcompact_handle1e_03_00_dasm(DASM_OPS_16); -int arcompact_handle1e_03_01_dasm(DASM_OPS_16); -int arcompact_handle1e_03_02_dasm(DASM_OPS_16); -int arcompact_handle1e_03_03_dasm(DASM_OPS_16); -int arcompact_handle1e_03_04_dasm(DASM_OPS_16); -int arcompact_handle1e_03_05_dasm(DASM_OPS_16); -int arcompact_handle1e_03_06_dasm(DASM_OPS_16); -int arcompact_handle1e_03_07_dasm(DASM_OPS_16); -int arcompact_handle1f_dasm(DASM_OPS_16); - -/************************************************************************************************************************************ -* * -* illegal opcode handlers (disassembly) * -* * -************************************************************************************************************************************/ - -int arcompact_handle01_01_00_06_dasm(DASM_OPS_32); -int arcompact_handle01_01_00_07_dasm(DASM_OPS_32); -int arcompact_handle01_01_00_08_dasm(DASM_OPS_32); -int arcompact_handle01_01_00_09_dasm(DASM_OPS_32); -int arcompact_handle01_01_00_0a_dasm(DASM_OPS_32); -int arcompact_handle01_01_00_0b_dasm(DASM_OPS_32); -int arcompact_handle01_01_00_0c_dasm(DASM_OPS_32); -int arcompact_handle01_01_00_0d_dasm(DASM_OPS_32); - -int arcompact_handle01_01_01_06_dasm(DASM_OPS_32); -int arcompact_handle01_01_01_07_dasm(DASM_OPS_32); -int arcompact_handle01_01_01_08_dasm(DASM_OPS_32); -int arcompact_handle01_01_01_09_dasm(DASM_OPS_32); -int arcompact_handle01_01_01_0a_dasm(DASM_OPS_32); -int arcompact_handle01_01_01_0b_dasm(DASM_OPS_32); -int arcompact_handle01_01_01_0c_dasm(DASM_OPS_32); -int arcompact_handle01_01_01_0d_dasm(DASM_OPS_32); - - -int arcompact_handle04_1e_dasm(DASM_OPS_32); -int arcompact_handle04_1f_dasm(DASM_OPS_32); - -int arcompact_handle04_24_dasm(DASM_OPS_32); -int arcompact_handle04_25_dasm(DASM_OPS_32); -int arcompact_handle04_26_dasm(DASM_OPS_32); -int arcompact_handle04_27_dasm(DASM_OPS_32); - -int arcompact_handle04_2c_dasm(DASM_OPS_32); -int arcompact_handle04_2d_dasm(DASM_OPS_32); -int arcompact_handle04_2e_dasm(DASM_OPS_32); - -int arcompact_handle04_2f_0d_dasm(DASM_OPS_32); -int arcompact_handle04_2f_0e_dasm(DASM_OPS_32); -int arcompact_handle04_2f_0f_dasm(DASM_OPS_32); -int arcompact_handle04_2f_10_dasm(DASM_OPS_32); -int arcompact_handle04_2f_11_dasm(DASM_OPS_32); -int arcompact_handle04_2f_12_dasm(DASM_OPS_32); -int arcompact_handle04_2f_13_dasm(DASM_OPS_32); -int arcompact_handle04_2f_14_dasm(DASM_OPS_32); -int arcompact_handle04_2f_15_dasm(DASM_OPS_32); -int arcompact_handle04_2f_16_dasm(DASM_OPS_32); -int arcompact_handle04_2f_17_dasm(DASM_OPS_32); -int arcompact_handle04_2f_18_dasm(DASM_OPS_32); -int arcompact_handle04_2f_19_dasm(DASM_OPS_32); -int arcompact_handle04_2f_1a_dasm(DASM_OPS_32); -int arcompact_handle04_2f_1b_dasm(DASM_OPS_32); -int arcompact_handle04_2f_1c_dasm(DASM_OPS_32); -int arcompact_handle04_2f_1d_dasm(DASM_OPS_32); -int arcompact_handle04_2f_1e_dasm(DASM_OPS_32); -int arcompact_handle04_2f_1f_dasm(DASM_OPS_32); -int arcompact_handle04_2f_20_dasm(DASM_OPS_32); -int arcompact_handle04_2f_21_dasm(DASM_OPS_32); -int arcompact_handle04_2f_22_dasm(DASM_OPS_32); -int arcompact_handle04_2f_23_dasm(DASM_OPS_32); -int arcompact_handle04_2f_24_dasm(DASM_OPS_32); -int arcompact_handle04_2f_25_dasm(DASM_OPS_32); -int arcompact_handle04_2f_26_dasm(DASM_OPS_32); -int arcompact_handle04_2f_27_dasm(DASM_OPS_32); -int arcompact_handle04_2f_28_dasm(DASM_OPS_32); -int arcompact_handle04_2f_29_dasm(DASM_OPS_32); -int arcompact_handle04_2f_2a_dasm(DASM_OPS_32); -int arcompact_handle04_2f_2b_dasm(DASM_OPS_32); -int arcompact_handle04_2f_2c_dasm(DASM_OPS_32); -int arcompact_handle04_2f_2d_dasm(DASM_OPS_32); -int arcompact_handle04_2f_2e_dasm(DASM_OPS_32); -int arcompact_handle04_2f_2f_dasm(DASM_OPS_32); -int arcompact_handle04_2f_30_dasm(DASM_OPS_32); -int arcompact_handle04_2f_31_dasm(DASM_OPS_32); -int arcompact_handle04_2f_32_dasm(DASM_OPS_32); -int arcompact_handle04_2f_33_dasm(DASM_OPS_32); -int arcompact_handle04_2f_34_dasm(DASM_OPS_32); -int arcompact_handle04_2f_35_dasm(DASM_OPS_32); -int arcompact_handle04_2f_36_dasm(DASM_OPS_32); -int arcompact_handle04_2f_37_dasm(DASM_OPS_32); -int arcompact_handle04_2f_38_dasm(DASM_OPS_32); -int arcompact_handle04_2f_39_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3a_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3b_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3c_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3d_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3e_dasm(DASM_OPS_32); - -int arcompact_handle04_2f_3f_00_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_06_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_07_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_08_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_09_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_0a_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_0b_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_0c_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_0d_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_0e_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_0f_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_10_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_11_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_12_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_13_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_14_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_15_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_16_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_17_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_18_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_19_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_1a_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_1b_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_1c_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_1d_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_1e_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_1f_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_20_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_21_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_22_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_23_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_24_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_25_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_26_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_27_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_28_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_29_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_2a_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_2b_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_2c_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_2d_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_2e_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_2f_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_30_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_31_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_32_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_33_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_34_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_35_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_36_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_37_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_38_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_39_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_3a_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_3b_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_3c_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_3d_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_3e_dasm(DASM_OPS_32); -int arcompact_handle04_2f_3f_3f_dasm(DASM_OPS_32); - -int arcompact_handle05_2f_00_dasm(DASM_OPS_32); -int arcompact_handle05_2f_01_dasm(DASM_OPS_32); -int arcompact_handle05_2f_02_dasm(DASM_OPS_32); -int arcompact_handle05_2f_03_dasm(DASM_OPS_32); -int arcompact_handle05_2f_04_dasm(DASM_OPS_32); -int arcompact_handle05_2f_05_dasm(DASM_OPS_32); -int arcompact_handle05_2f_06_dasm(DASM_OPS_32); -int arcompact_handle05_2f_07_dasm(DASM_OPS_32); -int arcompact_handle05_2f_08_dasm(DASM_OPS_32); -int arcompact_handle05_2f_09_dasm(DASM_OPS_32); -int arcompact_handle05_2f_0a_dasm(DASM_OPS_32); -int arcompact_handle05_2f_0b_dasm(DASM_OPS_32); -int arcompact_handle05_2f_0c_dasm(DASM_OPS_32); -int arcompact_handle05_2f_0d_dasm(DASM_OPS_32); -int arcompact_handle05_2f_0e_dasm(DASM_OPS_32); -int arcompact_handle05_2f_0f_dasm(DASM_OPS_32); -int arcompact_handle05_2f_10_dasm(DASM_OPS_32); -int arcompact_handle05_2f_11_dasm(DASM_OPS_32); -int arcompact_handle05_2f_12_dasm(DASM_OPS_32); -int arcompact_handle05_2f_13_dasm(DASM_OPS_32); -int arcompact_handle05_2f_14_dasm(DASM_OPS_32); -int arcompact_handle05_2f_15_dasm(DASM_OPS_32); -int arcompact_handle05_2f_16_dasm(DASM_OPS_32); -int arcompact_handle05_2f_17_dasm(DASM_OPS_32); -int arcompact_handle05_2f_18_dasm(DASM_OPS_32); -int arcompact_handle05_2f_19_dasm(DASM_OPS_32); -int arcompact_handle05_2f_1a_dasm(DASM_OPS_32); -int arcompact_handle05_2f_1b_dasm(DASM_OPS_32); -int arcompact_handle05_2f_1c_dasm(DASM_OPS_32); -int arcompact_handle05_2f_1d_dasm(DASM_OPS_32); -int arcompact_handle05_2f_1e_dasm(DASM_OPS_32); -int arcompact_handle05_2f_1f_dasm(DASM_OPS_32); -int arcompact_handle05_2f_20_dasm(DASM_OPS_32); -int arcompact_handle05_2f_21_dasm(DASM_OPS_32); -int arcompact_handle05_2f_22_dasm(DASM_OPS_32); -int arcompact_handle05_2f_23_dasm(DASM_OPS_32); -int arcompact_handle05_2f_24_dasm(DASM_OPS_32); -int arcompact_handle05_2f_25_dasm(DASM_OPS_32); -int arcompact_handle05_2f_26_dasm(DASM_OPS_32); -int arcompact_handle05_2f_27_dasm(DASM_OPS_32); -int arcompact_handle05_2f_28_dasm(DASM_OPS_32); -int arcompact_handle05_2f_29_dasm(DASM_OPS_32); -int arcompact_handle05_2f_2a_dasm(DASM_OPS_32); -int arcompact_handle05_2f_2b_dasm(DASM_OPS_32); -int arcompact_handle05_2f_2c_dasm(DASM_OPS_32); -int arcompact_handle05_2f_2d_dasm(DASM_OPS_32); -int arcompact_handle05_2f_2e_dasm(DASM_OPS_32); -int arcompact_handle05_2f_2f_dasm(DASM_OPS_32); -int arcompact_handle05_2f_30_dasm(DASM_OPS_32); -int arcompact_handle05_2f_31_dasm(DASM_OPS_32); -int arcompact_handle05_2f_32_dasm(DASM_OPS_32); -int arcompact_handle05_2f_33_dasm(DASM_OPS_32); -int arcompact_handle05_2f_34_dasm(DASM_OPS_32); -int arcompact_handle05_2f_35_dasm(DASM_OPS_32); -int arcompact_handle05_2f_36_dasm(DASM_OPS_32); -int arcompact_handle05_2f_37_dasm(DASM_OPS_32); -int arcompact_handle05_2f_38_dasm(DASM_OPS_32); -int arcompact_handle05_2f_39_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3a_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3b_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3c_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3d_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3e_dasm(DASM_OPS_32); - -int arcompact_handle05_2f_3f_00_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_01_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_02_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_03_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_04_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_05_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_06_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_07_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_08_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_09_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_0a_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_0b_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_0c_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_0d_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_0e_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_0f_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_10_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_11_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_12_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_13_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_14_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_15_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_16_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_17_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_18_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_19_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_1a_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_1b_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_1c_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_1d_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_1e_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_1f_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_20_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_21_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_22_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_23_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_24_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_25_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_26_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_27_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_28_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_29_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_2a_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_2b_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_2c_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_2d_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_2e_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_2f_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_30_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_31_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_32_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_33_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_34_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_35_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_36_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_37_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_38_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_39_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_3a_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_3b_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_3c_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_3d_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_3e_dasm(DASM_OPS_32); -int arcompact_handle05_2f_3f_3f_dasm(DASM_OPS_32); - - -int arcompact_handle04_38_dasm(DASM_OPS_32); -int arcompact_handle04_39_dasm(DASM_OPS_32); -int arcompact_handle04_3a_dasm(DASM_OPS_32); -int arcompact_handle04_3b_dasm(DASM_OPS_32); -int arcompact_handle04_3c_dasm(DASM_OPS_32); -int arcompact_handle04_3d_dasm(DASM_OPS_32); -int arcompact_handle04_3e_dasm(DASM_OPS_32); -int arcompact_handle04_3f_dasm(DASM_OPS_32); - -int arcompact_handle05_09_dasm(DASM_OPS_32); -int arcompact_handle05_0c_dasm(DASM_OPS_32); -int arcompact_handle05_0d_dasm(DASM_OPS_32); -int arcompact_handle05_0e_dasm(DASM_OPS_32); -int arcompact_handle05_0f_dasm(DASM_OPS_32); -int arcompact_handle05_10_dasm(DASM_OPS_32); -int arcompact_handle05_11_dasm(DASM_OPS_32); -int arcompact_handle05_12_dasm(DASM_OPS_32); -int arcompact_handle05_13_dasm(DASM_OPS_32); -int arcompact_handle05_14_dasm(DASM_OPS_32); -int arcompact_handle05_15_dasm(DASM_OPS_32); -int arcompact_handle05_16_dasm(DASM_OPS_32); -int arcompact_handle05_17_dasm(DASM_OPS_32); -int arcompact_handle05_18_dasm(DASM_OPS_32); -int arcompact_handle05_19_dasm(DASM_OPS_32); -int arcompact_handle05_1a_dasm(DASM_OPS_32); -int arcompact_handle05_1b_dasm(DASM_OPS_32); -int arcompact_handle05_1c_dasm(DASM_OPS_32); -int arcompact_handle05_1d_dasm(DASM_OPS_32); -int arcompact_handle05_1e_dasm(DASM_OPS_32); -int arcompact_handle05_1f_dasm(DASM_OPS_32); -int arcompact_handle05_20_dasm(DASM_OPS_32); -int arcompact_handle05_21_dasm(DASM_OPS_32); -int arcompact_handle05_22_dasm(DASM_OPS_32); -int arcompact_handle05_23_dasm(DASM_OPS_32); -int arcompact_handle05_24_dasm(DASM_OPS_32); -int arcompact_handle05_25_dasm(DASM_OPS_32); -int arcompact_handle05_26_dasm(DASM_OPS_32); -int arcompact_handle05_27_dasm(DASM_OPS_32); - -int arcompact_handle05_2a_dasm(DASM_OPS_32); -int arcompact_handle05_2b_dasm(DASM_OPS_32); -int arcompact_handle05_2c_dasm(DASM_OPS_32); -int arcompact_handle05_2d_dasm(DASM_OPS_32); -int arcompact_handle05_2e_dasm(DASM_OPS_32); - -int arcompact_handle05_30_dasm(DASM_OPS_32); -int arcompact_handle05_31_dasm(DASM_OPS_32); -int arcompact_handle05_32_dasm(DASM_OPS_32); -int arcompact_handle05_33_dasm(DASM_OPS_32); -int arcompact_handle05_34_dasm(DASM_OPS_32); -int arcompact_handle05_35_dasm(DASM_OPS_32); -int arcompact_handle05_36_dasm(DASM_OPS_32); -int arcompact_handle05_37_dasm(DASM_OPS_32); -int arcompact_handle05_38_dasm(DASM_OPS_32); -int arcompact_handle05_39_dasm(DASM_OPS_32); -int arcompact_handle05_3a_dasm(DASM_OPS_32); -int arcompact_handle05_3b_dasm(DASM_OPS_32); -int arcompact_handle05_3c_dasm(DASM_OPS_32); -int arcompact_handle05_3d_dasm(DASM_OPS_32); -int arcompact_handle05_3e_dasm(DASM_OPS_32); -int arcompact_handle05_3f_dasm(DASM_OPS_32); - -int arcompact_handle0f_00_04_dasm(DASM_OPS_16); -int arcompact_handle0f_00_05_dasm(DASM_OPS_16); -int arcompact_handle0f_00_07_02_dasm(DASM_OPS_16); -int arcompact_handle0f_00_07_03_dasm(DASM_OPS_16); -int arcompact_handle0f_01_dasm(DASM_OPS_16); -int arcompact_handle0f_03_dasm(DASM_OPS_16); -int arcompact_handle0f_08_dasm(DASM_OPS_16); -int arcompact_handle0f_09_dasm(DASM_OPS_16); -int arcompact_handle0f_0a_dasm(DASM_OPS_16); -int arcompact_handle0f_17_dasm(DASM_OPS_16); - -int arcompact_handle18_05_02_dasm(DASM_OPS_16); -int arcompact_handle18_05_03_dasm(DASM_OPS_16); -int arcompact_handle18_05_04_dasm(DASM_OPS_16); -int arcompact_handle18_05_05_dasm(DASM_OPS_16); -int arcompact_handle18_05_06_dasm(DASM_OPS_16); -int arcompact_handle18_05_07_dasm(DASM_OPS_16); -int arcompact_handle18_06_00_dasm(DASM_OPS_16); -int arcompact_handle18_06_02_dasm(DASM_OPS_16); -int arcompact_handle18_06_03_dasm(DASM_OPS_16); -int arcompact_handle18_06_04_dasm(DASM_OPS_16); -int arcompact_handle18_06_05_dasm(DASM_OPS_16); -int arcompact_handle18_06_06_dasm(DASM_OPS_16); -int arcompact_handle18_06_07_dasm(DASM_OPS_16); -int arcompact_handle18_06_08_dasm(DASM_OPS_16); -int arcompact_handle18_06_09_dasm(DASM_OPS_16); -int arcompact_handle18_06_0a_dasm(DASM_OPS_16); -int arcompact_handle18_06_0b_dasm(DASM_OPS_16); -int arcompact_handle18_06_0c_dasm(DASM_OPS_16); -int arcompact_handle18_06_0d_dasm(DASM_OPS_16); -int arcompact_handle18_06_0e_dasm(DASM_OPS_16); -int arcompact_handle18_06_0f_dasm(DASM_OPS_16); -int arcompact_handle18_06_10_dasm(DASM_OPS_16); -int arcompact_handle18_06_12_dasm(DASM_OPS_16); -int arcompact_handle18_06_13_dasm(DASM_OPS_16); -int arcompact_handle18_06_14_dasm(DASM_OPS_16); -int arcompact_handle18_06_15_dasm(DASM_OPS_16); -int arcompact_handle18_06_16_dasm(DASM_OPS_16); -int arcompact_handle18_06_17_dasm(DASM_OPS_16); -int arcompact_handle18_06_18_dasm(DASM_OPS_16); -int arcompact_handle18_06_19_dasm(DASM_OPS_16); -int arcompact_handle18_06_1a_dasm(DASM_OPS_16); -int arcompact_handle18_06_1b_dasm(DASM_OPS_16); -int arcompact_handle18_06_1c_dasm(DASM_OPS_16); -int arcompact_handle18_06_1d_dasm(DASM_OPS_16); -int arcompact_handle18_06_1e_dasm(DASM_OPS_16); -int arcompact_handle18_06_1f_dasm(DASM_OPS_16); -int arcompact_handle18_07_00_dasm(DASM_OPS_16); -int arcompact_handle18_07_02_dasm(DASM_OPS_16); -int arcompact_handle18_07_03_dasm(DASM_OPS_16); -int arcompact_handle18_07_04_dasm(DASM_OPS_16); -int arcompact_handle18_07_05_dasm(DASM_OPS_16); -int arcompact_handle18_07_06_dasm(DASM_OPS_16); -int arcompact_handle18_07_07_dasm(DASM_OPS_16); -int arcompact_handle18_07_08_dasm(DASM_OPS_16); -int arcompact_handle18_07_09_dasm(DASM_OPS_16); -int arcompact_handle18_07_0a_dasm(DASM_OPS_16); -int arcompact_handle18_07_0b_dasm(DASM_OPS_16); -int arcompact_handle18_07_0c_dasm(DASM_OPS_16); -int arcompact_handle18_07_0d_dasm(DASM_OPS_16); -int arcompact_handle18_07_0e_dasm(DASM_OPS_16); -int arcompact_handle18_07_0f_dasm(DASM_OPS_16); -int arcompact_handle18_07_10_dasm(DASM_OPS_16); -int arcompact_handle18_07_12_dasm(DASM_OPS_16); -int arcompact_handle18_07_13_dasm(DASM_OPS_16); -int arcompact_handle18_07_14_dasm(DASM_OPS_16); -int arcompact_handle18_07_15_dasm(DASM_OPS_16); -int arcompact_handle18_07_16_dasm(DASM_OPS_16); -int arcompact_handle18_07_17_dasm(DASM_OPS_16); -int arcompact_handle18_07_18_dasm(DASM_OPS_16); -int arcompact_handle18_07_19_dasm(DASM_OPS_16); -int arcompact_handle18_07_1a_dasm(DASM_OPS_16); -int arcompact_handle18_07_1b_dasm(DASM_OPS_16); -int arcompact_handle18_07_1c_dasm(DASM_OPS_16); -int arcompact_handle18_07_1d_dasm(DASM_OPS_16); -int arcompact_handle18_07_1e_dasm(DASM_OPS_16); -int arcompact_handle18_07_1f_dasm(DASM_OPS_16); diff --git a/src/devices/cpu/arm/arm.cpp b/src/devices/cpu/arm/arm.cpp index 077f693b144..ccf0f3e5009 100644 --- a/src/devices/cpu/arm/arm.cpp +++ b/src/devices/cpu/arm/arm.cpp @@ -20,9 +20,7 @@ #include "emu.h" #include "arm.h" #include "debugger.h" - -CPU_DISASSEMBLE( arm ); -CPU_DISASSEMBLE( arm_be ); +#include "armdasm.h" #define ARM_DEBUG_CORE 0 #define ARM_DEBUG_COPRO 0 @@ -1562,15 +1560,7 @@ void arm_cpu_device::HandleCoPro( uint32_t insn ) } -offs_t arm_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) -{ - extern CPU_DISASSEMBLE( arm ); - return CPU_DISASSEMBLE_NAME(arm)(this, stream, pc, oprom, opram, options); -} - - -offs_t arm_be_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *arm_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( arm_be ); - return CPU_DISASSEMBLE_NAME(arm_be)(this, stream, pc, oprom, opram, options); + return new arm_disassembler; } diff --git a/src/devices/cpu/arm/arm.h b/src/devices/cpu/arm/arm.h index 2de5fb3a39b..653d316b1fe 100644 --- a/src/devices/cpu/arm/arm.h +++ b/src/devices/cpu/arm/arm.h @@ -64,9 +64,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 4; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; address_space_config m_program_config; @@ -111,9 +109,6 @@ class arm_be_cpu_device : public arm_cpu_device public: // construction/destruction arm_be_cpu_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - -protected: - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; }; diff --git a/src/devices/cpu/arm/armdasm.cpp b/src/devices/cpu/arm/armdasm.cpp index 67d65209871..657ceb43550 100644 --- a/src/devices/cpu/arm/armdasm.cpp +++ b/src/devices/cpu/arm/armdasm.cpp @@ -7,9 +7,9 @@ */ #include "emu.h" -#include "arm.h" +#include "armdasm.h" -static void WriteImmediateOperand( std::ostream &stream, uint32_t opcode ) +void arm_disassembler::WriteImmediateOperand( std::ostream &stream, uint32_t opcode ) const { /* rrrrbbbbbbbb */ uint32_t imm; @@ -21,7 +21,7 @@ static void WriteImmediateOperand( std::ostream &stream, uint32_t opcode ) util::stream_format( stream, ", #$%x", imm ); } -static void WriteDataProcessingOperand( std::ostream &stream, uint32_t opcode, int printOp0, int printOp1, int printOp2 ) +void arm_disassembler::WriteDataProcessingOperand( std::ostream &stream, uint32_t opcode, int printOp0, int printOp1, int printOp2 ) const { /* ccccctttmmmm */ static const char *const pRegOp[4] = { "LSL","LSR","ASR","ROR" }; @@ -57,7 +57,7 @@ static void WriteDataProcessingOperand( std::ostream &stream, uint32_t opcode, i } } -static void WriteRegisterOperand1( std::ostream &stream, uint32_t opcode ) +void arm_disassembler::WriteRegisterOperand1( std::ostream &stream, uint32_t opcode ) const { /* ccccctttmmmm */ static const char *const pRegOp[4] = { "LSL","LSR","ASR","ROR" }; @@ -81,7 +81,7 @@ static void WriteRegisterOperand1( std::ostream &stream, uint32_t opcode ) } /* WriteRegisterOperand */ -static void WriteBranchAddress( std::ostream &stream, uint32_t pc, uint32_t opcode ) +void arm_disassembler::WriteBranchAddress( std::ostream &stream, uint32_t pc, uint32_t opcode ) const { opcode &= 0x00ffffff; if( opcode&0x00800000 ) @@ -92,14 +92,14 @@ static void WriteBranchAddress( std::ostream &stream, uint32_t pc, uint32_t opco util::stream_format( stream, "$%x", pc ); } /* WriteBranchAddress */ -static void WritePadding(std::ostream &stream, std::streampos start_position) +void arm_disassembler::WritePadding(std::ostream &stream, std::streampos start_position) const { std::streamoff difference = stream.tellp() - start_position; for (std::streamoff i = difference; i < 8; i++) stream << ' '; } -static uint32_t arm_disasm( std::ostream &stream, uint32_t pc, uint32_t opcode ) +offs_t arm_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { static const char *const pConditionCodeTable[16] = { @@ -119,6 +119,8 @@ static uint32_t arm_disasm( std::ostream &stream, uint32_t pc, uint32_t opcode ) uint32_t dasmflags = 0; std::streampos start_position = stream.tellp(); + u32 opcode = opcodes.r32(pc); + pConditionCode= pConditionCodeTable[opcode>>28]; if( (opcode&0x0fc000f0)==0x00000090u ) @@ -193,7 +195,7 @@ static uint32_t arm_disasm( std::ostream &stream, uint32_t pc, uint32_t opcode ) case 0x0d: /* look for mov pc,lr */ if (((opcode >> 12) & 0x0f) == 15 && ((opcode >> 0) & 0x0f) == 14 && (opcode & 0x02000000) == 0) - dasmflags = DASMFLAG_STEP_OUT; + dasmflags = STEP_OUT; case 0x0f: WriteDataProcessingOperand(stream, opcode, 1, 0, 1); break; @@ -325,7 +327,7 @@ static uint32_t arm_disasm( std::ostream &stream, uint32_t pc, uint32_t opcode ) if( opcode&0x01000000 ) { util::stream_format( stream, "BL" ); - dasmflags = DASMFLAG_STEP_OVER; + dasmflags = STEP_OVER; } else { @@ -380,24 +382,21 @@ static uint32_t arm_disasm( std::ostream &stream, uint32_t pc, uint32_t opcode ) util::stream_format( stream, "SWI%s $%x", pConditionCode, opcode&0x00ffffff ); - dasmflags = DASMFLAG_STEP_OVER; + dasmflags = STEP_OVER; } else { util::stream_format( stream, "Undefined" ); } - return dasmflags | DASMFLAG_SUPPORTED; + return 4 | dasmflags | SUPPORTED; } -CPU_DISASSEMBLE( arm ) +u32 arm_disassembler::opcode_alignment() const { - uint32_t opcode = oprom[0] | (oprom[1] << 8) | (oprom[2] << 16) | (oprom[3] << 24); - return 4 | arm_disasm(stream, pc, opcode); + return 4; } -CPU_DISASSEMBLE( arm_be ) +arm_disassembler::arm_disassembler() { - uint32_t opcode = oprom[3] | (oprom[2] << 8) | (oprom[1] << 16) | (oprom[0] << 24); - return 4 | arm_disasm(stream, pc, opcode); } diff --git a/src/devices/cpu/arm/armdasm.h b/src/devices/cpu/arm/armdasm.h new file mode 100644 index 00000000000..1e2ed19f394 --- /dev/null +++ b/src/devices/cpu/arm/armdasm.h @@ -0,0 +1,23 @@ + +#ifndef MAME_CPU_ARM_ARMDASM_H +#define MAME_CPU_ARM_ARMDASM_H + +#pragma once + +class arm_disassembler : public util::disasm_interface +{ +public: + arm_disassembler(); + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + void WriteImmediateOperand( std::ostream &stream, uint32_t opcode ) const; + void WriteDataProcessingOperand( std::ostream &stream, uint32_t opcode, int printOp0, int printOp1, int printOp2 ) const; + void WriteRegisterOperand1( std::ostream &stream, uint32_t opcode ) const; + void WriteBranchAddress( std::ostream &stream, uint32_t pc, uint32_t opcode ) const; + void WritePadding(std::ostream &stream, std::streampos start_position) const; + +}; + +#endif diff --git a/src/devices/cpu/arm7/arm7.cpp b/src/devices/cpu/arm7/arm7.cpp index 89ae14f8f11..cf8a8560990 100644 --- a/src/devices/cpu/arm7/arm7.cpp +++ b/src/devices/cpu/arm7/arm7.cpp @@ -929,83 +929,14 @@ void arm7_cpu_device::execute_set_input(int irqline, int state) } -offs_t arm7_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *arm7_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( arm7arm ); - extern CPU_DISASSEMBLE( arm7thumb ); - extern CPU_DISASSEMBLE( arm7arm_be ); - extern CPU_DISASSEMBLE( arm7thumb_be ); - - uint8_t fetched_op[4]; - uint32_t op = 0; - int prefetch_index = get_insn_prefetch_index(pc); - if (prefetch_index < 0) - { - memcpy(fetched_op, oprom, 4); - if (T_IS_SET(m_r[eCPSR])) - { - if ( m_endian == ENDIANNESS_BIG ) - { - return CPU_DISASSEMBLE_NAME(arm7thumb_be)(this, stream, pc, fetched_op, opram, options); - } - else - { - return CPU_DISASSEMBLE_NAME(arm7thumb)(this, stream, pc, fetched_op, opram, options); - } - } - else - { - if ( m_endian == ENDIANNESS_BIG ) - { - return CPU_DISASSEMBLE_NAME(arm7arm_be)(this, stream, pc, fetched_op, opram, options); - } - else - { - return CPU_DISASSEMBLE_NAME(arm7arm)(this, stream, pc, fetched_op, opram, options); - } - } - } - else - { - op = m_insn_prefetch_buffer[prefetch_index]; - if (T_IS_SET(m_r[eCPSR])) - { - if (m_endian == ENDIANNESS_BIG) - { - op >>= ((pc & 2) ? 0 : 16); - fetched_op[1] = op & 0xff; - fetched_op[0] = (op >> 8) & 0xff; - return CPU_DISASSEMBLE_NAME(arm7thumb_be)(this, stream, pc, fetched_op, opram, options); - } - else - { - op >>= ((pc & 2) ? 16 : 0); - fetched_op[0] = op & 0xff; - fetched_op[1] = (op >> 8) & 0xff; - return CPU_DISASSEMBLE_NAME(arm7thumb)(this, stream, pc, fetched_op, opram, options); - } - } - else - { - if (m_endian == ENDIANNESS_BIG) - { - fetched_op[3] = op & 0xff; - fetched_op[2] = (op >> 8) & 0xff; - fetched_op[1] = (op >> 16) & 0xff; - fetched_op[0] = (op >> 24) & 0xff; - return CPU_DISASSEMBLE_NAME(arm7arm_be)(this, stream, pc, fetched_op, opram, options); - } - else - { - fetched_op[0] = op & 0xff; - fetched_op[1] = (op >> 8) & 0xff; - fetched_op[2] = (op >> 16) & 0xff; - fetched_op[3] = (op >> 24) & 0xff; - return CPU_DISASSEMBLE_NAME(arm7arm)(this, stream, pc, fetched_op, opram, options); - } - } - } - return 0; + return new arm7_disassembler(this); +} + +bool arm7_cpu_device::get_t_flag() const +{ + return T_IS_SET(m_r[eCPSR]); } diff --git a/src/devices/cpu/arm7/arm7.h b/src/devices/cpu/arm7/arm7.h index 8a72a8bb1a8..b6c9926610e 100644 --- a/src/devices/cpu/arm7/arm7.h +++ b/src/devices/cpu/arm7/arm7.h @@ -23,6 +23,8 @@ #pragma once +#include "arm7dasm.h" + #include "cpu/drcfe.h" #include "cpu/drcuml.h" #include "cpu/drcumlsh.h" @@ -49,7 +51,7 @@ * PUBLIC FUNCTIONS ***************************************************************************************************/ -class arm7_cpu_device : public cpu_device +class arm7_cpu_device : public cpu_device, public arm7_disassembler::config { public: // construction/destruction @@ -130,9 +132,8 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; + virtual bool get_t_flag() const override; address_space_config m_program_config; diff --git a/src/devices/cpu/arm7/arm7dasm.cpp b/src/devices/cpu/arm7/arm7dasm.cpp index 8b12a8fdc65..80cab4f1da4 100644 --- a/src/devices/cpu/arm7/arm7dasm.cpp +++ b/src/devices/cpu/arm7/arm7dasm.cpp @@ -23,16 +23,17 @@ ******************************************************************************/ #include "emu.h" +#include "arm7dasm.h" #include "arm7core.h" -static void WritePadding(std::ostream &stream, std::streampos start_position) +void arm7_disassembler::WritePadding(std::ostream &stream, std::streampos start_position) { std::streamoff difference = stream.tellp() - start_position; for (std::streamoff i = difference; i < 8; i++) stream << ' '; } -static void DasmCoProc_RT(std::ostream &stream, uint32_t opcode, const char *pConditionCode, std::streampos start_position) +void arm7_disassembler::DasmCoProc_RT(std::ostream &stream, uint32_t opcode, const char *pConditionCode, std::streampos start_position) { /* co processor register transfer */ /* xxxx 1110 oooL nnnn dddd cccc ppp1 mmmm */ @@ -51,7 +52,7 @@ static void DasmCoProc_RT(std::ostream &stream, uint32_t opcode, const char *pCo if((opcode>>5)&7) util::stream_format( stream, ", %d",(opcode>>5)&7); } -static void DasmCoProc_DT(std::ostream &stream, uint32_t opcode, const char *pConditionCode, std::streampos start_position) +void arm7_disassembler::DasmCoProc_DT(std::ostream &stream, uint32_t opcode, const char *pConditionCode, std::streampos start_position) { /* co processor data transfer */ /* xxxx 111P UNWL nnnn dddd pppp oooooooo */ @@ -75,7 +76,7 @@ static void DasmCoProc_DT(std::ostream &stream, uint32_t opcode, const char *pCo util::stream_format(stream, "%s%s",(opcode&0x1000000)?"]":"",(opcode&0x200000)?"{!}":""); } -static void DasmCoProc_DO(std::ostream &stream, uint32_t opcode, const char *pConditionCode, std::streampos start_position) +void arm7_disassembler::DasmCoProc_DO(std::ostream &stream, uint32_t opcode, const char *pConditionCode, std::streampos start_position) { /* co processor data operation */ /* xxxx 1110 oooo nnnn dddd cccc ppp0 mmmm */ @@ -88,7 +89,7 @@ static void DasmCoProc_DO(std::ostream &stream, uint32_t opcode, const char *pCo if((opcode>>5)&7) util::stream_format(stream, ", %d",(opcode>>5)&7); } -static void WriteImmediateOperand( std::ostream &stream, uint32_t opcode ) +void arm7_disassembler::WriteImmediateOperand( std::ostream &stream, uint32_t opcode ) { /* rrrrbbbbbbbb */ uint32_t imm; @@ -100,7 +101,7 @@ static void WriteImmediateOperand( std::ostream &stream, uint32_t opcode ) util::stream_format( stream, ", #$%x", imm ); } -static void WriteDataProcessingOperand( std::ostream &stream, uint32_t opcode, int printOp0, int printOp1, int printOp2 ) +void arm7_disassembler::WriteDataProcessingOperand( std::ostream &stream, uint32_t opcode, int printOp0, int printOp1, int printOp2 ) { /* ccccctttmmmm */ static const char *const pRegOp[4] = { "LSL","LSR","ASR","ROR" }; @@ -142,7 +143,7 @@ static void WriteDataProcessingOperand( std::ostream &stream, uint32_t opcode, i } } -static void WriteRegisterOperand1( std::ostream &stream, uint32_t opcode ) +void arm7_disassembler::WriteRegisterOperand1( std::ostream &stream, uint32_t opcode ) { /* ccccctttmmmm */ static const char *const pRegOp[4] = { "LSL","LSR","ASR","ROR" }; @@ -172,7 +173,7 @@ static void WriteRegisterOperand1( std::ostream &stream, uint32_t opcode ) } /* WriteRegisterOperand */ -static void WriteBranchAddress( std::ostream &stream, uint32_t pc, uint32_t opcode, bool h_bit ) +void arm7_disassembler::WriteBranchAddress( std::ostream &stream, uint32_t pc, uint32_t opcode, bool h_bit ) { opcode <<= 2; if (h_bit && (opcode & 0x04000000)) @@ -188,7 +189,7 @@ static void WriteBranchAddress( std::ostream &stream, uint32_t pc, uint32_t opco util::stream_format( stream, "$%x", pc ); } /* WriteBranchAddress */ -static uint32_t arm7_disasm( std::ostream &stream, uint32_t pc, uint32_t opcode ) +u32 arm7_disassembler::arm7_disasm( std::ostream &stream, uint32_t pc, uint32_t opcode ) { static const char *const pConditionCodeTable[16] = { @@ -214,7 +215,7 @@ static uint32_t arm7_disasm( std::ostream &stream, uint32_t pc, uint32_t opcode { /* BLX(1) */ util::stream_format( stream, "BLX" ); - dasmflags = DASMFLAG_STEP_OVER; + dasmflags = STEP_OVER; WritePadding(stream, start_position); @@ -224,7 +225,7 @@ static uint32_t arm7_disasm( std::ostream &stream, uint32_t pc, uint32_t opcode { /* BLX(2) */ util::stream_format( stream, "BLX" ); - dasmflags = DASMFLAG_STEP_OVER; + dasmflags = STEP_OVER; WritePadding(stream, start_position); util::stream_format( stream, "R%d",(opcode&0xf)); } @@ -236,7 +237,7 @@ static uint32_t arm7_disasm( std::ostream &stream, uint32_t pc, uint32_t opcode WritePadding(stream, start_position); util::stream_format( stream, "R%d",(opcode&0xf)); if ((opcode & 0x0f) == 14) - dasmflags = DASMFLAG_STEP_OUT; + dasmflags = STEP_OUT; } else if ((opcode & 0x0ff000f0) == 0x01600010) // CLZ - v5 { @@ -500,7 +501,7 @@ static uint32_t arm7_disasm( std::ostream &stream, uint32_t pc, uint32_t opcode case 0x0d: /* look for mov pc,lr */ if (((opcode >> 12) & 0x0f) == 15 && ((opcode >> 0) & 0x0f) == 14 && (opcode & 0x02000000) == 0) - dasmflags = DASMFLAG_STEP_OUT; + dasmflags = STEP_OUT; case 0x0f: WriteDataProcessingOperand(stream, opcode, 1, 0, 1); break; @@ -649,7 +650,7 @@ static uint32_t arm7_disasm( std::ostream &stream, uint32_t pc, uint32_t opcode if( opcode&0x01000000 ) { util::stream_format( stream, "BL" ); - dasmflags = DASMFLAG_STEP_OVER; + dasmflags = STEP_OVER; } else { @@ -688,16 +689,16 @@ static uint32_t arm7_disasm( std::ostream &stream, uint32_t pc, uint32_t opcode util::stream_format( stream, "SWI%s $%x", pConditionCode, opcode&0x00ffffff ); - dasmflags = DASMFLAG_STEP_OVER; + dasmflags = STEP_OVER; } else { util::stream_format( stream, "Undefined" ); } - return dasmflags | DASMFLAG_SUPPORTED; + return dasmflags | SUPPORTED; } -static uint32_t thumb_disasm(std::ostream &stream, uint32_t pc, uint16_t opcode) +u32 arm7_disassembler::thumb_disasm(std::ostream &stream, uint32_t pc, uint16_t opcode) { std::streampos start_position = stream.tellp(); uint32_t dasmflags = 0; @@ -978,7 +979,7 @@ static uint32_t thumb_disasm(std::ostream &stream, uint32_t pc, uint16_t opcode) rd = ( ( opcode & THUMB_HIREG_RS ) >> THUMB_HIREG_RS_SHIFT ) + 8; util::stream_format( stream, "BX R%d", rd ); if (rd == 14) - dasmflags = DASMFLAG_STEP_OUT; + dasmflags = STEP_OUT; break; case 0x2: rd = ( opcode & THUMB_HIREG_RS ) >> THUMB_HIREG_RS_SHIFT; @@ -1287,7 +1288,7 @@ static uint32_t thumb_disasm(std::ostream &stream, uint32_t pc, uint16_t opcode) { addr = ( ( opcode & THUMB_BLOP_OFFS ) << 1 ) & 0xfffc; util::stream_format( stream, "BLX (LO) %08x", addr ); - dasmflags = DASMFLAG_STEP_OVER; + dasmflags = STEP_OVER; } else { @@ -1303,7 +1304,7 @@ static uint32_t thumb_disasm(std::ostream &stream, uint32_t pc, uint16_t opcode) if( opcode & THUMB_BLOP_LO ) { util::stream_format( stream, "BL (LO) %08x", ( opcode & THUMB_BLOP_OFFS ) << 1 ); - dasmflags = DASMFLAG_STEP_OVER; + dasmflags = STEP_OVER; } else { @@ -1313,7 +1314,7 @@ static uint32_t thumb_disasm(std::ostream &stream, uint32_t pc, uint16_t opcode) addr |= 0xff800000; } util::stream_format( stream, "BL (HI) %08x", addr ); - dasmflags = DASMFLAG_STEP_OVER; + dasmflags = STEP_OVER; } break; default: @@ -1321,25 +1322,22 @@ static uint32_t thumb_disasm(std::ostream &stream, uint32_t pc, uint16_t opcode) break; } - return dasmflags | DASMFLAG_SUPPORTED; + return dasmflags | SUPPORTED; } -CPU_DISASSEMBLE( arm7arm ) +arm7_disassembler::arm7_disassembler(config *conf) : m_config(conf) { - return arm7_disasm(stream, pc, oprom[0] | (oprom[1] << 8) | (oprom[2] << 16) | (oprom[3] << 24)) | 4; } -CPU_DISASSEMBLE( arm7arm_be ) +u32 arm7_disassembler::opcode_alignment() const { - return arm7_disasm(stream, pc, oprom[3] | (oprom[2] << 8) | (oprom[1] << 16) | (oprom[0] << 24)) | 4; + return m_config->get_t_flag() ? 2 : 4; } -CPU_DISASSEMBLE( arm7thumb ) +offs_t arm7_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - return thumb_disasm(stream, pc, oprom[0] | (oprom[1] << 8)) | 2; -} - -CPU_DISASSEMBLE( arm7thumb_be ) -{ - return thumb_disasm(stream, pc, oprom[1] | (oprom[0] << 8)) | 2; + if(m_config->get_t_flag()) + return arm7_disasm(stream, pc, opcodes.r32(pc)); + else + return thumb_disasm(stream, pc, opcodes.r16(pc)); } diff --git a/src/devices/cpu/arm7/arm7dasm.h b/src/devices/cpu/arm7/arm7dasm.h new file mode 100644 index 00000000000..9f90b47308f --- /dev/null +++ b/src/devices/cpu/arm7/arm7dasm.h @@ -0,0 +1,51 @@ +// license:BSD-3-Clause +// copyright-holders:Steve Ellenoff,R. Belmont,Ryan Holtz +/***************************************************************************** + * + * arm7dasm.c + * Portable ARM7TDMI Core Emulator - Disassembler + * + * Copyright Steve Ellenoff, all rights reserved. + * + * This work is based on: + * #1) 'Atmel Corporation ARM7TDMI (Thumb) Datasheet - January 1999' + * #2) Arm 2/3/6 emulator By Bryan McPhail (bmcphail@tendril.co.uk) and Phil Stroffolino (MAME CORE 0.76) + * + *****************************************************************************/ + +#ifndef MAME_CPU_ARM7_ARM7DASM_H +#define MAME_CPU_ARM7_ARM7DASM_H + +#pragma once + +class arm7_disassembler : public util::disasm_interface +{ +public: + class config { + public: + virtual ~config() = default; + virtual bool get_t_flag() const = 0; + }; + + arm7_disassembler(config *conf); + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + config *m_config; + + void WritePadding(std::ostream &stream, std::streampos start_position); + void DasmCoProc_RT(std::ostream &stream, u32 opcode, const char *pConditionCode, std::streampos start_position); + void DasmCoProc_DT(std::ostream &stream, u32 opcode, const char *pConditionCode, std::streampos start_position); + void DasmCoProc_DO(std::ostream &stream, u32 opcode, const char *pConditionCode, std::streampos start_position); + void WriteImmediateOperand( std::ostream &stream, u32 opcode ); + void WriteDataProcessingOperand( std::ostream &stream, u32 opcode, int printOp0, int printOp1, int printOp2 ); + void WriteRegisterOperand1( std::ostream &stream, u32 opcode ); + void WriteBranchAddress( std::ostream &stream, u32 pc, u32 opcode, bool h_bit ); + u32 arm7_disasm( std::ostream &stream, u32 pc, u32 opcode ); + u32 thumb_disasm(std::ostream &stream, u32 pc, u16 opcode); +}; + + +#endif diff --git a/src/devices/cpu/asap/asap.cpp b/src/devices/cpu/asap/asap.cpp index e808f3fbb6c..94d54c4e4ea 100644 --- a/src/devices/cpu/asap/asap.cpp +++ b/src/devices/cpu/asap/asap.cpp @@ -13,6 +13,7 @@ #include "emu.h" #include "asap.h" +#include "asapdasm.h" #include "debugger.h" @@ -300,40 +301,16 @@ void asap_device::state_string_export(const device_state_entry &entry, std::stri //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t asap_device::disasm_min_opcode_bytes() const -{ - return 4; -} - - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t asap_device::disasm_max_opcode_bytes() const -{ - return 12; -} - - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t asap_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *asap_device::create_disassembler() { - extern CPU_DISASSEMBLE( asap ); - return CPU_DISASSEMBLE_NAME(asap)(this, stream, pc, oprom, opram, options); + return new asap_disassembler; } - //************************************************************************** // INLINE HELPERS //************************************************************************** diff --git a/src/devices/cpu/asap/asap.h b/src/devices/cpu/asap/asap.h index 55d78d5b6cf..93df7d56e0d 100644 --- a/src/devices/cpu/asap/asap.h +++ b/src/devices/cpu/asap/asap.h @@ -89,9 +89,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // helpers inline uint32_t readop(offs_t pc); diff --git a/src/devices/cpu/asap/asapdasm.cpp b/src/devices/cpu/asap/asapdasm.cpp index 840c50f2635..8f652b6dad4 100644 --- a/src/devices/cpu/asap/asapdasm.cpp +++ b/src/devices/cpu/asap/asapdasm.cpp @@ -9,10 +9,10 @@ ***************************************************************************/ #include "emu.h" -#include "asap.h" +#include "asapdasm.h" -static const char *const reg[32] = +const char *const asap_disassembler::reg[32] = { "0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15", @@ -20,12 +20,12 @@ static const char *const reg[32] = "r24", "r25", "r26", "r27", "r28", "r29", "r30", "r31" }; -static const char *const setcond[2] = +const char *const asap_disassembler::setcond[2] = { " ", ".c" }; -static const char *const condition[16] = +const char *const asap_disassembler::condition[16] = { "sp", "mz", "gt", "le", "ge", "lt", "hi", "ls", "cc", "cs", "pl", "mi", "ne", "eq", "vc", "vs" }; @@ -35,19 +35,17 @@ static const char *const condition[16] = CODE CODE ***************************************************************************/ -static inline char *src2(uint32_t op, int scale) +std::string asap_disassembler::src2(uint32_t op, int scale) { - static char temp[20]; if ((op & 0xffe0) == 0xffe0) - sprintf(temp, "%s", reg[op & 31]); + return util::string_format("%s", reg[op & 31]); else - sprintf(temp, "$%x", (op & 0xffff) << scale); - return temp; + return util::string_format("$%x", (op & 0xffff) << scale); } -CPU_DISASSEMBLE(asap) +offs_t asap_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - uint32_t op = oprom[0] | (oprom[1] << 8) | (oprom[2] << 16) | (oprom[3] << 24); + uint32_t op = opcodes.r32(pc); int opcode = op >> 27; int cond = (op >> 21) & 1; int rdst = (op >> 22) & 31; @@ -58,21 +56,21 @@ CPU_DISASSEMBLE(asap) switch (opcode) { - case 0x00: util::stream_format(stream, "trap $00"); flags = DASMFLAG_STEP_OVER; break; + case 0x00: util::stream_format(stream, "trap $00"); flags = STEP_OVER; break; case 0x01: util::stream_format(stream, "b%s $%08x", condition[rdst & 15], pc + ((int32_t)(op << 10) >> 8)); break; case 0x02: if ((op & 0x003fffff) == 3) { - uint32_t nextop = oprom[4] | (oprom[5] << 8) | (oprom[6] << 16) | (oprom[7] << 24); + uint32_t nextop = opcodes.r32(pc+4); if ((nextop >> 27) == 0x10 && ((nextop >> 22) & 31) == rdst && (nextop & 0xffff) == 0) { - uint32_t nextnextop = oprom[8] | (oprom[9] << 8) | (oprom[10] << 16) | (oprom[11] << 24); + uint32_t nextnextop = opcodes.r32(pc+8); util::stream_format(stream, "llit%s $%08x,%s", setcond[cond], nextnextop, reg[rdst]); - return 12 | DASMFLAG_STEP_OVER | DASMFLAG_SUPPORTED; + return 12 | STEP_OVER | SUPPORTED; } } if (rdst) { - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); util::stream_format(stream, "bsr %s,$%08x", reg[rdst], pc + ((int32_t)(op << 10) >> 8)); } else @@ -123,24 +121,29 @@ CPU_DISASSEMBLE(asap) case 0x1d: util::stream_format(stream, "putps %s", src2(op,0)); break; case 0x1e: if (rdst && rsrc2_iszero) { - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); util::stream_format(stream, "jsr%s %s,%s", setcond[cond], reg[rdst], reg[rsrc1]); } else if (rdst) { - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); util::stream_format(stream, "jsr%s %s,%s[%s]", setcond[cond], reg[rdst], reg[rsrc1], src2(op,2)); } else if (rsrc2_iszero) { if (rsrc1 == 28) - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; util::stream_format(stream, "jmp%s %s", setcond[cond], reg[rsrc1]); } else util::stream_format(stream, "jmp%s %s[%s]", setcond[cond], reg[rsrc1], src2(op,2)); break; - case 0x1f: util::stream_format(stream, "trap $1f"); flags = DASMFLAG_STEP_OVER; break; + case 0x1f: util::stream_format(stream, "trap $1f"); flags = STEP_OVER; break; } - return 4 | flags | DASMFLAG_SUPPORTED; + return 4 | flags | SUPPORTED; +} + +u32 asap_disassembler::opcode_alignment() const +{ + return 4; } diff --git a/src/devices/cpu/asap/asapdasm.h b/src/devices/cpu/asap/asapdasm.h new file mode 100644 index 00000000000..45ca554368d --- /dev/null +++ b/src/devices/cpu/asap/asapdasm.h @@ -0,0 +1,33 @@ +// license:BSD-3-Clause +// copyright-holders:Aaron Giles +/*************************************************************************** + + asapdasm.c + Disassembler for the portable ASAP emulator. + Written by Aaron Giles + +***************************************************************************/ + +#ifndef MAME_CPU_ASAP_ASAPDASM_H +#define MAME_CPU_ASAP_ASAPDASM_H + +#pragma once + +class asap_disassembler : public util::disasm_interface +{ +public: + asap_disassembler() = default; + virtual ~asap_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *const reg[32]; + static const char *const setcond[2]; + static const char *const condition[16]; + std::string src2(uint32_t op, int scale); + +}; + +#endif diff --git a/src/devices/cpu/avr8/avr8.cpp b/src/devices/cpu/avr8/avr8.cpp index 763cdad799e..2f55b4a0317 100644 --- a/src/devices/cpu/avr8/avr8.cpp +++ b/src/devices/cpu/avr8/avr8.cpp @@ -59,6 +59,7 @@ #include "emu.h" #include "avr8.h" +#include "avr8dasm.h" #include "debugger.h" #define VERBOSE_LEVEL (0) @@ -911,36 +912,13 @@ void avr8_device::state_string_export(const device_state_entry &entry, std::stri //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t avr8_device::disasm_min_opcode_bytes() const -{ - return 2; -} - - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t avr8_device::disasm_max_opcode_bytes() const -{ - return 4; -} - - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t avr8_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *avr8_device::create_disassembler() { - extern CPU_DISASSEMBLE( avr8 ); - return CPU_DISASSEMBLE_NAME(avr8)(this, stream, pc, oprom, opram, options); + return new avr8_disassembler; } diff --git a/src/devices/cpu/avr8/avr8.h b/src/devices/cpu/avr8/avr8.h index 0da73a4cc1c..f8c953a3aa3 100644 --- a/src/devices/cpu/avr8/avr8.h +++ b/src/devices/cpu/avr8/avr8.h @@ -123,9 +123,7 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // device_state_interface overrides virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; @@ -848,6 +846,4 @@ enum #define AVR8_SPCR_CPHA_MASK 0x04 #define AVR8_SPCR_SPR_MASK 0x03 -CPU_DISASSEMBLE( avr8 ); - #endif /* __AVR8_H__ */ diff --git a/src/devices/cpu/avr8/avr8dasm.cpp b/src/devices/cpu/avr8/avr8dasm.cpp index cfc99b955d3..5f47198c425 100644 --- a/src/devices/cpu/avr8/avr8dasm.cpp +++ b/src/devices/cpu/avr8/avr8dasm.cpp @@ -7,7 +7,7 @@ */ #include "emu.h" -#include "avr8.h" +#include "avr8dasm.h" #define RD2(op) (((op) >> 4) & 0x0003) #define RD3(op) (((op) >> 4) & 0x0007) @@ -25,11 +25,16 @@ #define ACONST6(op) ((((op) >> 5) & 0x0030) | ((op) & 0x000f)) #define MULCONST2(op) ((((op) >> 6) & 0x0002) | (((op) >> 3) & 0x0001)) -CPU_DISASSEMBLE(avr8) +u32 avr8_disassembler::opcode_alignment() const { - int pos = 0; - uint32_t op = oprom[pos++]; - op |= oprom[pos++] << 8; + return 2; +} + +offs_t avr8_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + offs_t base_pc = pc; + uint32_t op = opcodes.r16(pc); + pc += 2; uint32_t addr; const char* register_names[0x40] = {"PINA", "DDRA", "PORTA", "PINB", "DDRB", "PORTB", "PINC", "DDRC", "PORTC", "PIND", "DDRD", "PORTD", "PINE", "DDRE", "PORTE", "PINF", "DDRF", "PORTF", "PING", "DDRG", "PORTG", "TIFR0", "TIFR1", "TIFR2","TIFR3", "TIFR4", "TIFR5", "PCIFR", "EIFR", "EIMSK", "GPIOR0", "EECR", "EEDR", "EEARL", "EEARH", "GTCCR", "TCCR0A", "TCCR0B", "TCNT0", "OCR0A", "OCR0B", "0x29", "GPIOR1", "GPIOR2", "SPCR", "SPSR", "SPDR", "0x2F", "ACSR", "OCDR", "0x32", "SMCR", "MCUSR", "MCUCR", "0x36", "SPMCSR", "0x38", "0x39", "0x3A", "RAMPZ", "EIND", "SPL", "SPH", "SREG"}; @@ -226,8 +231,8 @@ CPU_DISASSEMBLE(avr8) { case 0x0000: op <<= 16; - op |= oprom[pos++]; - op |= oprom[pos++] << 8; + op |= opcodes.r16(pc); + pc += 2; util::stream_format(stream, "LDS R%d, (0x%04x)", RD5(op >> 16), op & 0x0000ffff); break; case 0x0001: @@ -277,8 +282,8 @@ CPU_DISASSEMBLE(avr8) { case 0x0000: op <<= 16; - op |= oprom[pos++]; - op |= oprom[pos++] << 8; + op |= opcodes.r16(pc); + pc += 2; util::stream_format(stream, "STS (0x%04x), R%d", op & 0x0000ffff, RD5(op >> 16)); break; case 0x0001: @@ -410,15 +415,15 @@ CPU_DISASSEMBLE(avr8) case 0x000c: case 0x000d: addr = KCONST22(op) << 16; - addr |= oprom[pos++]; - addr |= oprom[pos++] << 8; + addr |= opcodes.r16(pc); + pc += 2; util::stream_format(stream, "JMP 0x%06x", addr << 1); break; case 0x000e: case 0x000f: addr = KCONST22(op) << 16; - addr |= oprom[pos++]; - addr |= oprom[pos++] << 8; + addr |= opcodes.r16(pc); + pc += 2; util::stream_format(stream, "CALL 0x%06x", addr << 1); break; default: @@ -505,15 +510,15 @@ CPU_DISASSEMBLE(avr8) case 0x000c: case 0x000d: op <<= 16; - op |= oprom[pos++]; - op |= oprom[pos++] << 8; + op |= opcodes.r16(pc); + pc += 2; util::stream_format(stream, "JMP 0x%06x", KCONST22(op) << 1); break; case 0x000e: case 0x000f: op <<= 16; - op |= oprom[pos++]; - op |= oprom[pos++] << 8; + op |= opcodes.r16(pc); + pc += 2; util::stream_format(stream, "CALL 0x%06x", KCONST22(op) << 1); break; } @@ -669,5 +674,5 @@ CPU_DISASSEMBLE(avr8) break; } - return pos | DASMFLAG_SUPPORTED; + return (pc - base_pc) | SUPPORTED; } diff --git a/src/devices/cpu/avr8/avr8dasm.h b/src/devices/cpu/avr8/avr8dasm.h new file mode 100644 index 00000000000..a7f55fdb86b --- /dev/null +++ b/src/devices/cpu/avr8/avr8dasm.h @@ -0,0 +1,24 @@ +// license:BSD-3-Clause +// copyright-holders:Ryan Holtz +/* + Atmel 8-bit AVR disassembler + + Written by Ryan Holtz +*/ + +#ifndef MAME_CPU_AVR8_AVR8DASM_H +#define MAME_CPU_AVR8_AVR8DASM_H + +#pragma once + +class avr8_disassembler : public util::disasm_interface +{ +public: + avr8_disassembler() = default; + virtual ~avr8_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/capricorn/capricorn.cpp b/src/devices/cpu/capricorn/capricorn.cpp index b25800a6541..c99a66be04d 100644 --- a/src/devices/cpu/capricorn/capricorn.cpp +++ b/src/devices/cpu/capricorn/capricorn.cpp @@ -7,6 +7,7 @@ // #include "emu.h" #include "capricorn.h" +#include "capricorn_dasm.h" #include "debugger.h" // Register indexes @@ -237,10 +238,9 @@ void capricorn_cpu_device::state_string_export(const device_state_entry &entry, } } -offs_t capricorn_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +util::disasm_interface *capricorn_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE(capricorn); - return CPU_DISASSEMBLE_NAME(capricorn)(this, stream, pc, oprom, opram, options); + return new capricorn_disassembler; } void capricorn_cpu_device::start_mem_burst(ea_addr_t addr) diff --git a/src/devices/cpu/capricorn/capricorn.h b/src/devices/cpu/capricorn/capricorn.h index 7cf11b7f0ae..874db7d637e 100644 --- a/src/devices/cpu/capricorn/capricorn.h +++ b/src/devices/cpu/capricorn/capricorn.h @@ -39,11 +39,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual u32 disasm_min_opcode_bytes() const override - { return 1; } - virtual u32 disasm_max_opcode_bytes() const override - { return 9; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/capricorn/capricorn_dasm.cpp b/src/devices/cpu/capricorn/capricorn_dasm.cpp index 5a45cb2c832..1b1794a954f 100644 --- a/src/devices/cpu/capricorn/capricorn_dasm.cpp +++ b/src/devices/cpu/capricorn/capricorn_dasm.cpp @@ -5,204 +5,197 @@ // ******************************************************************************** #include "emu.h" -#include "capricorn.h" +#include "capricorn_dasm.h" -typedef offs_t (*fn_dis_param)(std::ostream &stream , offs_t pc , const uint8_t *oprom); - -typedef struct { - uint8_t m_op_mask; - uint8_t m_opcode; - const char *m_mnemonic; - bool m_has_mb; - char m_addr_mode; - fn_dis_param m_param_fn; - uint32_t m_dasm_flags; -} dis_entry_t; - -static void direct_addr(std::ostream &stream , const uint8_t *oprom) +void capricorn_disassembler::direct_addr(std::ostream &stream, offs_t pc, const data_buffer &opcodes) { - util::stream_format(stream , "$%02x%02x" , oprom[ 1 ] , oprom[ 0 ]); + util::stream_format(stream, "$%04x", opcodes.r16(pc)); } -static offs_t param_arp_drp(std::ostream &stream , offs_t pc , const uint8_t *oprom) +offs_t capricorn_disassembler::param_arp_drp(std::ostream &stream, offs_t pc, const data_buffer &opcodes) { stream << "R"; - util::stream_format(stream , "%02o" , oprom[ 0 ] & 0x3f); + util::stream_format(stream, "%02o", opcodes.r8(pc) & 0x3f); return 0; } -static offs_t param_dr(std::ostream &stream , offs_t pc , const uint8_t *oprom) +offs_t capricorn_disassembler::param_dr(std::ostream &stream, offs_t pc, const data_buffer &opcodes) { stream << "DR"; return 0; } -static offs_t param_dr_ar(std::ostream &stream , offs_t pc , const uint8_t *oprom) +offs_t capricorn_disassembler::param_dr_ar(std::ostream &stream, offs_t pc, const data_buffer &opcodes) { stream << "DR,AR"; return 0; } -static offs_t param_dr_lit(std::ostream &stream , offs_t pc , const uint8_t *oprom) +offs_t capricorn_disassembler::param_dr_lit(std::ostream &stream, offs_t pc, const data_buffer &opcodes) { stream << "DR,="; // Here we assume that multi-byte instructions operate on 2 bytes because we // have no way of knowing how many they are (the actual number of bytes is // dynamically determined by the value of DRP register at run-time) - unsigned bytes = BIT(oprom[ 0 ] , 0) ? 2 : 1; + unsigned bytes = BIT(opcodes.r8(pc), 0) ? 2 : 1; for (unsigned i = 1; i <= bytes; i++) { - util::stream_format(stream , "$%02x " , oprom[ i ]); + util::stream_format(stream, "$%02x ", opcodes.r8(pc+i)); } return bytes; } -static offs_t param_dr_lit_dir(std::ostream &stream , offs_t pc ,const uint8_t *oprom) +offs_t capricorn_disassembler::param_dr_lit_dir(std::ostream &stream, offs_t pc,const data_buffer &opcodes) { stream << "DR,="; - direct_addr(stream , &oprom[ 1 ]); + direct_addr(stream, pc+1, opcodes); return 2; } -static offs_t param_dr_idx_dir(std::ostream &stream , offs_t pc ,const uint8_t *oprom) +offs_t capricorn_disassembler::param_dr_idx_dir(std::ostream &stream, offs_t pc,const data_buffer &opcodes) { stream << "DR,XAR,"; - direct_addr(stream , &oprom[ 1 ]); + direct_addr(stream, pc+1, opcodes); return 2; } -static offs_t param_xr_lit(std::ostream &stream , offs_t pc ,const uint8_t *oprom) +offs_t capricorn_disassembler::param_xr_lit(std::ostream &stream, offs_t pc,const data_buffer &opcodes) { stream << "XR,"; - direct_addr(stream , &oprom[ 1 ]); + direct_addr(stream, pc+1, opcodes); return 2; } -static offs_t param_lit_dir(std::ostream &stream , offs_t pc ,const uint8_t *oprom) +offs_t capricorn_disassembler::param_lit_dir(std::ostream &stream, offs_t pc,const data_buffer &opcodes) { stream << "="; - direct_addr(stream , &oprom[ 1 ]); + direct_addr(stream, pc+1, opcodes); return 2; } -static offs_t param_dr_id_ar(std::ostream &stream , offs_t pc , const uint8_t *oprom) +offs_t capricorn_disassembler::param_dr_id_ar(std::ostream &stream, offs_t pc, const data_buffer &opcodes) { - stream << "DR," << (BIT(oprom[ 0 ] , 1) ? '-' : '+') << "AR"; + stream << "DR," << (BIT(opcodes.r8(pc), 1) ? '-' : '+') << "AR"; return 0; } -static offs_t param_jmp_off(std::ostream &stream , offs_t pc , const uint8_t *oprom) +offs_t capricorn_disassembler::param_jmp_off(std::ostream &stream, offs_t pc, const data_buffer &opcodes) { - uint16_t off = oprom[ 1 ]; - if (BIT(off , 7)) { + uint16_t off = opcodes.r8(pc+1); + if (BIT(off, 7)) { off -= 0x100; } - util::stream_format(stream , "$%04x" , (pc + 2 + off) & 0xffff); + util::stream_format(stream, "$%04x", (pc + 2 + off) & 0xffff); return 1; } -static const dis_entry_t dis_table[] = { - { 0xff , 0x01 , "ARP R*" , false , '\0' , nullptr , 0 }, - { 0xc0 , 0x00 , "ARP" , false , '\0' , param_arp_drp , 0 }, - { 0xff , 0x41 , "DRP R*" , false , '\0' , nullptr , 0 }, - { 0xc0 , 0x40 , "DRP" , false , '\0' , param_arp_drp , 0 }, - { 0xfe , 0x80 , "EL" , true , '\0' , param_dr , 0 }, - { 0xfe , 0x82 , "ER" , true , '\0' , param_dr , 0 }, - { 0xfe , 0x84 , "LL" , true , '\0' , param_dr , 0 }, - { 0xfe , 0x86 , "LR" , true , '\0' , param_dr , 0 }, - { 0xfe , 0x88 , "IC" , true , '\0' , param_dr , 0 }, - { 0xfe , 0x8a , "DC" , true , '\0' , param_dr , 0 }, - { 0xfe , 0x8c , "TC" , true , '\0' , param_dr , 0 }, - { 0xfe , 0x8e , "NC" , true , '\0' , param_dr , 0 }, - { 0xfe , 0x90 , "TS" , true , '\0' , param_dr , 0 }, - { 0xfe , 0x92 , "CL" , true , '\0' , param_dr , 0 }, - { 0xfe , 0x94 , "OR" , true , '\0' , param_dr_ar , 0 }, - { 0xfe , 0x96 , "XR" , true , '\0' , param_dr_ar , 0 }, - { 0xff , 0x98 , "BIN" , false , '\0' , nullptr , 0 }, - { 0xff , 0x99 , "BCD" , false , '\0' , nullptr , 0 }, - { 0xff , 0x9a , "SAD" , false , '\0' , nullptr , 0 }, - { 0xff , 0x9b , "DCE" , false , '\0' , nullptr , 0 }, - { 0xff , 0x9c , "ICE" , false , '\0' , nullptr , 0 }, - { 0xff , 0x9d , "CLE" , false , '\0' , nullptr , 0 }, - { 0xff , 0x9e , "RTN" , false , '\0' , nullptr , DASMFLAG_STEP_OUT }, - { 0xff , 0x9f , "PAD" , false , '\0' , nullptr , 0 }, - { 0xfe , 0xa0 , "LD" , true , '\0' , param_dr_ar , 0 }, - { 0xfe , 0xa2 , "ST" , true , '\0' , param_dr_ar , 0 }, - { 0xfe , 0xa4 , "LD" , true , 'D' , param_dr_ar , 0 }, - { 0xfe , 0xa6 , "ST" , true , 'D' , param_dr_ar , 0 }, - { 0xfe , 0xa8 , "LD" , true , '\0' , param_dr_lit , 0 }, - { 0xfe , 0xaa , "ST" , true , '\0' , param_dr_lit , 0 }, - { 0xfe , 0xac , "LD" , true , 'I' , param_dr_ar , 0 }, - { 0xfe , 0xae , "ST" , true , 'I' , param_dr_ar , 0 }, - { 0xfe , 0xb0 , "LD" , true , 'D' , param_dr_lit_dir , 0 }, - { 0xfe , 0xb2 , "ST" , true , 'D' , param_dr_lit_dir , 0 }, - { 0xfe , 0xb4 , "LD" , true , 'D' , param_dr_idx_dir , 0 }, - { 0xfe , 0xb6 , "ST" , true , 'D' , param_dr_idx_dir , 0 }, - { 0xfe , 0xb8 , "LD" , true , 'I' , param_dr_lit_dir , 0 }, - { 0xfe , 0xba , "ST" , true , 'I' , param_dr_lit_dir , 0 }, - { 0xfe , 0xbc , "LD" , true , 'I' , param_dr_idx_dir , 0 }, - { 0xfe , 0xbe , "ST" , true , 'I' , param_dr_idx_dir , 0 }, - { 0xfe , 0xc0 , "CM" , true , '\0' , param_dr_ar , 0 }, - { 0xfe , 0xc2 , "AD" , true , '\0' , param_dr_ar , 0 }, - { 0xfe , 0xc4 , "SB" , true , '\0' , param_dr_ar , 0 }, - { 0xff , 0xc6 , "JSB" , false , '\0' , param_xr_lit , DASMFLAG_STEP_OVER }, - { 0xff , 0xc7 , "ANM" , false , '\0' , param_dr_ar , 0 }, - { 0xfe , 0xc8 , "CM" , true , '\0' , param_dr_lit , 0 }, - { 0xfe , 0xca , "AD" , true , '\0' , param_dr_lit , 0 }, - { 0xfe , 0xcc , "SB" , true , '\0' , param_dr_lit , 0 }, - { 0xff , 0xce , "JSB" , false , '\0' , param_lit_dir , DASMFLAG_STEP_OVER }, - { 0xff , 0xcf , "ANM" , false , '\0' , param_dr_lit , 0 }, - { 0xfe , 0xd0 , "CM" , true , 'D' , param_dr_lit_dir , 0 }, - { 0xfe , 0xd2 , "AD" , true , 'D' , param_dr_lit_dir , 0 }, - { 0xfe , 0xd4 , "SB" , true , 'D' , param_dr_lit_dir , 0 }, - { 0xff , 0xd7 , "ANM" , false , 'D' , param_dr_lit_dir , 0 }, - { 0xfe , 0xd8 , "CM" , true , 'D' , param_dr_ar , 0 }, - { 0xfe , 0xda , "AD" , true , 'D' , param_dr_ar , 0 }, - { 0xfe , 0xdc , "SB" , true , 'D' , param_dr_ar , 0 }, - { 0xff , 0xdf , "ANM" , false , 'D' , param_dr_ar , 0 }, - { 0xfc , 0xe0 , "PO" , true , 'D' , param_dr_id_ar , 0 }, - { 0xfc , 0xe4 , "PU" , true , 'D' , param_dr_id_ar , 0 }, - { 0xfc , 0xe8 , "PO" , true , 'I' , param_dr_id_ar , 0 }, - { 0xfc , 0xec , "PU" , true , 'I' , param_dr_id_ar , 0 }, - { 0xff , 0xf0 , "JMP" , false , '\0' , param_jmp_off , 0 }, - { 0xff , 0xf1 , "JNO" , false , '\0' , param_jmp_off , 0 }, - { 0xff , 0xf2 , "JOD" , false , '\0' , param_jmp_off , 0 }, - { 0xff , 0xf3 , "JEV" , false , '\0' , param_jmp_off , 0 }, - { 0xff , 0xf4 , "JNG" , false , '\0' , param_jmp_off , 0 }, - { 0xff , 0xf5 , "JPS" , false , '\0' , param_jmp_off , 0 }, - { 0xff , 0xf6 , "JNZ" , false , '\0' , param_jmp_off , 0 }, - { 0xff , 0xf7 , "JZR" , false , '\0' , param_jmp_off , 0 }, - { 0xff , 0xf8 , "JEN" , false , '\0' , param_jmp_off , 0 }, - { 0xff , 0xf9 , "JEZ" , false , '\0' , param_jmp_off , 0 }, - { 0xff , 0xfa , "JNC" , false , '\0' , param_jmp_off , 0 }, - { 0xff , 0xfb , "JCY" , false , '\0' , param_jmp_off , 0 }, - { 0xff , 0xfc , "JLZ" , false , '\0' , param_jmp_off , 0 }, - { 0xff , 0xfd , "JLN" , false , '\0' , param_jmp_off , 0 }, - { 0xff , 0xfe , "JRZ" , false , '\0' , param_jmp_off , 0 }, - { 0xff , 0xff , "JRN" , false , '\0' , param_jmp_off , 0 }, +const capricorn_disassembler::dis_entry_t capricorn_disassembler::dis_table[] = { + { 0xff, 0x01, "ARP R*", false, '\0', nullptr, 0 }, + { 0xc0, 0x00, "ARP" , false, '\0', &capricorn_disassembler::param_arp_drp, 0 }, + { 0xff, 0x41, "DRP R*", false, '\0', nullptr, 0 }, + { 0xc0, 0x40, "DRP" , false, '\0', &capricorn_disassembler::param_arp_drp, 0 }, + { 0xfe, 0x80, "EL" , true , '\0', &capricorn_disassembler::param_dr, 0 }, + { 0xfe, 0x82, "ER" , true , '\0', &capricorn_disassembler::param_dr, 0 }, + { 0xfe, 0x84, "LL" , true , '\0', &capricorn_disassembler::param_dr, 0 }, + { 0xfe, 0x86, "LR" , true , '\0', &capricorn_disassembler::param_dr, 0 }, + { 0xfe, 0x88, "IC" , true , '\0', &capricorn_disassembler::param_dr, 0 }, + { 0xfe, 0x8a, "DC" , true , '\0', &capricorn_disassembler::param_dr, 0 }, + { 0xfe, 0x8c, "TC" , true , '\0', &capricorn_disassembler::param_dr, 0 }, + { 0xfe, 0x8e, "NC" , true , '\0', &capricorn_disassembler::param_dr, 0 }, + { 0xfe, 0x90, "TS" , true , '\0', &capricorn_disassembler::param_dr, 0 }, + { 0xfe, 0x92, "CL" , true , '\0', &capricorn_disassembler::param_dr, 0 }, + { 0xfe, 0x94, "OR" , true , '\0', &capricorn_disassembler::param_dr_ar, 0 }, + { 0xfe, 0x96, "XR" , true , '\0', &capricorn_disassembler::param_dr_ar, 0 }, + { 0xff, 0x98, "BIN" , false, '\0', nullptr, 0 }, + { 0xff, 0x99, "BCD" , false, '\0', nullptr, 0 }, + { 0xff, 0x9a, "SAD" , false, '\0', nullptr, 0 }, + { 0xff, 0x9b, "DCE" , false, '\0', nullptr, 0 }, + { 0xff, 0x9c, "ICE" , false, '\0', nullptr, 0 }, + { 0xff, 0x9d, "CLE" , false, '\0', nullptr, 0 }, + { 0xff, 0x9e, "RTN" , false, '\0', nullptr, STEP_OUT }, + { 0xff, 0x9f, "PAD" , false, '\0', nullptr, 0 }, + { 0xfe, 0xa0, "LD" , true , '\0', &capricorn_disassembler::param_dr_ar, 0 }, + { 0xfe, 0xa2, "ST" , true , '\0', &capricorn_disassembler::param_dr_ar, 0 }, + { 0xfe, 0xa4, "LD" , true , 'D' , &capricorn_disassembler::param_dr_ar, 0 }, + { 0xfe, 0xa6, "ST" , true , 'D' , &capricorn_disassembler::param_dr_ar, 0 }, + { 0xfe, 0xa8, "LD" , true , '\0', &capricorn_disassembler::param_dr_lit, 0 }, + { 0xfe, 0xaa, "ST" , true , '\0', &capricorn_disassembler::param_dr_lit, 0 }, + { 0xfe, 0xac, "LD" , true , 'I' , &capricorn_disassembler::param_dr_ar, 0 }, + { 0xfe, 0xae, "ST" , true , 'I' , &capricorn_disassembler::param_dr_ar, 0 }, + { 0xfe, 0xb0, "LD" , true , 'D' , &capricorn_disassembler::param_dr_lit_dir, 0 }, + { 0xfe, 0xb2, "ST" , true , 'D' , &capricorn_disassembler::param_dr_lit_dir, 0 }, + { 0xfe, 0xb4, "LD" , true , 'D' , &capricorn_disassembler::param_dr_idx_dir, 0 }, + { 0xfe, 0xb6, "ST" , true , 'D' , &capricorn_disassembler::param_dr_idx_dir, 0 }, + { 0xfe, 0xb8, "LD" , true , 'I' , &capricorn_disassembler::param_dr_lit_dir, 0 }, + { 0xfe, 0xba, "ST" , true , 'I' , &capricorn_disassembler::param_dr_lit_dir, 0 }, + { 0xfe, 0xbc, "LD" , true , 'I' , &capricorn_disassembler::param_dr_idx_dir, 0 }, + { 0xfe, 0xbe, "ST" , true , 'I' , &capricorn_disassembler::param_dr_idx_dir, 0 }, + { 0xfe, 0xc0, "CM" , true , '\0', &capricorn_disassembler::param_dr_ar, 0 }, + { 0xfe, 0xc2, "AD" , true , '\0', &capricorn_disassembler::param_dr_ar, 0 }, + { 0xfe, 0xc4, "SB" , true , '\0', &capricorn_disassembler::param_dr_ar, 0 }, + { 0xff, 0xc6, "JSB" , false, '\0', &capricorn_disassembler::param_xr_lit, STEP_OVER }, + { 0xff, 0xc7, "ANM" , false, '\0', &capricorn_disassembler::param_dr_ar, 0 }, + { 0xfe, 0xc8, "CM" , true , '\0', &capricorn_disassembler::param_dr_lit, 0 }, + { 0xfe, 0xca, "AD" , true , '\0', &capricorn_disassembler::param_dr_lit, 0 }, + { 0xfe, 0xcc, "SB" , true , '\0', &capricorn_disassembler::param_dr_lit, 0 }, + { 0xff, 0xce, "JSB" , false, '\0', &capricorn_disassembler::param_lit_dir, STEP_OVER }, + { 0xff, 0xcf, "ANM" , false, '\0', &capricorn_disassembler::param_dr_lit, 0 }, + { 0xfe, 0xd0, "CM" , true , 'D' , &capricorn_disassembler::param_dr_lit_dir, 0 }, + { 0xfe, 0xd2, "AD" , true , 'D' , &capricorn_disassembler::param_dr_lit_dir, 0 }, + { 0xfe, 0xd4, "SB" , true , 'D' , &capricorn_disassembler::param_dr_lit_dir, 0 }, + { 0xff, 0xd7, "ANM" , false, 'D' , &capricorn_disassembler::param_dr_lit_dir, 0 }, + { 0xfe, 0xd8, "CM" , true , 'D' , &capricorn_disassembler::param_dr_ar, 0 }, + { 0xfe, 0xda, "AD" , true , 'D' , &capricorn_disassembler::param_dr_ar, 0 }, + { 0xfe, 0xdc, "SB" , true , 'D' , &capricorn_disassembler::param_dr_ar, 0 }, + { 0xff, 0xdf, "ANM" , false, 'D' , &capricorn_disassembler::param_dr_ar, 0 }, + { 0xfc, 0xe0, "PO" , true , 'D' , &capricorn_disassembler::param_dr_id_ar, 0 }, + { 0xfc, 0xe4, "PU" , true , 'D' , &capricorn_disassembler::param_dr_id_ar, 0 }, + { 0xfc, 0xe8, "PO" , true , 'I' , &capricorn_disassembler::param_dr_id_ar, 0 }, + { 0xfc, 0xec, "PU" , true , 'I' , &capricorn_disassembler::param_dr_id_ar, 0 }, + { 0xff, 0xf0, "JMP" , false, '\0', &capricorn_disassembler::param_jmp_off, 0 }, + { 0xff, 0xf1, "JNO" , false, '\0', &capricorn_disassembler::param_jmp_off, 0 }, + { 0xff, 0xf2, "JOD" , false, '\0', &capricorn_disassembler::param_jmp_off, 0 }, + { 0xff, 0xf3, "JEV" , false, '\0', &capricorn_disassembler::param_jmp_off, 0 }, + { 0xff, 0xf4, "JNG" , false, '\0', &capricorn_disassembler::param_jmp_off, 0 }, + { 0xff, 0xf5, "JPS" , false, '\0', &capricorn_disassembler::param_jmp_off, 0 }, + { 0xff, 0xf6, "JNZ" , false, '\0', &capricorn_disassembler::param_jmp_off, 0 }, + { 0xff, 0xf7, "JZR" , false, '\0', &capricorn_disassembler::param_jmp_off, 0 }, + { 0xff, 0xf8, "JEN" , false, '\0', &capricorn_disassembler::param_jmp_off, 0 }, + { 0xff, 0xf9, "JEZ" , false, '\0', &capricorn_disassembler::param_jmp_off, 0 }, + { 0xff, 0xfa, "JNC" , false, '\0', &capricorn_disassembler::param_jmp_off, 0 }, + { 0xff, 0xfb, "JCY" , false, '\0', &capricorn_disassembler::param_jmp_off, 0 }, + { 0xff, 0xfc, "JLZ" , false, '\0', &capricorn_disassembler::param_jmp_off, 0 }, + { 0xff, 0xfd, "JLN" , false, '\0', &capricorn_disassembler::param_jmp_off, 0 }, + { 0xff, 0xfe, "JRZ" , false, '\0', &capricorn_disassembler::param_jmp_off, 0 }, + { 0xff, 0xff, "JRN" , false, '\0', &capricorn_disassembler::param_jmp_off, 0 }, // *** END *** - {0 , 0 , nullptr , false , 0 , nullptr , 0 } + {0, 0, nullptr, false, 0, nullptr, 0 } }; -CPU_DISASSEMBLE(capricorn) +u32 capricorn_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t capricorn_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { const dis_entry_t *p; - uint8_t opcode = oprom[ 0 ]; + uint8_t opcode = opcodes.r8(pc); for (p = dis_table; p->m_op_mask; p++) { if ((opcode & p->m_op_mask) == p->m_opcode) { - offs_t res = 1 | p->m_dasm_flags | DASMFLAG_SUPPORTED; + offs_t res = 1 | p->m_dasm_flags | SUPPORTED; stream << p->m_mnemonic; if (p->m_has_mb) { - stream << (BIT(opcode , 0) ? 'M' : 'B'); + stream << (BIT(opcode, 0) ? 'M' : 'B'); } if (p->m_addr_mode != '\0') { stream << p->m_addr_mode; } if (p->m_param_fn != nullptr) { stream << " "; - res += p->m_param_fn(stream , pc , oprom); + res += (this->*(p->m_param_fn))(stream, pc, opcodes); } return res; } @@ -210,5 +203,5 @@ CPU_DISASSEMBLE(capricorn) // Unknown opcode stream << "???"; - return 1 | DASMFLAG_SUPPORTED; + return 1 | SUPPORTED; } diff --git a/src/devices/cpu/capricorn/capricorn_dasm.h b/src/devices/cpu/capricorn/capricorn_dasm.h new file mode 100644 index 00000000000..af3525fd03b --- /dev/null +++ b/src/devices/cpu/capricorn/capricorn_dasm.h @@ -0,0 +1,50 @@ +// license:BSD-3-Clause +// copyright-holders:F. Ulivi +// ******************************************************************************** +// * HP Capricorn processor disassembler +// ******************************************************************************** + +#ifndef MAME_CPU_CAPRICORN_CAPRICORN_DASM_H +#define MAME_CPU_CAPRICORN_CAPRICORN_DASM_H + +#pragma once + +class capricorn_disassembler : public util::disasm_interface +{ +public: + capricorn_disassembler() = default; + virtual ~capricorn_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + typedef offs_t (capricorn_disassembler::*fn_dis_param)(std::ostream &stream, offs_t pc, const data_buffer &opcodes); + + struct dis_entry_t { + uint8_t m_op_mask; + uint8_t m_opcode; + const char *m_mnemonic; + bool m_has_mb; + char m_addr_mode; + fn_dis_param m_param_fn; + uint32_t m_dasm_flags; + }; + + static const dis_entry_t dis_table[]; + + void direct_addr(std::ostream &stream, offs_t pc, const data_buffer &opcodes); + offs_t param_arp_drp(std::ostream &stream, offs_t pc, const data_buffer &opcodes); + offs_t param_dr(std::ostream &stream, offs_t pc, const data_buffer &opcodes); + offs_t param_dr_ar(std::ostream &stream, offs_t pc, const data_buffer &opcodes); + offs_t param_dr_lit(std::ostream &stream, offs_t pc, const data_buffer &opcodes); + offs_t param_dr_lit_dir(std::ostream &stream, offs_t pc,const data_buffer &opcodes); + offs_t param_dr_idx_dir(std::ostream &stream, offs_t pc,const data_buffer &opcodes); + offs_t param_xr_lit(std::ostream &stream, offs_t pc,const data_buffer &opcodes); + offs_t param_lit_dir(std::ostream &stream, offs_t pc,const data_buffer &opcodes); + offs_t param_dr_id_ar(std::ostream &stream, offs_t pc, const data_buffer &opcodes); + offs_t param_jmp_off(std::ostream &stream, offs_t pc, const data_buffer &opcodes); + +}; + +#endif diff --git a/src/devices/cpu/ccpu/ccpu.cpp b/src/devices/cpu/ccpu/ccpu.cpp index cc13d8e9125..5f04c3d7235 100644 --- a/src/devices/cpu/ccpu/ccpu.cpp +++ b/src/devices/cpu/ccpu/ccpu.cpp @@ -12,6 +12,7 @@ #include "emu.h" #include "ccpu.h" +#include "ccpudasm.h" #include "debugger.h" @@ -695,8 +696,7 @@ void ccpu_cpu_device::execute_run() } -offs_t ccpu_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *ccpu_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( ccpu ); - return CPU_DISASSEMBLE_NAME(ccpu)(this, stream, pc, oprom, opram, options); + return new ccpu_disassembler; } diff --git a/src/devices/cpu/ccpu/ccpu.h b/src/devices/cpu/ccpu/ccpu.h index 3a74c21a1fe..5b45f19b64c 100644 --- a/src/devices/cpu/ccpu/ccpu.h +++ b/src/devices/cpu/ccpu/ccpu.h @@ -78,9 +78,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 3; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; address_space_config m_program_config; address_space_config m_data_config; diff --git a/src/devices/cpu/ccpu/ccpudasm.cpp b/src/devices/cpu/ccpu/ccpudasm.cpp index bb843374c2b..feb4ebcb58d 100644 --- a/src/devices/cpu/ccpu/ccpudasm.cpp +++ b/src/devices/cpu/ccpu/ccpudasm.cpp @@ -11,13 +11,17 @@ ***************************************************************************/ #include "emu.h" -#include "ccpu.h" +#include "ccpudasm.h" +u32 ccpu_disassembler::opcode_alignment() const +{ + return 1; +} -CPU_DISASSEMBLE(ccpu) +offs_t ccpu_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { unsigned startpc = pc; - uint8_t opcode = oprom[pc++ - startpc]; + uint8_t opcode = opcodes.r8(pc++); uint8_t tempval; switch (opcode) @@ -40,7 +44,7 @@ CPU_DISASSEMBLE(ccpu) /* A8I */ case 0x20: - util::stream_format(stream, "A8I $%X", oprom[pc++ - startpc]); + util::stream_format(stream, "A8I $%X", opcodes.r8(pc++)); break; /* A4I */ @@ -53,7 +57,7 @@ CPU_DISASSEMBLE(ccpu) /* S8I */ case 0x30: - util::stream_format(stream, "S8I $%X", oprom[pc++ - startpc]); + util::stream_format(stream, "S8I $%X", opcodes.r8(pc++)); break; /* S4I */ @@ -69,7 +73,7 @@ CPU_DISASSEMBLE(ccpu) case 0x44: case 0x45: case 0x46: case 0x47: case 0x48: case 0x49: case 0x4a: case 0x4b: case 0x4c: case 0x4d: case 0x4e: case 0x4f: - tempval = oprom[pc++ - startpc]; + tempval = opcodes.r8(pc++); util::stream_format(stream, "LPAI $%03X", (opcode & 0x0f) + (tempval & 0xf0) + ((tempval & 0x0f) << 8)); break; @@ -326,5 +330,5 @@ CPU_DISASSEMBLE(ccpu) break; } - return (pc - startpc) | DASMFLAG_SUPPORTED; + return (pc - startpc) | SUPPORTED; } diff --git a/src/devices/cpu/ccpu/ccpudasm.h b/src/devices/cpu/ccpu/ccpudasm.h new file mode 100644 index 00000000000..b9c4b83c6e6 --- /dev/null +++ b/src/devices/cpu/ccpu/ccpudasm.h @@ -0,0 +1,28 @@ +// license:BSD-3-Clause +// copyright-holders:Aaron Giles +/*************************************************************************** + + ccpudasm.c + Core implementation for the portable Cinematronics CPU disassembler. + + Written by Aaron Giles + Special thanks to Zonn Moore for his detailed documentation. + +***************************************************************************/ + +#ifndef MAME_CPU_CCPU_CCPUDASM_H +#define MAME_CPU_CCPU_CCPUDASM_H + +#pragma once + +class ccpu_disassembler : public util::disasm_interface +{ +public: + ccpu_disassembler() = default; + virtual ~ccpu_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/clipper/clipper.cpp b/src/devices/cpu/clipper/clipper.cpp index d7498beb6f2..c2f8c85dfd8 100644 --- a/src/devices/cpu/clipper/clipper.cpp +++ b/src/devices/cpu/clipper/clipper.cpp @@ -19,6 +19,7 @@ #include "emu.h" #include "debugger.h" #include "clipper.h" +#include "clipperd.h" #define LOG_GENERAL (1U << 0) #define LOG_INTERRUPT (1U << 1) @@ -1652,7 +1653,7 @@ inline void clipper_device::set_fp64(const u8 reg, const float64 data) m_ssw |= SSW_FRD; } -offs_t clipper_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +util::disasm_interface *clipper_device::create_disassembler() { - return CPU_DISASSEMBLE_NAME(clipper)(this, stream, pc, oprom, opram, options); + return new clipper_disassembler; } diff --git a/src/devices/cpu/clipper/clipper.h b/src/devices/cpu/clipper/clipper.h index 6a1d5dc0ba2..667e835d8c8 100644 --- a/src/devices/cpu/clipper/clipper.h +++ b/src/devices/cpu/clipper/clipper.h @@ -221,9 +221,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual u32 disasm_min_opcode_bytes() const override { return 2; } // smallest instruction - virtual u32 disasm_max_opcode_bytes() const override { return 8; } // largest instruction - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; void set_ssw(u32 data) { m_ssw = (m_ssw & SSW(ID)) | (data & ~SSW(ID)); } @@ -314,6 +312,4 @@ DECLARE_DEVICE_TYPE(CLIPPER_C100, clipper_c100_device) DECLARE_DEVICE_TYPE(CLIPPER_C300, clipper_c300_device) DECLARE_DEVICE_TYPE(CLIPPER_C400, clipper_c400_device) -extern CPU_DISASSEMBLE(clipper); - #endif // MAME_CPU_CLIPPER_CLIPPER_H diff --git a/src/devices/cpu/clipper/clipperd.cpp b/src/devices/cpu/clipper/clipperd.cpp index 521f13d1c8d..d328d3b4631 100644 --- a/src/devices/cpu/clipper/clipperd.cpp +++ b/src/devices/cpu/clipper/clipperd.cpp @@ -2,6 +2,7 @@ // copyright-holders:Patrick Mackinlay #include "emu.h" +#include "clipperd.h" /* * TODO @@ -14,33 +15,20 @@ // enable C400 instruction decoding #define C400_INSTRUCTIONS 1 -// the CLIPPER addressing modes (unshifted) -enum -{ - ADDR_MODE_PC32 = 0x10, - ADDR_MODE_ABS32 = 0x30, - ADDR_MODE_REL32 = 0x60, - ADDR_MODE_PC16 = 0x90, - ADDR_MODE_REL12 = 0xa0, - ADDR_MODE_ABS16 = 0xb0, - ADDR_MODE_PCX = 0xd0, - ADDR_MODE_RELX = 0xe0 -}; - // macros for decoding various operand fields -#define R1 ((insn[0] & 0x00f0) >> 4) -#define R2 (insn[0] & 0x000f) +#define R1 ((opcodes.r16(pc) & 0x00f0) >> 4) +#define R2 (opcodes.r16(pc) & 0x000f) -#define I16 ((int16_t)insn[1]) -#define I32 (*(int32_t *)&insn[1]) -#define IMM_VALUE (insn[0] & 0x0080 ? I16 : I32) -#define IMM_SIZE (insn[0] & 0x0080 ? 2 : 4) +#define I16 (int16_t(opcodes.r16(pc+2))) +#define I32 (int32_t(opcodes.r32(pc+2))) +#define IMM_VALUE (opcodes.r16(pc) & 0x0080 ? I16 : I32) +#define IMM_SIZE (opcodes.r16(pc) & 0x0080 ? 2 : 4) -#define ADDR_MODE (insn[0] & 0x00f0) -#define ADDR_R2 ((insn[0] & 0x0050) == 0x0010 ? (insn[0] & 0x000f) : (insn[1] & 0x000f)) +#define ADDR_MODE (opcodes.r16(pc) & 0x00f0) +#define ADDR_R2 ((opcodes.r16(pc) & 0x0050) == 0x0010 ? (opcodes.r16(pc) & 0x000f) : (opcodes.r16(pc+2) & 0x000f)) #define ADDR_SIZE (ADDR_MODE > ADDR_MODE_REL32 ? 2 : ADDR_MODE == ADDR_MODE_REL32 ? 6 : 4) -#define ADDR_RX ((insn[1] & 0xf0) >> 4) -#define ADDR_I12 (((int16_t)insn[1]) >> 4) +#define ADDR_RX ((opcodes.r16(pc+2) & 0xf0) >> 4) +#define ADDR_I12 (((int16_t)opcodes.r16(pc+2)) >> 4) /* * Branch condition code mnemonics - the forms beginning with 'c' are @@ -49,7 +37,7 @@ enum * instructions. We use the first form because we can't know which type * should be used without some kind of dynamic information. */ -static const char *const cc[] = +const char *const clipper_disassembler::cc[] = { "", "clt", // rgt @@ -72,13 +60,13 @@ static const char *const cc[] = /* * Decode an addressing mode into a string. */ -std::string address (offs_t pc, u16 *insn) +std::string clipper_disassembler::address (offs_t pc, const data_buffer &opcodes) { switch (ADDR_MODE) { case ADDR_MODE_PC32: return util::string_format("0x%x", pc + I32); case ADDR_MODE_ABS32: return util::string_format("0x%x", I32); - case ADDR_MODE_REL32: return util::string_format("%d(r%d)", *(int32_t *)&insn[2], R2); + case ADDR_MODE_REL32: return util::string_format("%d(r%d)", opcodes.r32(pc+4), R2); case ADDR_MODE_PC16: return util::string_format("0x%x", pc + I16); case ADDR_MODE_REL12: return util::string_format("%d(r%d)", ADDR_I12, R2); case ADDR_MODE_ABS16: return util::string_format("0x%x", I16); @@ -96,26 +84,30 @@ std::string address (offs_t pc, u16 *insn) * an on-CPU macro instruction ROM. It appears at least some of these macro instructions were removed * from the C400 and generate traps which can be used to implement them in software instead. */ -CPU_DISASSEMBLE(clipper) +u32 clipper_disassembler::opcode_alignment() const +{ + return 2; +} + +offs_t clipper_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - u16 *insn = (u16 *)oprom; - u32 flags = DASMFLAG_SUPPORTED; + u32 flags = SUPPORTED; offs_t bytes; - switch (insn[0] >> 8) + switch (opcodes.r16(pc) >> 8) { case 0x00: - if (oprom[0] == 0) + if (opcodes.r16(pc) == 0) util::stream_format(stream, "noop"); else - util::stream_format(stream, "noop $%d", oprom[0]); + util::stream_format(stream, "noop $%d", opcodes.r16(pc)); bytes = 2; break; case 0x10: util::stream_format(stream, "movwp r%d,%s", R2, R1 == 0 ? "psw" : R1 == 1 ? "ssw" : "sswf"); bytes = 2; break; case 0x11: util::stream_format(stream, "movpw %s,r%d", R1 == 0 ? "psw" : "ssw", R2); bytes = 2; break; - case 0x12: util::stream_format(stream, "calls $%d", insn[0] & 0x7F); bytes = 2; flags |= DASMFLAG_STEP_OVER; break; - case 0x13: util::stream_format(stream, "ret r%d", R2); bytes = 2; flags |= DASMFLAG_STEP_OUT; break; + case 0x12: util::stream_format(stream, "calls $%d", opcodes.r16(pc) & 0x7F); bytes = 2; flags |= STEP_OVER; break; + case 0x13: util::stream_format(stream, "ret r%d", R2); bytes = 2; flags |= STEP_OUT; break; case 0x14: util::stream_format(stream, "pushw r%d,r%d", R2, R1); bytes = 2; break; case 0x16: util::stream_format(stream, "popw r%d,r%d", R1, R2); bytes = 2; break; @@ -151,60 +143,60 @@ CPU_DISASSEMBLE(clipper) case 0x3c: util::stream_format(stream, "roti $%d,r%d", I16, R2); bytes = 4; break; case 0x3d: util::stream_format(stream, "rotli $%d,r%d:r%d", I16, R2 + 0, R2 + 1); bytes = 4; break; - case 0x44: util::stream_format(stream, "call r%d,(r%d)", R2, R1); bytes = 2; flags |= DASMFLAG_STEP_OVER; break; - case 0x45: util::stream_format(stream, "call r%d,%s", ADDR_R2, address(pc, insn)); bytes = 2 + ADDR_SIZE; flags |= DASMFLAG_STEP_OVER; break; + case 0x44: util::stream_format(stream, "call r%d,(r%d)", R2, R1); bytes = 2; flags |= STEP_OVER; break; + case 0x45: util::stream_format(stream, "call r%d,%s", ADDR_R2, address(pc, opcodes)); bytes = 2 + ADDR_SIZE; flags |= STEP_OVER; break; #if C400_INSTRUCTIONS case 0x46: util::stream_format(stream, "loadd2 (r%d),f%d", R1, R2); bytes = 2; break; - case 0x47: util::stream_format(stream, "loadd2 %s,f%d", address(pc, insn), ADDR_R2); bytes = 2 + ADDR_SIZE; break; + case 0x47: util::stream_format(stream, "loadd2 %s,f%d", address(pc, opcodes), ADDR_R2); bytes = 2 + ADDR_SIZE; break; #endif case 0x48: util::stream_format(stream, "b%-4s (r%d)", cc[R2], R1); bytes = 2; break; - case 0x49: util::stream_format(stream, "b%-4s %s", cc[ADDR_R2], address(pc, insn)); bytes = 2 + ADDR_SIZE; break; + case 0x49: util::stream_format(stream, "b%-4s %s", cc[ADDR_R2], address(pc, opcodes)); bytes = 2 + ADDR_SIZE; break; #if C400_INSTRUCTIONS // delayed branches case 0x4a: util::stream_format(stream, "cdb r%d,(r%d)", R2, R1); bytes = 2; break; - case 0x4b: util::stream_format(stream, "cdb r%d,%s", ADDR_R2, address(pc, insn)); bytes = 2 + ADDR_SIZE; break; + case 0x4b: util::stream_format(stream, "cdb r%d,%s", ADDR_R2, address(pc, opcodes)); bytes = 2 + ADDR_SIZE; break; case 0x4c: util::stream_format(stream, "cdbeq r%d,(r%d)", R2, R1); bytes = 2; break; - case 0x4d: util::stream_format(stream, "cdbeq r%d,%s", ADDR_R2, address(pc, insn)); bytes = 2 + ADDR_SIZE; break; + case 0x4d: util::stream_format(stream, "cdbeq r%d,%s", ADDR_R2, address(pc, opcodes)); bytes = 2 + ADDR_SIZE; break; case 0x4e: util::stream_format(stream, "cdbne r%d,(r%d)", R2, R1); bytes = 2; break; - case 0x4f: util::stream_format(stream, "cdbne r%d,%s", ADDR_R2, address(pc, insn)); bytes = 2 + ADDR_SIZE; break; + case 0x4f: util::stream_format(stream, "cdbne r%d,%s", ADDR_R2, address(pc, opcodes)); bytes = 2 + ADDR_SIZE; break; case 0x50: util::stream_format(stream, "db%-4s (r%d)", cc[R2], R1); bytes = 2; break; - case 0x51: util::stream_format(stream, "db%-4s %s", cc[ADDR_R2], address(pc, insn)); bytes = 2 + ADDR_SIZE; break; + case 0x51: util::stream_format(stream, "db%-4s %s", cc[ADDR_R2], address(pc, opcodes)); bytes = 2 + ADDR_SIZE; break; #else // these instructions are in the C300 documentation, but appear to be replaced in the C400 case 0x4c: util::stream_format(stream, "bf%s (r%d)", R2 == 0 ? "any" : "bad", R1); bytes = 2; break; - case 0x4d: util::stream_format(stream, "bf%s %s", ADDR_R2 == 0 ? "any" : "bad", address(pc, insn)); bytes = 2 + ADDR_SIZE; break; + case 0x4d: util::stream_format(stream, "bf%s %s", ADDR_R2 == 0 ? "any" : "bad", address(pc, opcodes)); bytes = 2 + ADDR_SIZE; break; #endif case 0x60: util::stream_format(stream, "loadw (r%d),r%d", R1, R2); bytes = 2; break; - case 0x61: util::stream_format(stream, "loadw %s,r%d", address(pc, insn), ADDR_R2); bytes = 2 + ADDR_SIZE; break; + case 0x61: util::stream_format(stream, "loadw %s,r%d", address(pc, opcodes), ADDR_R2); bytes = 2 + ADDR_SIZE; break; case 0x62: util::stream_format(stream, "loada (r%d),r%d", R1, R2); bytes = 2; break; - case 0x63: util::stream_format(stream, "loada %s,r%d", address(pc, insn), ADDR_R2); bytes = 2 + ADDR_SIZE; break; + case 0x63: util::stream_format(stream, "loada %s,r%d", address(pc, opcodes), ADDR_R2); bytes = 2 + ADDR_SIZE; break; case 0x64: util::stream_format(stream, "loads (r%d),f%d", R1, R2); bytes = 2; break; - case 0x65: util::stream_format(stream, "loads %s,f%d", address(pc, insn), ADDR_R2); bytes = 2 + ADDR_SIZE; break; + case 0x65: util::stream_format(stream, "loads %s,f%d", address(pc, opcodes), ADDR_R2); bytes = 2 + ADDR_SIZE; break; case 0x66: util::stream_format(stream, "loadd (r%d),f%d", R1, R2); bytes = 2; break; - case 0x67: util::stream_format(stream, "loadd %s,f%d", address(pc, insn), ADDR_R2); bytes = 2 + ADDR_SIZE; break; + case 0x67: util::stream_format(stream, "loadd %s,f%d", address(pc, opcodes), ADDR_R2); bytes = 2 + ADDR_SIZE; break; case 0x68: util::stream_format(stream, "loadb (r%d),r%d", R1, R2); bytes = 2; break; - case 0x69: util::stream_format(stream, "loadb %s,r%d", address(pc, insn), ADDR_R2); bytes = 2 + ADDR_SIZE; break; + case 0x69: util::stream_format(stream, "loadb %s,r%d", address(pc, opcodes), ADDR_R2); bytes = 2 + ADDR_SIZE; break; case 0x6a: util::stream_format(stream, "loadbu (r%d),r%d", R1, R2); bytes = 2; break; - case 0x6b: util::stream_format(stream, "loadbu %s,r%d", address(pc, insn), ADDR_R2); bytes = 2 + ADDR_SIZE; break; + case 0x6b: util::stream_format(stream, "loadbu %s,r%d", address(pc, opcodes), ADDR_R2); bytes = 2 + ADDR_SIZE; break; case 0x6c: util::stream_format(stream, "loadh (r%d),r%d", R1, R2); bytes = 2; break; - case 0x6d: util::stream_format(stream, "loadh %s,r%d", address(pc, insn), ADDR_R2); bytes = 2 + ADDR_SIZE; break; + case 0x6d: util::stream_format(stream, "loadh %s,r%d", address(pc, opcodes), ADDR_R2); bytes = 2 + ADDR_SIZE; break; case 0x6e: util::stream_format(stream, "loadhu (r%d),r%d", R1, R2); bytes = 2; break; - case 0x6f: util::stream_format(stream, "loadhu %s,r%d", address(pc, insn), ADDR_R2); bytes = 2 + ADDR_SIZE; break; + case 0x6f: util::stream_format(stream, "loadhu %s,r%d", address(pc, opcodes), ADDR_R2); bytes = 2 + ADDR_SIZE; break; case 0x70: util::stream_format(stream, "storw r%d,(r%d)", R2, R1); bytes = 2; break; - case 0x71: util::stream_format(stream, "storw r%d,%s", ADDR_R2, address(pc, insn)); bytes = 2 + ADDR_SIZE; break; + case 0x71: util::stream_format(stream, "storw r%d,%s", ADDR_R2, address(pc, opcodes)); bytes = 2 + ADDR_SIZE; break; case 0x72: util::stream_format(stream, "tsts (r%d),r%d", R1, R2); bytes = 2; break; - case 0x73: util::stream_format(stream, "tsts %s,r%d", address(pc, insn), ADDR_R2); bytes = 2 + ADDR_SIZE; break; + case 0x73: util::stream_format(stream, "tsts %s,r%d", address(pc, opcodes), ADDR_R2); bytes = 2 + ADDR_SIZE; break; case 0x74: util::stream_format(stream, "stors f%d,(r%d)", R2, R1); bytes = 2; break; - case 0x75: util::stream_format(stream, "stors f%d,%s", ADDR_R2, address(pc, insn)); bytes = 2 + ADDR_SIZE; break; + case 0x75: util::stream_format(stream, "stors f%d,%s", ADDR_R2, address(pc, opcodes)); bytes = 2 + ADDR_SIZE; break; case 0x76: util::stream_format(stream, "stord f%d,(r%d)", R2, R1); bytes = 2; break; - case 0x77: util::stream_format(stream, "stord f%d,%s", ADDR_R2, address(pc, insn)); bytes = 2 + ADDR_SIZE; break; + case 0x77: util::stream_format(stream, "stord f%d,%s", ADDR_R2, address(pc, opcodes)); bytes = 2 + ADDR_SIZE; break; case 0x78: util::stream_format(stream, "storb r%d,(r%d)", R2, R1); bytes = 2; break; - case 0x79: util::stream_format(stream, "storb r%d,%s", ADDR_R2, address(pc, insn)); bytes = 2 + ADDR_SIZE; break; + case 0x79: util::stream_format(stream, "storb r%d,%s", ADDR_R2, address(pc, opcodes)); bytes = 2 + ADDR_SIZE; break; case 0x7c: util::stream_format(stream, "storh r%d,(r%d)", R2, R1); bytes = 2; break; - case 0x7d: util::stream_format(stream, "storh r%d,%s", ADDR_R2, address(pc, insn)); bytes = 2 + ADDR_SIZE; break; + case 0x7d: util::stream_format(stream, "storh r%d,%s", ADDR_R2, address(pc, opcodes)); bytes = 2 + ADDR_SIZE; break; case 0x80: util::stream_format(stream, "addw r%d,r%d", R1, R2); bytes = 2; break; @@ -258,7 +250,7 @@ CPU_DISASSEMBLE(clipper) case 0xb4: case 0xb5: // unprivileged macro instructions - switch (insn[0] & 0xff) + switch (opcodes.r16(pc) & 0xff) { case 0x00: case 0x01: case 0x02: case 0x03: case 0x04: case 0x05: case 0x06: case 0x07: @@ -288,25 +280,25 @@ CPU_DISASSEMBLE(clipper) util::stream_format(stream, "restd%d", R2); break; - case 0x30: util::stream_format(stream, "cnvsw f%d,r%d", (insn[1] & 0xf0) >> 4, insn[1] & 0xf); break; - case 0x31: util::stream_format(stream, "cnvrsw f%d,r%d", (insn[1] & 0xf0) >> 4, insn[1] & 0xf); break; - case 0x32: util::stream_format(stream, "cnvtsw f%d,r%d", (insn[1] & 0xf0) >> 4, insn[1] & 0xf); break; - case 0x33: util::stream_format(stream, "cnvws r%d,f%d", (insn[1] & 0xf0) >> 4, insn[1] & 0xf); break; - case 0x34: util::stream_format(stream, "cnvdw f%d,r%d", (insn[1] & 0xf0) >> 4, insn[1] & 0xf); break; - case 0x35: util::stream_format(stream, "cnvrdw f%d,r%d", (insn[1] & 0xf0) >> 4, insn[1] & 0xf); break; - case 0x36: util::stream_format(stream, "cnvtdw f%d,r%d", (insn[1] & 0xf0) >> 4, insn[1] & 0xf); break; - case 0x37: util::stream_format(stream, "cnvwd r%d,f%d", (insn[1] & 0xf0) >> 4, insn[1] & 0xf); break; - case 0x38: util::stream_format(stream, "cnvsd f%d,f%d", (insn[1] & 0xf0) >> 4, insn[1] & 0xf); break; - case 0x39: util::stream_format(stream, "cnvds f%d,f%d", (insn[1] & 0xf0) >> 4, insn[1] & 0xf); break; - case 0x3a: util::stream_format(stream, "negs f%d,f%d", (insn[1] & 0xf0) >> 4, insn[1] & 0xf); break; - case 0x3b: util::stream_format(stream, "negd f%d,f%d", (insn[1] & 0xf0) >> 4, insn[1] & 0xf); break; - case 0x3c: util::stream_format(stream, "scalbs r%d,f%d", (insn[1] & 0xf0) >> 4, insn[1] & 0xf); break; - case 0x3d: util::stream_format(stream, "scalbd r%d,f%d", (insn[1] & 0xf0) >> 4, insn[1] & 0xf); break; + case 0x30: util::stream_format(stream, "cnvsw f%d,r%d", (opcodes.r16(pc+2) & 0xf0) >> 4, opcodes.r16(pc+2) & 0xf); break; + case 0x31: util::stream_format(stream, "cnvrsw f%d,r%d", (opcodes.r16(pc+2) & 0xf0) >> 4, opcodes.r16(pc+2) & 0xf); break; + case 0x32: util::stream_format(stream, "cnvtsw f%d,r%d", (opcodes.r16(pc+2) & 0xf0) >> 4, opcodes.r16(pc+2) & 0xf); break; + case 0x33: util::stream_format(stream, "cnvws r%d,f%d", (opcodes.r16(pc+2) & 0xf0) >> 4, opcodes.r16(pc+2) & 0xf); break; + case 0x34: util::stream_format(stream, "cnvdw f%d,r%d", (opcodes.r16(pc+2) & 0xf0) >> 4, opcodes.r16(pc+2) & 0xf); break; + case 0x35: util::stream_format(stream, "cnvrdw f%d,r%d", (opcodes.r16(pc+2) & 0xf0) >> 4, opcodes.r16(pc+2) & 0xf); break; + case 0x36: util::stream_format(stream, "cnvtdw f%d,r%d", (opcodes.r16(pc+2) & 0xf0) >> 4, opcodes.r16(pc+2) & 0xf); break; + case 0x37: util::stream_format(stream, "cnvwd r%d,f%d", (opcodes.r16(pc+2) & 0xf0) >> 4, opcodes.r16(pc+2) & 0xf); break; + case 0x38: util::stream_format(stream, "cnvsd f%d,f%d", (opcodes.r16(pc+2) & 0xf0) >> 4, opcodes.r16(pc+2) & 0xf); break; + case 0x39: util::stream_format(stream, "cnvds f%d,f%d", (opcodes.r16(pc+2) & 0xf0) >> 4, opcodes.r16(pc+2) & 0xf); break; + case 0x3a: util::stream_format(stream, "negs f%d,f%d", (opcodes.r16(pc+2) & 0xf0) >> 4, opcodes.r16(pc+2) & 0xf); break; + case 0x3b: util::stream_format(stream, "negd f%d,f%d", (opcodes.r16(pc+2) & 0xf0) >> 4, opcodes.r16(pc+2) & 0xf); break; + case 0x3c: util::stream_format(stream, "scalbs r%d,f%d", (opcodes.r16(pc+2) & 0xf0) >> 4, opcodes.r16(pc+2) & 0xf); break; + case 0x3d: util::stream_format(stream, "scalbd r%d,f%d", (opcodes.r16(pc+2) & 0xf0) >> 4, opcodes.r16(pc+2) & 0xf); break; case 0x3e: util::stream_format(stream, "trapfn"); break; - case 0x3f: util::stream_format(stream, "loadfs r%d,f%d", (insn[1] & 0xf0) >> 4, insn[1] & 0xf); break; + case 0x3f: util::stream_format(stream, "loadfs r%d,f%d", (opcodes.r16(pc+2) & 0xf0) >> 4, opcodes.r16(pc+2) & 0xf); break; default: - util::stream_format(stream, "macro 0x%04x 0x%04x", insn[0], insn[1]); + util::stream_format(stream, "macro 0x%04x 0x%04x", opcodes.r16(pc), opcodes.r16(pc+2)); break; } bytes = 4; @@ -314,19 +306,19 @@ CPU_DISASSEMBLE(clipper) case 0xb6: case 0xb7: // privileged macro instructions - switch (insn[0] & 0xff) + switch (opcodes.r16(pc) & 0xff) { - case 0x00: util::stream_format(stream, "movus r%d,r%d", (insn[1] & 0xf0) >> 4, insn[1] & 0xf); break; - case 0x01: util::stream_format(stream, "movsu r%d,r%d", (insn[1] & 0xf0) >> 4, insn[1] & 0xf); break; - case 0x02: util::stream_format(stream, "saveur r%d", (insn[1] & 0xf0) >> 4); break; - case 0x03: util::stream_format(stream, "restur r%d", (insn[1] & 0xf0) >> 4); break; - case 0x04: util::stream_format(stream, "reti r%d", (insn[1] & 0xf0) >> 4); flags |= DASMFLAG_STEP_OUT; break; + case 0x00: util::stream_format(stream, "movus r%d,r%d", (opcodes.r16(pc+2) & 0xf0) >> 4, opcodes.r16(pc+2) & 0xf); break; + case 0x01: util::stream_format(stream, "movsu r%d,r%d", (opcodes.r16(pc+2) & 0xf0) >> 4, opcodes.r16(pc+2) & 0xf); break; + case 0x02: util::stream_format(stream, "saveur r%d", (opcodes.r16(pc+2) & 0xf0) >> 4); break; + case 0x03: util::stream_format(stream, "restur r%d", (opcodes.r16(pc+2) & 0xf0) >> 4); break; + case 0x04: util::stream_format(stream, "reti r%d", (opcodes.r16(pc+2) & 0xf0) >> 4); flags |= STEP_OUT; break; case 0x05: util::stream_format(stream, "wait"); break; #if C400_INSTRUCTIONS - case 0x07: util::stream_format(stream, "loadts r%d,f%d", (insn[1] & 0xf0) >> 4, insn[1] & 0xf); break; + case 0x07: util::stream_format(stream, "loadts r%d,f%d", (opcodes.r16(pc+2) & 0xf0) >> 4, opcodes.r16(pc+2) & 0xf); break; #endif default: - util::stream_format(stream, "macro 0x%04x 0x%04x", insn[0], insn[1]); + util::stream_format(stream, "macro 0x%04x 0x%04x", opcodes.r16(pc), opcodes.r16(pc+2)); break; } bytes = 4; @@ -338,7 +330,7 @@ CPU_DISASSEMBLE(clipper) #endif default: - util::stream_format(stream, ".word 0x%04x", insn[0]); + util::stream_format(stream, ".word 0x%04x", opcodes.r16(pc)); bytes = 2; break; } diff --git a/src/devices/cpu/clipper/clipperd.h b/src/devices/cpu/clipper/clipperd.h new file mode 100644 index 00000000000..cad59a490de --- /dev/null +++ b/src/devices/cpu/clipper/clipperd.h @@ -0,0 +1,38 @@ +// license:BSD-3-Clause +// copyright-holders:Patrick Mackinlay + +#ifndef MAME_CPU_CLIPPER_CLIPPERDASM_H +#define MAME_CPU_CLIPPER_CLIPPERDASM_H + +#pragma once + +class clipper_disassembler : public util::disasm_interface +{ +public: + clipper_disassembler() = default; + virtual ~clipper_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + // the CLIPPER addressing modes (unshifted) + enum + { + ADDR_MODE_PC32 = 0x10, + ADDR_MODE_ABS32 = 0x30, + ADDR_MODE_REL32 = 0x60, + ADDR_MODE_PC16 = 0x90, + ADDR_MODE_REL12 = 0xa0, + ADDR_MODE_ABS16 = 0xb0, + ADDR_MODE_PCX = 0xd0, + ADDR_MODE_RELX = 0xe0 + }; + + static const char *const cc[]; + std::string address (offs_t pc, const data_buffer &opcodes); + + +}; + +#endif diff --git a/src/devices/cpu/cop400/cop400.cpp b/src/devices/cpu/cop400/cop400.cpp index 696e504835d..5451e6775c3 100644 --- a/src/devices/cpu/cop400/cop400.cpp +++ b/src/devices/cpu/cop400/cop400.cpp @@ -56,6 +56,10 @@ #include "emu.h" #include "debugger.h" #include "cop400.h" +#include "cop410ds.h" +#include "cop420ds.h" +#include "cop424ds.h" +#include "cop444ds.h" DEFINE_DEVICE_TYPE(COP401, cop401_cpu_device, "cop401", "COP401") @@ -1362,29 +1366,24 @@ void cop400_cpu_device::state_string_export(const device_state_entry &entry, std } -offs_t cop400_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *cop400_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( cop410 ); - extern CPU_DISASSEMBLE( cop420 ); - extern CPU_DISASSEMBLE( cop444 ); - extern CPU_DISASSEMBLE( cop424 ); - if ( m_featuremask & COP424C_FEATURE ) { - return CPU_DISASSEMBLE_NAME(cop424)(this, stream, pc, oprom, opram, options); + return new cop424_disassembler; } if ( m_featuremask & COP444L_FEATURE ) { - return CPU_DISASSEMBLE_NAME(cop444)(this, stream, pc, oprom, opram, options); + return new cop444_disassembler; } if ( m_featuremask & COP420_FEATURE ) { - return CPU_DISASSEMBLE_NAME(cop420)(this, stream, pc, oprom, opram, options); + return new cop420_disassembler; } - return CPU_DISASSEMBLE_NAME(cop410)(this, stream, pc, oprom, opram, options); + return new cop410_disassembler; } READ8_MEMBER( cop400_cpu_device::microbus_rd ) diff --git a/src/devices/cpu/cop400/cop400.h b/src/devices/cpu/cop400/cop400.h index 3a047d10c8a..257fbfa693e 100644 --- a/src/devices/cpu/cop400/cop400.h +++ b/src/devices/cpu/cop400/cop400.h @@ -165,9 +165,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 2; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; address_space_config m_program_config; address_space_config m_data_config; diff --git a/src/devices/cpu/cop400/cop410ds.cpp b/src/devices/cpu/cop400/cop410ds.cpp index 4570417538f..9da69df8034 100644 --- a/src/devices/cpu/cop400/cop410ds.cpp +++ b/src/devices/cpu/cop400/cop410ds.cpp @@ -9,11 +9,17 @@ ***************************************************************************/ #include "emu.h" +#include "cop410ds.h" -CPU_DISASSEMBLE(cop410) +u32 cop410_disassembler::opcode_alignment() const { - uint8_t opcode = oprom[0]; - uint8_t next_opcode = oprom[1]; + return 1; +} + +offs_t cop410_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + uint8_t opcode = opcodes.r8(pc); + uint8_t next_opcode = opcodes.r8(pc+1); uint16_t address; uint32_t flags = 0; int bytes = 1; @@ -38,7 +44,7 @@ CPU_DISASSEMBLE(cop410) { address = (uint16_t)(0x80 | (opcode & 0x3F)); util::stream_format(stream, "JSRP %03X", address); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; } } } @@ -72,7 +78,7 @@ CPU_DISASSEMBLE(cop410) { address = ((opcode & 0x01) << 8) | next_opcode; util::stream_format(stream, "JSR %03X", address); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; bytes = 2; } else if (opcode >= 0x70 && opcode <= 0x7F) @@ -302,12 +308,12 @@ CPU_DISASSEMBLE(cop410) case 0x48: util::stream_format(stream, "RET"); - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; case 0x49: util::stream_format(stream, "RETSK"); - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; case 0x4B: @@ -348,5 +354,5 @@ CPU_DISASSEMBLE(cop410) } } - return bytes | flags | DASMFLAG_SUPPORTED; + return bytes | flags | SUPPORTED; } diff --git a/src/devices/cpu/cop400/cop410ds.h b/src/devices/cpu/cop400/cop410ds.h new file mode 100644 index 00000000000..c1841ec996c --- /dev/null +++ b/src/devices/cpu/cop400/cop410ds.h @@ -0,0 +1,26 @@ +// license:BSD-3-Clause +// copyright-holders:Curt Coder +/*************************************************************************** + + cop410ds.c + + National Semiconductor COP410 Emulator. + +***************************************************************************/ + +#ifndef MAME_CPU_COP410_COP410DS_H +#define MAME_CPU_COP410_COP410DS_H + +#pragma once + +class cop410_disassembler : public util::disasm_interface +{ +public: + cop410_disassembler() = default; + virtual ~cop410_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/cop400/cop420ds.cpp b/src/devices/cpu/cop400/cop420ds.cpp index 39ea87ba9b4..f8f910f174b 100644 --- a/src/devices/cpu/cop400/cop420ds.cpp +++ b/src/devices/cpu/cop400/cop420ds.cpp @@ -9,11 +9,17 @@ ***************************************************************************/ #include "emu.h" +#include "cop420ds.h" -CPU_DISASSEMBLE(cop420) +u32 cop420_disassembler::opcode_alignment() const { - uint8_t opcode = oprom[0]; - uint8_t next_opcode = oprom[1]; + return 1; +} + +offs_t cop420_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + uint8_t opcode = opcodes.r8(pc); + uint8_t next_opcode = opcodes.r8(pc+1); uint16_t address; uint32_t flags = 0; int bytes = 1; @@ -38,7 +44,7 @@ CPU_DISASSEMBLE(cop420) { address = (uint16_t)(0x80 | (opcode & 0x3F)); util::stream_format(stream, "JSRP %03X", address); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; } } } @@ -72,7 +78,7 @@ CPU_DISASSEMBLE(cop420) { address = ((opcode & 0x03) << 8) | next_opcode; util::stream_format(stream, "JSR %03X", address); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; bytes = 2; } else if (opcode >= 0x70 && opcode <= 0x7F) @@ -346,12 +352,12 @@ CPU_DISASSEMBLE(cop420) case 0x48: util::stream_format(stream, "RET"); - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; case 0x49: util::stream_format(stream, "RETSK"); - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; case 0x4A: @@ -396,5 +402,5 @@ CPU_DISASSEMBLE(cop420) } } - return bytes | flags | DASMFLAG_SUPPORTED; + return bytes | flags | SUPPORTED; } diff --git a/src/devices/cpu/cop400/cop420ds.h b/src/devices/cpu/cop400/cop420ds.h new file mode 100644 index 00000000000..a92ba84a54f --- /dev/null +++ b/src/devices/cpu/cop400/cop420ds.h @@ -0,0 +1,26 @@ +// license:BSD-3-Clause +// copyright-holders:Curt Coder +/*************************************************************************** + + cop420ds.c + + National Semiconductor COP420 Emulator. + +***************************************************************************/ + +#ifndef MAME_CPU_COP420_COP420DS_H +#define MAME_CPU_COP420_COP420DS_H + +#pragma once + +class cop420_disassembler : public util::disasm_interface +{ +public: + cop420_disassembler() = default; + virtual ~cop420_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/cop400/cop424ds.cpp b/src/devices/cpu/cop400/cop424ds.cpp index fc8396f4903..e42c5dc3120 100644 --- a/src/devices/cpu/cop400/cop424ds.cpp +++ b/src/devices/cpu/cop400/cop424ds.cpp @@ -9,11 +9,17 @@ ***************************************************************************/ #include "emu.h" +#include "cop424ds.h" -CPU_DISASSEMBLE(cop424) +u32 cop424_disassembler::opcode_alignment() const { - uint8_t opcode = oprom[0]; - uint8_t next_opcode = oprom[1]; + return 1; +} + +offs_t cop424_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + uint8_t opcode = opcodes.r8(pc); + uint8_t next_opcode = opcodes.r8(pc+1); uint16_t address; uint32_t flags = 0; int bytes = 1; @@ -38,7 +44,7 @@ CPU_DISASSEMBLE(cop424) { address = (uint16_t)(0x80 | (opcode & 0x3F)); util::stream_format(stream, "JSRP %03X", address); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; } } } @@ -72,7 +78,7 @@ CPU_DISASSEMBLE(cop424) { address = ((opcode & 0x07) << 8) | next_opcode; util::stream_format(stream, "JSR %03X", address); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; bytes = 2; } else if (opcode >= 0x70 && opcode <= 0x7F) @@ -347,12 +353,12 @@ CPU_DISASSEMBLE(cop424) case 0x48: util::stream_format(stream, "RET"); - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; case 0x49: util::stream_format(stream, "RETSK"); - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; case 0x4A: @@ -397,5 +403,5 @@ CPU_DISASSEMBLE(cop424) } } - return bytes | flags | DASMFLAG_SUPPORTED; + return bytes | flags | SUPPORTED; } diff --git a/src/devices/cpu/cop400/cop424ds.h b/src/devices/cpu/cop400/cop424ds.h new file mode 100644 index 00000000000..e093568a913 --- /dev/null +++ b/src/devices/cpu/cop400/cop424ds.h @@ -0,0 +1,26 @@ +// license:BSD-3-Clause +// copyright-holders:Curt Coder +/*************************************************************************** + + cop424ds.c + + National Semiconductor COP424 Emulator. + +***************************************************************************/ + +#ifndef MAME_CPU_COP424_COP424DS_H +#define MAME_CPU_COP424_COP424DS_H + +#pragma once + +class cop424_disassembler : public util::disasm_interface +{ +public: + cop424_disassembler() = default; + virtual ~cop424_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/cop400/cop444ds.cpp b/src/devices/cpu/cop400/cop444ds.cpp index cae2274546c..23e6cd23cec 100644 --- a/src/devices/cpu/cop400/cop444ds.cpp +++ b/src/devices/cpu/cop400/cop444ds.cpp @@ -9,11 +9,17 @@ ***************************************************************************/ #include "emu.h" +#include "cop444ds.h" -CPU_DISASSEMBLE(cop444) +u32 cop444_disassembler::opcode_alignment() const { - uint8_t opcode = oprom[0]; - uint8_t next_opcode = oprom[1]; + return 1; +} + +offs_t cop444_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + uint8_t opcode = opcodes.r8(pc); + uint8_t next_opcode = opcodes.r8(pc+1); uint16_t address; uint32_t flags = 0; int bytes = 1; @@ -38,7 +44,7 @@ CPU_DISASSEMBLE(cop444) { address = (uint16_t)(0x80 | (opcode & 0x3F)); util::stream_format(stream, "JSRP %03X", address); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; } } } @@ -72,7 +78,7 @@ CPU_DISASSEMBLE(cop444) { address = ((opcode & 0x07) << 8) | next_opcode; util::stream_format(stream, "JSR %03X", address); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; bytes = 2; } else if (opcode >= 0x70 && opcode <= 0x7F) @@ -330,12 +336,12 @@ CPU_DISASSEMBLE(cop444) case 0x48: util::stream_format(stream, "RET"); - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; case 0x49: util::stream_format(stream, "RETSK"); - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; case 0x4A: @@ -380,5 +386,5 @@ CPU_DISASSEMBLE(cop444) } } - return bytes | flags | DASMFLAG_SUPPORTED; + return bytes | flags | SUPPORTED; } diff --git a/src/devices/cpu/cop400/cop444ds.h b/src/devices/cpu/cop400/cop444ds.h new file mode 100644 index 00000000000..c268616f846 --- /dev/null +++ b/src/devices/cpu/cop400/cop444ds.h @@ -0,0 +1,26 @@ +// license:BSD-3-Clause +// copyright-holders:Curt Coder +/*************************************************************************** + + cop444ds.c + + National Semiconductor COP444 Emulator. + +***************************************************************************/ + +#ifndef MAME_CPU_COP444_COP444DS_H +#define MAME_CPU_COP444_COP444DS_H + +#pragma once + +class cop444_disassembler : public util::disasm_interface +{ +public: + cop444_disassembler() = default; + virtual ~cop444_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/cosmac/cosdasm.cpp b/src/devices/cpu/cosmac/cosdasm.cpp index 72f039037b5..c818fd2c9a9 100644 --- a/src/devices/cpu/cosmac/cosdasm.cpp +++ b/src/devices/cpu/cosmac/cosdasm.cpp @@ -10,56 +10,62 @@ ***************************************************************************/ #include "emu.h" - -enum -{ - TYPE_1801, - TYPE_1802 -}; +#include "cosdasm.h" #define CDP1801_OPCODE(...) \ util::stream_format(stream, __VA_ARGS__) #define CDP1802_OPCODE(...) \ - if (variant < TYPE_1802) stream << "illegal"; else util::stream_format(stream, __VA_ARGS__) + if (m_variant < TYPE_1802) stream << "illegal"; else util::stream_format(stream, __VA_ARGS__) -static offs_t implied(const uint8_t opcode) +offs_t cosmac_disassembler::implied(const uint8_t opcode) { return opcode & 0x0f; } -static offs_t immediate(const uint8_t **opram) +offs_t cosmac_disassembler::immediate(offs_t &pc, const data_buffer ¶ms) { - return *(*opram)++; + return params.r8(pc++); } -static offs_t short_branch(offs_t pc, const uint8_t **opram) +offs_t cosmac_disassembler::short_branch(offs_t base_pc, offs_t &pc, const data_buffer ¶ms) { - return (pc & 0xff00) | immediate(opram); + return (base_pc & 0xff00) | immediate(pc, params); } -static offs_t long_branch(const uint8_t **opram) +offs_t cosmac_disassembler::long_branch(offs_t &pc, const data_buffer ¶ms) { - return (immediate(opram) << 8) | immediate(opram); + u16 res = params.r16(pc); + pc += 2; + return res; } -static offs_t short_skip(offs_t pc) +offs_t cosmac_disassembler::short_skip(offs_t pc) { return pc + 2; } -static offs_t long_skip(offs_t pc) +offs_t cosmac_disassembler::long_skip(offs_t pc) { return pc + 3; } -static uint32_t disassemble(device_t *device, std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t variant) + +u32 cosmac_disassembler::opcode_alignment() const +{ + return 1; +} + +cosmac_disassembler::cosmac_disassembler(int variant) : m_variant(variant) +{ +} + +offs_t cosmac_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - const uint8_t *startram = opram; + offs_t base_pc = pc; uint32_t flags = 0; - opram++; - uint8_t opcode = *oprom++; + uint8_t opcode = opcodes.r8(pc++); switch (opcode) { @@ -73,20 +79,20 @@ static uint32_t disassemble(device_t *device, std::ostream &stream, offs_t pc, c case 0x20: case 0x21: case 0x22: case 0x23: case 0x24: case 0x25: case 0x26: case 0x27: case 0x28: case 0x29: case 0x2a: case 0x2b: case 0x2c: case 0x2d: case 0x2e: case 0x2f: CDP1801_OPCODE("DEC R%01X", implied(opcode)); break; - case 0x30: CDP1801_OPCODE("BR %04X", short_branch(pc, &opram)); break; - case 0x32: CDP1801_OPCODE("BZ %04X", short_branch(pc, &opram)); break; - case 0x33: CDP1801_OPCODE("BDF %04X", short_branch(pc, &opram)); break; - case 0x34: CDP1801_OPCODE("B1 %04X", short_branch(pc, &opram)); break; - case 0x35: CDP1801_OPCODE("B2 %04X", short_branch(pc, &opram)); break; - case 0x36: CDP1801_OPCODE("B3 %04X", short_branch(pc, &opram)); break; - case 0x37: CDP1801_OPCODE("B4 %04X", short_branch(pc, &opram)); break; + case 0x30: CDP1801_OPCODE("BR %04X", short_branch(base_pc, pc, params)); break; + case 0x32: CDP1801_OPCODE("BZ %04X", short_branch(base_pc, pc, params)); break; + case 0x33: CDP1801_OPCODE("BDF %04X", short_branch(base_pc, pc, params)); break; + case 0x34: CDP1801_OPCODE("B1 %04X", short_branch(base_pc, pc, params)); break; + case 0x35: CDP1801_OPCODE("B2 %04X", short_branch(base_pc, pc, params)); break; + case 0x36: CDP1801_OPCODE("B3 %04X", short_branch(base_pc, pc, params)); break; + case 0x37: CDP1801_OPCODE("B4 %04X", short_branch(base_pc, pc, params)); break; case 0x38: CDP1801_OPCODE("SKP %04X", short_skip(pc)); break; - case 0x3a: CDP1801_OPCODE("BNZ %04X", short_branch(pc, &opram)); break; - case 0x3b: CDP1801_OPCODE("BNF %04X", short_branch(pc, &opram)); break; - case 0x3c: CDP1801_OPCODE("BN1 %04X", short_branch(pc, &opram)); break; - case 0x3d: CDP1801_OPCODE("BN2 %04X", short_branch(pc, &opram)); break; - case 0x3e: CDP1801_OPCODE("BN3 %04X", short_branch(pc, &opram)); break; - case 0x3f: CDP1801_OPCODE("BN4 %04X", short_branch(pc, &opram)); break; + case 0x3a: CDP1801_OPCODE("BNZ %04X", short_branch(base_pc, pc, params)); break; + case 0x3b: CDP1801_OPCODE("BNF %04X", short_branch(base_pc, pc, params)); break; + case 0x3c: CDP1801_OPCODE("BN1 %04X", short_branch(base_pc, pc, params)); break; + case 0x3d: CDP1801_OPCODE("BN2 %04X", short_branch(base_pc, pc, params)); break; + case 0x3e: CDP1801_OPCODE("BN3 %04X", short_branch(base_pc, pc, params)); break; + case 0x3f: CDP1801_OPCODE("BN4 %04X", short_branch(base_pc, pc, params)); break; case 0x40: case 0x41: case 0x42: case 0x43: case 0x44: case 0x45: case 0x46: case 0x47: case 0x48: case 0x49: case 0x4a: case 0x4b: case 0x4c: case 0x4d: case 0x4e: case 0x4f: CDP1801_OPCODE("LDA R%01X", implied(opcode)); break; @@ -107,8 +113,8 @@ static uint32_t disassemble(device_t *device, std::ostream &stream, offs_t pc, c case 0x6d: CDP1801_OPCODE("INP 5"); break; case 0x6e: CDP1801_OPCODE("INP 6"); break; case 0x6f: CDP1801_OPCODE("INP 7"); break; - case 0x70: CDP1801_OPCODE("RET"); flags = DASMFLAG_STEP_OUT; break; - case 0x71: CDP1801_OPCODE("DIS"); flags = DASMFLAG_STEP_OUT; break; + case 0x70: CDP1801_OPCODE("RET"); flags = STEP_OUT; break; + case 0x71: CDP1801_OPCODE("DIS"); flags = STEP_OUT; break; case 0x78: CDP1801_OPCODE("SAV"); break; case 0x80: case 0x81: case 0x82: case 0x83: case 0x84: case 0x85: case 0x86: case 0x87: case 0x88: case 0x89: case 0x8a: case 0x8b: case 0x8c: case 0x8d: case 0x8e: case 0x8f: @@ -124,7 +130,7 @@ static uint32_t disassemble(device_t *device, std::ostream &stream, offs_t pc, c CDP1801_OPCODE("PHI R%01X", implied(opcode)); break; case 0xd0: case 0xd1: case 0xd2: case 0xd3: case 0xd4: case 0xd5: case 0xd6: case 0xd7: case 0xd8: case 0xd9: case 0xda: case 0xdb: case 0xdc: case 0xdd: case 0xde: case 0xdf: - CDP1801_OPCODE("SEP R%01X", implied(opcode)); flags = DASMFLAG_STEP_OVER; break; + CDP1801_OPCODE("SEP R%01X", implied(opcode)); flags = STEP_OVER; break; case 0xe0: case 0xe1: case 0xe2: case 0xe3: case 0xe4: case 0xe5: case 0xe6: case 0xe7: case 0xe8: case 0xe9: case 0xea: case 0xeb: case 0xec: case 0xed: case 0xee: case 0xef: CDP1801_OPCODE("SEX R%01X", implied(opcode)); break; @@ -136,16 +142,16 @@ static uint32_t disassemble(device_t *device, std::ostream &stream, offs_t pc, c case 0xf5: CDP1801_OPCODE("SD"); break; case 0xf6: CDP1801_OPCODE("SHR"); break; case 0xf7: CDP1801_OPCODE("SM"); break; - case 0xf8: CDP1801_OPCODE("LDI #%02X", immediate(&opram)); break; - case 0xf9: CDP1801_OPCODE("ORI #%02X", immediate(&opram)); break; - case 0xfa: CDP1801_OPCODE("ANI #%02X", immediate(&opram)); break; - case 0xfb: CDP1801_OPCODE("XRI #%02X", immediate(&opram)); break; - case 0xfc: CDP1801_OPCODE("ADI #%02X", immediate(&opram)); break; - case 0xfd: CDP1801_OPCODE("SDI #%02X", immediate(&opram)); break; - case 0xff: CDP1801_OPCODE("SMI #%02X", immediate(&opram)); break; + case 0xf8: CDP1801_OPCODE("LDI #%02X", immediate(pc, params)); break; + case 0xf9: CDP1801_OPCODE("ORI #%02X", immediate(pc, params)); break; + case 0xfa: CDP1801_OPCODE("ANI #%02X", immediate(pc, params)); break; + case 0xfb: CDP1801_OPCODE("XRI #%02X", immediate(pc, params)); break; + case 0xfc: CDP1801_OPCODE("ADI #%02X", immediate(pc, params)); break; + case 0xfd: CDP1801_OPCODE("SDI #%02X", immediate(pc, params)); break; + case 0xff: CDP1801_OPCODE("SMI #%02X", immediate(pc, params)); break; // CDP1802 - case 0x31: CDP1802_OPCODE("BQ %04X", short_branch(pc, &opram)); break; - case 0x39: CDP1802_OPCODE("BNQ %04X", short_branch(pc, &opram)); break; + case 0x31: CDP1802_OPCODE("BQ %04X", short_branch(base_pc, pc, params)); break; + case 0x39: CDP1802_OPCODE("BNQ %04X", short_branch(base_pc, pc, params)); break; case 0x60: CDP1802_OPCODE("IRX"); break; case 0x72: CDP1802_OPCODE("LDXA"); break; case 0x73: CDP1802_OPCODE("STXD"); break; @@ -156,14 +162,14 @@ static uint32_t disassemble(device_t *device, std::ostream &stream, offs_t pc, c case 0x79: CDP1802_OPCODE("MARK"); break; case 0x7a: CDP1802_OPCODE("REQ"); break; case 0x7b: CDP1802_OPCODE("SEQ"); break; - case 0x7c: CDP1802_OPCODE("ADCI #%02X", immediate(&opram)); break; - case 0x7d: CDP1802_OPCODE("SDBI #%02X", immediate(&opram)); break; + case 0x7c: CDP1802_OPCODE("ADCI #%02X", immediate(pc, params)); break; + case 0x7d: CDP1802_OPCODE("SDBI #%02X", immediate(pc, params)); break; case 0x7e: CDP1802_OPCODE("SHLC"); break; - case 0x7f: CDP1802_OPCODE("SMBI #%02X", immediate(&opram)); break; - case 0xc0: CDP1802_OPCODE("LBR %04X", long_branch(&opram)); break; - case 0xc1: CDP1802_OPCODE("LBQ %04X", long_branch(&opram)); break; - case 0xc2: CDP1802_OPCODE("LBZ %04X", long_branch(&opram)); break; - case 0xc3: CDP1802_OPCODE("LBDF %04X", long_branch(&opram)); break; + case 0x7f: CDP1802_OPCODE("SMBI #%02X", immediate(pc, params)); break; + case 0xc0: CDP1802_OPCODE("LBR %04X", long_branch(pc, params)); break; + case 0xc1: CDP1802_OPCODE("LBQ %04X", long_branch(pc, params)); break; + case 0xc2: CDP1802_OPCODE("LBZ %04X", long_branch(pc, params)); break; + case 0xc3: CDP1802_OPCODE("LBDF %04X", long_branch(pc, params)); break; case 0xc4: CDP1802_OPCODE("NOP"); break; case 0xc5: CDP1802_OPCODE("LSNQ %04X", long_skip(pc)); break; case 0xc6: CDP1802_OPCODE("LSNZ %04X", long_skip(pc)); break; @@ -181,17 +187,5 @@ static uint32_t disassemble(device_t *device, std::ostream &stream, offs_t pc, c default: CDP1801_OPCODE("illegal"); break; } - return (opram - startram) | flags | DASMFLAG_SUPPORTED; -} - - -CPU_DISASSEMBLE( cdp1801 ) -{ - return disassemble(device, stream, pc, oprom, opram, TYPE_1801); -} - - -CPU_DISASSEMBLE( cdp1802 ) -{ - return disassemble(device, stream, pc, oprom, opram, TYPE_1802); + return (pc - base_pc) | flags | SUPPORTED; } diff --git a/src/devices/cpu/cosmac/cosdasm.h b/src/devices/cpu/cosmac/cosdasm.h new file mode 100644 index 00000000000..38011b792c6 --- /dev/null +++ b/src/devices/cpu/cosmac/cosdasm.h @@ -0,0 +1,43 @@ +// license:BSD-3-Clause +// copyright-holders:Curt Coder +/*************************************************************************** + + cosdasm.c + + Simple RCA COSMAC disassembler. + Written by Curt Coder + +***************************************************************************/ + +#ifndef MAME_CPU_COSMAC_COSDASM_H +#define MAME_CPU_COSMAC_COSDASM_H + +#pragma once + +class cosmac_disassembler : public util::disasm_interface +{ +public: + enum + { + TYPE_1801, + TYPE_1802 + }; + + cosmac_disassembler(int variant); + virtual ~cosmac_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + int m_variant; + + offs_t implied(const uint8_t opcode); + offs_t immediate(offs_t &pc, const data_buffer ¶ms); + offs_t short_branch(offs_t base_pc, offs_t &pc, const data_buffer ¶ms); + offs_t long_branch(offs_t &pc, const data_buffer ¶ms); + offs_t short_skip(offs_t pc); + offs_t long_skip(offs_t pc); +}; + +#endif diff --git a/src/devices/cpu/cosmac/cosmac.cpp b/src/devices/cpu/cosmac/cosmac.cpp index 171a4a4d734..f489eca224b 100644 --- a/src/devices/cpu/cosmac/cosmac.cpp +++ b/src/devices/cpu/cosmac/cosmac.cpp @@ -9,6 +9,7 @@ #include "emu.h" #include "debugger.h" #include "cosmac.h" +#include "cosdasm.h" #include "coreutil.h" // permit our enums to be saved @@ -479,45 +480,21 @@ void cosmac_device::state_string_export(const device_state_entry &entry, std::st //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t cosmac_device::disasm_min_opcode_bytes() const -{ - return 1; -} - - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t cosmac_device::disasm_max_opcode_bytes() const -{ - return 3; -} - - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t cdp1801_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *cdp1801_device::create_disassembler() { - extern CPU_DISASSEMBLE( cdp1801 ); - return CPU_DISASSEMBLE_NAME( cdp1801 )(this, stream, pc, oprom, opram, options); + return new cosmac_disassembler(cosmac_disassembler::TYPE_1801); } -offs_t cdp1802_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) + +util::disasm_interface *cdp1802_device::create_disassembler() { - extern CPU_DISASSEMBLE( cdp1802 ); - return CPU_DISASSEMBLE_NAME( cdp1802 )(this, stream, pc, oprom, opram, options); + return new cosmac_disassembler(cosmac_disassembler::TYPE_1802); } - //************************************************************************** // INLINE HELPERS //************************************************************************** diff --git a/src/devices/cpu/cosmac/cosmac.h b/src/devices/cpu/cosmac/cosmac.h index 36ad0922f48..17cf3b4e798 100644 --- a/src/devices/cpu/cosmac/cosmac.h +++ b/src/devices/cpu/cosmac/cosmac.h @@ -240,10 +240,6 @@ protected: virtual void state_export(const device_state_entry &entry) override; virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; - // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - // helpers inline uint8_t read_opcode(offs_t pc); inline uint8_t read_byte(offs_t address); @@ -459,7 +455,7 @@ public: protected: // device_disasm_interface overrides - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual cosmac_device::ophandler get_ophandler(uint8_t opcode) override; @@ -477,7 +473,7 @@ public: protected: // device_disasm_interface overrides - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual cosmac_device::ophandler get_ophandler(uint8_t opcode) override; diff --git a/src/devices/cpu/cp1610/1610dasm.cpp b/src/devices/cpu/cp1610/1610dasm.cpp index 0e9ed461dd3..112bbda6523 100644 --- a/src/devices/cpu/cp1610/1610dasm.cpp +++ b/src/devices/cpu/cp1610/1610dasm.cpp @@ -1,12 +1,16 @@ // license:BSD-3-Clause // copyright-holders:Frank Palazzolo #include "emu.h" -#include "debugger.h" -#include "cp1610.h" +#include "1610dasm.h" -CPU_DISASSEMBLE(cp1610) +u32 cp1610_disassembler::opcode_alignment() const { - uint16_t oprom16[4]={ static_cast((oprom[0] << 8) | oprom[1]), static_cast((oprom[2] << 8) | oprom[3]), static_cast((oprom[4] << 8) | oprom[5]), static_cast((oprom[6] << 8) | oprom[7]) }; + return 1; +} + +offs_t cp1610_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + uint16_t oprom16[4]={ opcodes.r16(pc), opcodes.r16(pc+1), opcodes.r16(pc+2), opcodes.r16(pc+3) }; uint16_t op = oprom16[0]; uint16_t subop; uint16_t ea, ea1, ea2; unsigned size = 1; diff --git a/src/devices/cpu/cp1610/1610dasm.h b/src/devices/cpu/cp1610/1610dasm.h new file mode 100644 index 00000000000..59cc61b36f9 --- /dev/null +++ b/src/devices/cpu/cp1610/1610dasm.h @@ -0,0 +1,19 @@ +// license:BSD-3-Clause +// copyright-holders:Frank Palazzolo + +#ifndef MAME_CPU_CP1610_CP1610DASM_H +#define MAME_CPU_CP1610_CP1610DASM_H + +#pragma once + +class cp1610_disassembler : public util::disasm_interface +{ +public: + cp1610_disassembler() = default; + virtual ~cp1610_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/cp1610/cp1610.cpp b/src/devices/cpu/cp1610/cp1610.cpp index 5a113b4e954..085ee1e2ab5 100644 --- a/src/devices/cpu/cp1610/cp1610.cpp +++ b/src/devices/cpu/cp1610/cp1610.cpp @@ -16,7 +16,7 @@ #include "emu.h" #include "cp1610.h" #include "debugger.h" - +#include "1610dasm.h" DEFINE_DEVICE_TYPE(CP1610, cp1610_cpu_device, "cp1610", "GI CP1610") @@ -3422,9 +3422,7 @@ void cp1610_cpu_device::state_string_export(const device_state_entry &entry, std } } - -offs_t cp1610_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *cp1610_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( cp1610 ); - return CPU_DISASSEMBLE_NAME(cp1610)(this, stream, pc, oprom, opram, options); + return new cp1610_disassembler; } diff --git a/src/devices/cpu/cp1610/cp1610.h b/src/devices/cpu/cp1610/cp1610.h index c3a844189e3..54daa10b4bc 100644 --- a/src/devices/cpu/cp1610/cp1610.h +++ b/src/devices/cpu/cp1610/cp1610.h @@ -60,9 +60,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 8; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; @@ -211,7 +209,4 @@ private: DECLARE_DEVICE_TYPE(CP1610, cp1610_cpu_device) - -CPU_DISASSEMBLE( cp1610 ); - #endif // MAME_CPU_CP1610_CP1610_H diff --git a/src/devices/cpu/cubeqcpu/cubedasm.cpp b/src/devices/cpu/cubeqcpu/cubedasm.cpp index 20fd5a266d0..2bfb3ac0431 100644 --- a/src/devices/cpu/cubeqcpu/cubedasm.cpp +++ b/src/devices/cpu/cubeqcpu/cubedasm.cpp @@ -9,7 +9,7 @@ ***************************************************************************/ #include "emu.h" -#include "cubeqcpu.h" +#include "cubedasm.h" /*************************************************************************** @@ -17,7 +17,7 @@ ***************************************************************************/ /* Am2901 Instruction Fields */ -static const char *const ins[] = +const char *const cubeq_disassembler::ins[] = { "ADD ", "SUBR ", @@ -29,7 +29,7 @@ static const char *const ins[] = "EXNOR", }; -static const char *const src[] = +const char *const cubeq_disassembler::src[] = { "A,Q", "A,B", @@ -41,7 +41,7 @@ static const char *const src[] = "D,0", }; -static const char *const dst[] = +const char *const cubeq_disassembler::dst[] = { "QREG ", "NOP ", @@ -53,12 +53,16 @@ static const char *const dst[] = "RAMU ", }; +u32 cubeq_disassembler::opcode_alignment() const +{ + return 1; +} /*************************************************************************** SOUND DISASSEMBLY HOOK ***************************************************************************/ -CPU_DISASSEMBLE(cquestsnd) +offs_t cquestsnd_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { static const char *const jmps[] = { @@ -81,7 +85,7 @@ CPU_DISASSEMBLE(cquestsnd) " ", }; - uint64_t inst = big_endianize_int64(*(uint64_t *)oprom); + uint64_t inst = opcodes.r64(pc); uint32_t inslow = inst & 0xffffffff; uint32_t inshig = inst >> 32; @@ -121,7 +125,7 @@ CPU_DISASSEMBLE(cquestsnd) _ipwrt ? ' ' : 'W', inca ? 'I' : ' '); - return 1 | DASMFLAG_SUPPORTED; + return 1 | SUPPORTED; } @@ -129,7 +133,7 @@ CPU_DISASSEMBLE(cquestsnd) ROTATE DISASSEMBLY HOOK ***************************************************************************/ -CPU_DISASSEMBLE(cquestrot) +offs_t cquestrot_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { static const char *const jmps[] = { @@ -185,7 +189,7 @@ CPU_DISASSEMBLE(cquestrot) "??? " }; - uint64_t inst = big_endianize_int64(*(uint64_t *)oprom); + uint64_t inst = opcodes.r64(pc); uint32_t inslow = inst & 0xffffffff; uint32_t inshig = inst >> 32; @@ -217,7 +221,7 @@ CPU_DISASSEMBLE(cquestrot) spfs[spf], t); - return 1 | DASMFLAG_SUPPORTED; + return 1 | SUPPORTED; } @@ -225,7 +229,7 @@ CPU_DISASSEMBLE(cquestrot) LINE DRAWER DISASSEMBLY HOOK ***************************************************************************/ -CPU_DISASSEMBLE(cquestlin) +offs_t cquestlin_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { static const char *const jmps[] = { @@ -272,7 +276,7 @@ CPU_DISASSEMBLE(cquestlin) "BRES ", }; - uint64_t inst = big_endianize_int64(*(uint64_t *)oprom); + uint64_t inst = opcodes.r64(pc); uint32_t inslow = inst & 0xffffffff; uint32_t inshig = inst >> 32; @@ -303,5 +307,5 @@ CPU_DISASSEMBLE(cquestlin) _pbcs ? " " : "PB", spfs[spf]); - return 1 | DASMFLAG_SUPPORTED; + return 1 | SUPPORTED; } diff --git a/src/devices/cpu/cubeqcpu/cubedasm.h b/src/devices/cpu/cubeqcpu/cubedasm.h new file mode 100644 index 00000000000..e43018a1998 --- /dev/null +++ b/src/devices/cpu/cubeqcpu/cubedasm.h @@ -0,0 +1,54 @@ +// license:BSD-3-Clause +// copyright-holders:Philip Bennett +/*************************************************************************** + + cubedasm.c + + Implementation of the Cube Quest AM2901-based CPUs + +***************************************************************************/ + +#ifndef MAME_CPU_CUBEQCPU_CUBEDASM_H +#define MAME_CPU_CUBEQCPU_CUBEDASM_H + +#pragma once + +class cubeq_disassembler : public util::disasm_interface +{ +public: + cubeq_disassembler() = default; + virtual ~cubeq_disassembler() = default; + + virtual u32 opcode_alignment() const override; + +protected: + static const char *const ins[]; + static const char *const src[]; + static const char *const dst[]; +}; + +class cquestsnd_disassembler : public cubeq_disassembler +{ +public: + cquestsnd_disassembler() = default; + virtual ~cquestsnd_disassembler() = default; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +class cquestrot_disassembler : public cubeq_disassembler +{ +public: + cquestrot_disassembler() = default; + virtual ~cquestrot_disassembler() = default; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +class cquestlin_disassembler : public cubeq_disassembler +{ +public: + cquestlin_disassembler() = default; + virtual ~cquestlin_disassembler() = default; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/cubeqcpu/cubeqcpu.cpp b/src/devices/cpu/cubeqcpu/cubeqcpu.cpp index 9c3652fd40e..9f614bcf017 100644 --- a/src/devices/cpu/cubeqcpu/cubeqcpu.cpp +++ b/src/devices/cpu/cubeqcpu/cubeqcpu.cpp @@ -16,6 +16,7 @@ #include "emu.h" #include "debugger.h" #include "cubeqcpu.h" +#include "cubedasm.h" /*************************************************************************** @@ -91,10 +92,9 @@ device_memory_interface::space_config_vector cquestsnd_cpu_device::memory_space_ } -offs_t cquestsnd_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *cquestsnd_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( cquestsnd ); - return CPU_DISASSEMBLE_NAME(cquestsnd)(this, stream, pc, oprom, opram, options); + return new cquestsnd_disassembler; } @@ -112,10 +112,9 @@ READ16_MEMBER( cquestrot_cpu_device::linedata_r ) } -offs_t cquestrot_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *cquestrot_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( cquestrot ); - return CPU_DISASSEMBLE_NAME(cquestrot)(this, stream, pc, oprom, opram, options); + return new cquestsnd_disassembler; } @@ -135,10 +134,9 @@ device_memory_interface::space_config_vector cquestlin_cpu_device::memory_space_ }; } -offs_t cquestlin_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *cquestlin_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( cquestlin ); - return CPU_DISASSEMBLE_NAME(cquestlin)(this, stream, pc, oprom, opram, options); + return new cquestlin_disassembler; } diff --git a/src/devices/cpu/cubeqcpu/cubeqcpu.h b/src/devices/cpu/cubeqcpu/cubeqcpu.h index de80a2830d5..321d10efb11 100644 --- a/src/devices/cpu/cubeqcpu/cubeqcpu.h +++ b/src/devices/cpu/cubeqcpu/cubeqcpu.h @@ -87,9 +87,7 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 8; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 8; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; @@ -190,9 +188,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 8; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 8; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; @@ -304,9 +300,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 8; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 8; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/dsp16/dsp16.cpp b/src/devices/cpu/dsp16/dsp16.cpp index 4426502cdf7..d1bf8847906 100644 --- a/src/devices/cpu/dsp16/dsp16.cpp +++ b/src/devices/cpu/dsp16/dsp16.cpp @@ -11,6 +11,7 @@ #include "emu.h" #include "debugger.h" #include "dsp16.h" +#include "dsp16dis.h" // // TODO: @@ -321,42 +322,17 @@ void dsp16_device::state_string_export(const device_state_entry &entry, std::str } } - -//------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t dsp16_device::disasm_min_opcode_bytes() const -{ - return 2; -} - - //------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t dsp16_device::disasm_max_opcode_bytes() const -{ - return 4; -} - - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t dsp16_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *dsp16_device::create_disassembler() { - extern CPU_DISASSEMBLE( dsp16a ); - return CPU_DISASSEMBLE_NAME(dsp16a)(this, stream, pc, oprom, opram, options); + return new dsp16a_disassembler; } - /*************************************************************************** MEMORY ACCESSORS ***************************************************************************/ diff --git a/src/devices/cpu/dsp16/dsp16.h b/src/devices/cpu/dsp16/dsp16.h index fd41dd03ef1..9c3ec245f11 100644 --- a/src/devices/cpu/dsp16/dsp16.h +++ b/src/devices/cpu/dsp16/dsp16.h @@ -83,9 +83,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // address spaces const address_space_config m_program_config; diff --git a/src/devices/cpu/dsp16/dsp16dis.cpp b/src/devices/cpu/dsp16/dsp16dis.cpp index eb371719cb6..40e122741e3 100644 --- a/src/devices/cpu/dsp16/dsp16dis.cpp +++ b/src/devices/cpu/dsp16/dsp16dis.cpp @@ -1,9 +1,9 @@ // license:BSD-3-Clause // copyright-holders:Andrew Gardner #include "emu.h" -#include "dsp16.h" +#include "dsp16dis.h" -std::string disasmF1Field(const uint8_t& F1, const uint8_t& D, const uint8_t& S) +std::string dsp16a_disassembler::disasmF1Field(const uint8_t& F1, const uint8_t& D, const uint8_t& S) { switch (F1) { @@ -28,7 +28,7 @@ std::string disasmF1Field(const uint8_t& F1, const uint8_t& D, const uint8_t& S) } } -std::string disasmYField(const uint8_t& Y) +std::string dsp16a_disassembler::disasmYField(const uint8_t& Y) { switch (Y) { @@ -58,7 +58,7 @@ std::string disasmYField(const uint8_t& Y) //return ""; } -std::string disasmZField(const uint8_t& Z) +std::string dsp16a_disassembler::disasmZField(const uint8_t& Z) { switch (Z) { @@ -88,7 +88,7 @@ std::string disasmZField(const uint8_t& Z) //return ""; } -std::string disasmF2Field(const uint8_t& F2, const uint8_t& D, const uint8_t& S) +std::string dsp16a_disassembler::disasmF2Field(const uint8_t& F2, const uint8_t& D, const uint8_t& S) { std::string ret = ""; switch (F2) @@ -116,7 +116,7 @@ std::string disasmF2Field(const uint8_t& F2, const uint8_t& D, const uint8_t& S) return ret; } -std::string disasmCONField(const uint8_t& CON) +std::string dsp16a_disassembler::disasmCONField(const uint8_t& CON) { switch (CON) { @@ -145,7 +145,7 @@ std::string disasmCONField(const uint8_t& CON) //return ""; } -std::string disasmBField(const uint8_t& B) +std::string dsp16a_disassembler::disasmBField(const uint8_t& B) { switch (B) { @@ -164,7 +164,7 @@ std::string disasmBField(const uint8_t& B) //return ""; } -std::string disasmRImmediateField(const uint8_t& R) +std::string dsp16a_disassembler::disasmRImmediateField(const uint8_t& R) { switch (R) { @@ -183,7 +183,7 @@ std::string disasmRImmediateField(const uint8_t& R) //return ""; } -std::string disasmRField(const uint8_t& R) +std::string dsp16a_disassembler::disasmRField(const uint8_t& R) { switch (R) { @@ -222,7 +222,7 @@ std::string disasmRField(const uint8_t& R) //return ""; } -std::string disasmIField(const uint8_t& I) +std::string dsp16a_disassembler::disasmIField(const uint8_t& I) { switch (I) { @@ -237,7 +237,7 @@ std::string disasmIField(const uint8_t& I) //return ""; } -bool disasmSIField(const uint8_t& SI) +bool dsp16a_disassembler::disasmSIField(const uint8_t& SI) { switch (SI) { @@ -248,12 +248,17 @@ bool disasmSIField(const uint8_t& SI) } -CPU_DISASSEMBLE(dsp16a) +u32 dsp16a_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t dsp16a_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { uint8_t opSize = 1; uint32_t dasmflags = 0; - uint16_t op = oprom[0] | (oprom[1] << 8); - uint16_t op2 = oprom[2] | (oprom[3] << 8); + uint16_t op = opcodes.r16(pc); + uint16_t op2 = opcodes.r16(pc+1); // TODO: Test for previous "if CON" instruction and tab the next instruction in? @@ -582,5 +587,5 @@ CPU_DISASSEMBLE(dsp16a) } } - return opSize | dasmflags | DASMFLAG_SUPPORTED; + return opSize | dasmflags | SUPPORTED; } diff --git a/src/devices/cpu/dsp16/dsp16dis.h b/src/devices/cpu/dsp16/dsp16dis.h new file mode 100644 index 00000000000..9d5361e75ae --- /dev/null +++ b/src/devices/cpu/dsp16/dsp16dis.h @@ -0,0 +1,32 @@ +// license:BSD-3-Clause +// copyright-holders:Andrew Gardner + +#ifndef MAME_CPU_DSP16_DSP16DIS_H +#define MAME_CPU_DSP16_DSP16DIS_H + +#pragma once + +class dsp16a_disassembler : public util::disasm_interface +{ +public: + dsp16a_disassembler() = default; + virtual ~dsp16a_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + std::string disasmF1Field(const uint8_t& F1, const uint8_t& D, const uint8_t& S); + std::string disasmYField(const uint8_t& Y); + std::string disasmZField(const uint8_t& Z); + std::string disasmF2Field(const uint8_t& F2, const uint8_t& D, const uint8_t& S); + std::string disasmCONField(const uint8_t& CON); + std::string disasmBField(const uint8_t& B); + std::string disasmRImmediateField(const uint8_t& R); + std::string disasmRField(const uint8_t& R); + std::string disasmIField(const uint8_t& I); + bool disasmSIField(const uint8_t& SI); + +}; + +#endif diff --git a/src/devices/cpu/dsp32/dsp32.cpp b/src/devices/cpu/dsp32/dsp32.cpp index e91a0fddf29..4169d110384 100644 --- a/src/devices/cpu/dsp32/dsp32.cpp +++ b/src/devices/cpu/dsp32/dsp32.cpp @@ -30,6 +30,7 @@ #include "emu.h" #include "dsp32.h" +#include "dsp32dis.h" #include "debugger.h" @@ -397,41 +398,17 @@ void dsp32c_device::state_string_export(const device_state_entry &entry, std::st //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t dsp32c_device::disasm_min_opcode_bytes() const -{ - return 4; -} - - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t dsp32c_device::disasm_max_opcode_bytes() const -{ - return 4; -} - - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t dsp32c_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *dsp32c_device::create_disassembler() { - extern CPU_DISASSEMBLE( dsp32c ); - return CPU_DISASSEMBLE_NAME(dsp32c)(this, stream, pc, oprom, opram, options); + return new dsp32c_disassembler; } - //************************************************************************** // MEMORY ACCESSORS //************************************************************************** diff --git a/src/devices/cpu/dsp32/dsp32.h b/src/devices/cpu/dsp32/dsp32.h index b11f5ad1d89..6e6c121d80e 100644 --- a/src/devices/cpu/dsp32/dsp32.h +++ b/src/devices/cpu/dsp32/dsp32.h @@ -126,9 +126,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // memory accessors uint32_t ROPCODE(offs_t pc); diff --git a/src/devices/cpu/dsp32/dsp32dis.cpp b/src/devices/cpu/dsp32/dsp32dis.cpp index 88399882df9..8748b2b55ab 100644 --- a/src/devices/cpu/dsp32/dsp32dis.cpp +++ b/src/devices/cpu/dsp32/dsp32dis.cpp @@ -9,7 +9,7 @@ ***************************************************************************/ #include "emu.h" -#include "dsp32.h" +#include "dsp32dis.h" /*************************************************************************** @@ -23,17 +23,17 @@ CODE CODE ***************************************************************************/ -static const char *const sizesuffix[] = { "", "e" }; -static const char *const unarysign[] = { "", "-" }; -static const char *const sign[] = { "+", "-" }; -static const char *const aMvals[] = { "a0", "a1", "a2", "a3", "0.0", "1.0", "Format 4", "Reserved" }; -static const char *const memsuffix[] = { "h", "l", "", "e" }; -static const char *const functable[] = +const char *const dsp32c_disassembler::sizesuffix[] = { "", "e" }; +const char *const dsp32c_disassembler::unarysign[] = { "", "-" }; +const char *const dsp32c_disassembler::sign[] = { "+", "-" }; +const char *const dsp32c_disassembler::aMvals[] = { "a0", "a1", "a2", "a3", "0.0", "1.0", "Format 4", "Reserved" }; +const char *const dsp32c_disassembler::memsuffix[] = { "h", "l", "", "e" }; +const char *const dsp32c_disassembler::functable[] = { "ic", "oc", "float", "int", "round", "ifalt", "ifaeq", "ifagt", "reserved8", "reserved9", "float24", "int24", "ieee", "dsp", "seed", "reservedf" }; -static const char *const condtable[] = +const char *const dsp32c_disassembler::condtable[] = { "false", "true", "pl", "mi", @@ -68,14 +68,14 @@ static const char *const condtable[] = "!?1e", "?1e", "!?1f", "?1f" }; -static const char *const regname[] = +const char *const dsp32c_disassembler::regname[] = { "0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", "r11", "r12", "r13", "r14", "pc", "0", "r15", "r16", "r17", "r18", "r19", "-1", "1", "r20", "r21", "dauc", "ioc", "res1c", "r22", "pcsh", "res1f" }; -static const char *const regnamee[] = +const char *const dsp32c_disassembler::regnamee[] = { "0", "r1e", "r2e", "r3e", "r4e", "r5e", "r6e", "r7e", "r8e", "r9e", "r10e", "r11e", "r12e", "r13e", "r14e", "pce", @@ -83,48 +83,39 @@ static const char *const regnamee[] = "r20e", "r21e", "dauce", "ioce", "res1ce", "r22e", "pcshe", "res1fe" }; -static inline char *signed_16bit_unary(int16_t val) +std::string dsp32c_disassembler::signed_16bit_unary(int16_t val) { - static char temp[10]; if (val < 0) - sprintf(temp, "-$%x", -val); + return util::string_format("-$%x", -val); else - sprintf(temp, "$%x", val); - return temp; + return util::string_format("$%x", val); } -static inline char *signed_16bit_sep(int16_t val) +std::string dsp32c_disassembler::signed_16bit_sep(int16_t val) { - static char temp[10]; if (val < 0) - sprintf(temp, " - $%x", -val); + return util::string_format(" - $%x", -val); else - sprintf(temp, " + $%x", val); - return temp; + return util::string_format(" + $%x", val); } -static inline char *signed_16bit_sep_nospace(int16_t val) +std::string dsp32c_disassembler::signed_16bit_sep_nospace(int16_t val) { - static char temp[10]; if (val < 0) - sprintf(temp, "-$%x", -val); + return util::string_format("-$%x", -val); else - sprintf(temp, "+$%x", val); - return temp; + return util::string_format("+$%x", val); } -static inline char *unsigned_16bit_size(int16_t val, uint8_t size) +std::string dsp32c_disassembler::unsigned_16bit_size(int16_t val, uint8_t size) { - static char temp[10]; if (size) - sprintf(temp, "$%06x", (int32_t)val & 0xffffff); + return util::string_format("$%06x", (int32_t)val & 0xffffff); else - sprintf(temp, "$%04x", val & 0xffff); - return temp; + return util::string_format("$%04x", val & 0xffff); } -static uint8_t lastp; -static std::string dasm_XYZ(uint8_t bits) +std::string dsp32c_disassembler::dasm_XYZ(uint8_t bits) { std::string buffer; uint8_t p = bits >> 3; @@ -164,7 +155,7 @@ static std::string dasm_XYZ(uint8_t bits) } -static std::string dasm_PI(uint16_t bits) +std::string dsp32c_disassembler::dasm_PI(uint16_t bits) { std::string buffer; uint8_t p = bits >> 5; @@ -199,10 +190,11 @@ static std::string dasm_PI(uint16_t bits) } -static unsigned dasm_dsp32(std::ostream &stream, unsigned pc, uint32_t op) +offs_t dsp32c_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { uint32_t flags = 0; + uint32_t op = opcodes.r32(pc); switch (op >> 25) { /* DA format 1 */ @@ -344,7 +336,7 @@ static unsigned dasm_dsp32(std::ostream &stream, unsigned pc, uint32_t op) else { if (((op >> 16) & 0x1f) == 20) - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; util::stream_format(stream, "goto %s", rH); } } @@ -359,7 +351,7 @@ static unsigned dasm_dsp32(std::ostream &stream, unsigned pc, uint32_t op) else { if (((op >> 16) & 0x1f) == 20) - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; util::stream_format(stream, "if (%s) goto %s", condtable[C], rH); } } @@ -377,7 +369,7 @@ static unsigned dasm_dsp32(std::ostream &stream, unsigned pc, uint32_t op) { util::stream_format(stream, "if (%s-- >= 0) goto %s%s [%x]", rM, rH, signed_16bit_sep_nospace(N), (pc + 8 + N) & 0xffffff); if (((pc + 8 + N) & 0xffffff) < pc) - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; } else if (N && rH[0] != '0') util::stream_format(stream, "if (%s-- >= 0) goto %s%s", rM, rH, signed_16bit_sep_nospace(N)); @@ -385,13 +377,13 @@ static unsigned dasm_dsp32(std::ostream &stream, unsigned pc, uint32_t op) { util::stream_format(stream, "if (%s-- >= 0) goto $%x", rM, ((int32_t)N & 0xffffff)); if (((int32_t)N & 0xffffff) < pc) - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; } else { util::stream_format(stream, "if (%s-- >= 0) goto %s", rM, rH); if (((op >> 16) & 0x1f) == 20) - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; } break; } @@ -419,7 +411,7 @@ static unsigned dasm_dsp32(std::ostream &stream, unsigned pc, uint32_t op) util::stream_format(stream, "call $%x (%s)", ((int32_t)N & 0xffffff), rM); else util::stream_format(stream, "call %s (%s)", rH, rM); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; } @@ -659,7 +651,7 @@ static unsigned dasm_dsp32(std::ostream &stream, unsigned pc, uint32_t op) else { if (((op >> 16) & 0x1f) == 20) - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; util::stream_format(stream, "goto %s", rH); } break; @@ -685,20 +677,15 @@ static unsigned dasm_dsp32(std::ostream &stream, unsigned pc, uint32_t op) int32_t N = (op & 0xffff) | ((int32_t)((op & 0x1fe00000) << 3) >> 8); const char *rM = regname[(op >> 16) & 0x1f]; util::stream_format(stream, "call $%x (%s)", N & 0xffffff, rM); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; } } - return 4 | flags | DASMFLAG_SUPPORTED; + return 4 | flags | SUPPORTED; } - -/*************************************************************************** - DISASSEMBLY HOOK -***************************************************************************/ - -CPU_DISASSEMBLE( dsp32c ) +uint32_t dsp32c_disassembler::opcode_alignment() const { - return dasm_dsp32(stream, pc, oprom[0] | (oprom[1] << 8) | (oprom[2] << 16) | (oprom[3] << 24)); + return 4; } diff --git a/src/devices/cpu/dsp32/dsp32dis.h b/src/devices/cpu/dsp32/dsp32dis.h new file mode 100644 index 00000000000..96a36de954c --- /dev/null +++ b/src/devices/cpu/dsp32/dsp32dis.h @@ -0,0 +1,45 @@ +// license:BSD-3-Clause +// copyright-holders:Aaron Giles +/*************************************************************************** + + dsp32dis.c + Disassembler for the portable AT&T/Lucent DSP32C emulator. + Written by Aaron Giles + +***************************************************************************/ + +#ifndef MAME_CPU_DSP32_DSP32DIS_H +#define MAME_CPU_DSP32_DSP32DIS_H + +#pragma once + +class dsp32c_disassembler : public util::disasm_interface +{ +public: + dsp32c_disassembler() = default; + virtual ~dsp32c_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *const sizesuffix[]; + static const char *const unarysign[]; + static const char *const sign[]; + static const char *const aMvals[]; + static const char *const memsuffix[]; + static const char *const functable[]; + static const char *const condtable[]; + static const char *const regname[]; + static const char *const regnamee[]; + std::string signed_16bit_unary(int16_t val); + std::string signed_16bit_sep(int16_t val); + std::string signed_16bit_sep_nospace(int16_t val); + std::string unsigned_16bit_size(int16_t val, uint8_t size); + std::string dasm_XYZ(uint8_t bits); + std::string dasm_PI(uint16_t bits); + + uint8_t lastp; +}; + +#endif diff --git a/src/devices/cpu/dsp56k/dsp56dsm.cpp b/src/devices/cpu/dsp56k/dsp56dsm.cpp index 5ca4aab30a0..847a4bda6a0 100644 --- a/src/devices/cpu/dsp56k/dsp56dsm.cpp +++ b/src/devices/cpu/dsp56k/dsp56dsm.cpp @@ -10,22 +10,25 @@ #include "emu.h" #include "opcode.h" +#include "dsp56dsm.h" -#include "emu.h" -#include "dsp56k.h" +u32 dsp56k_disassembler::opcode_alignment() const +{ + return 1; +} /*****************************/ /* Main disassembly function */ /*****************************/ -CPU_DISASSEMBLE(dsp56k) +offs_t dsp56k_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - const uint16_t w0 = oprom[0] | (oprom[1] << 8); - const uint16_t w1 = oprom[2] | (oprom[3] << 8); + const uint16_t w0 = opcodes.r16(pc); + const uint16_t w1 = opcodes.r16(pc+1); // Decode and disassemble. DSP56K::Opcode op(w0, w1); stream << op.disassemble(); const unsigned size = op.size(); - return (size | DASMFLAG_SUPPORTED); + return (size | SUPPORTED); } diff --git a/src/devices/cpu/dsp56k/dsp56dsm.h b/src/devices/cpu/dsp56k/dsp56dsm.h new file mode 100644 index 00000000000..3e0f7cb87ff --- /dev/null +++ b/src/devices/cpu/dsp56k/dsp56dsm.h @@ -0,0 +1,26 @@ +// license:BSD-3-Clause +// copyright-holders:Andrew Gardner +/*************************************************************************** + + dsp56dsm.c + Disassembler for the portable Motorola/Freescale dsp56k emulator. + Written by Andrew Gardner + +***************************************************************************/ + +#ifndef MAME_CPU_DSP56K_DSP56DSM_H +#define MAME_CPU_DSP56K_DSP56DSM_H + +#pragma once + +class dsp56k_disassembler : public util::disasm_interface +{ +public: + dsp56k_disassembler() = default; + virtual ~dsp56k_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/dsp56k/dsp56k.cpp b/src/devices/cpu/dsp56k/dsp56k.cpp index c84948701ef..69b2d8b0341 100644 --- a/src/devices/cpu/dsp56k/dsp56k.cpp +++ b/src/devices/cpu/dsp56k/dsp56k.cpp @@ -33,6 +33,7 @@ #include "emu.h" #include "dsp56k.h" +#include "dsp56dsm.h" #include "opcode.h" @@ -503,9 +504,9 @@ void dsp56k_device::execute_run() } -offs_t dsp56k_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *dsp56k_device::create_disassembler() { - return CPU_DISASSEMBLE_NAME(dsp56k)(this, stream, pc, oprom, opram, options); + return new dsp56k_disassembler; } } // namespace DSP56K diff --git a/src/devices/cpu/dsp56k/dsp56k.h b/src/devices/cpu/dsp56k/dsp56k.h index 4ab93b9b9ca..670078c16c7 100644 --- a/src/devices/cpu/dsp56k/dsp56k.h +++ b/src/devices/cpu/dsp56k/dsp56k.h @@ -235,9 +235,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; @@ -256,6 +254,4 @@ private: DECLARE_DEVICE_TYPE_NS(DSP56156, DSP56K, dsp56k_device) using DSP56K::dsp56k_device; -extern CPU_DISASSEMBLE( dsp56k ); - #endif // MAME_CPU_DSP56K_DSP56K_H diff --git a/src/devices/cpu/dsp56k/inst.h b/src/devices/cpu/dsp56k/inst.h index 91a624f030a..a1ac7ad0a5b 100644 --- a/src/devices/cpu/dsp56k/inst.h +++ b/src/devices/cpu/dsp56k/inst.h @@ -759,7 +759,7 @@ public: void evaluate(dsp56k_core* cpustate) override {} size_t size() const override { return 2; } size_t accumulatorBitsModified() const override { return BM_HIGH | BM_MIDDLE | BM_LOW; } - size_t flags() const override { return DASMFLAG_STEP_OVER; } + size_t flags() const override { return util::disasm_interface::STEP_OVER; } private: op_mnem m_mnem; @@ -790,7 +790,7 @@ public: void evaluate(dsp56k_core* cpustate) override {} size_t size() const override { return 1; } size_t accumulatorBitsModified() const override { return BM_HIGH | BM_MIDDLE | BM_LOW; } - size_t flags() const override { return DASMFLAG_STEP_OVER; } + size_t flags() const override { return util::disasm_interface::STEP_OVER; } private: op_mnem m_mnem; @@ -821,7 +821,7 @@ public: void evaluate(dsp56k_core* cpustate) override {} size_t size() const override { return 2; } size_t accumulatorBitsModified() const override { return BM_HIGH | BM_MIDDLE | BM_LOW; } - size_t flags() const override { return DASMFLAG_STEP_OVER; } + size_t flags() const override { return util::disasm_interface::STEP_OVER; } private: int16_t m_immediate; @@ -847,7 +847,7 @@ public: void evaluate(dsp56k_core* cpustate) override {} size_t size() const override { return 1; } size_t accumulatorBitsModified() const override { return BM_HIGH | BM_MIDDLE | BM_LOW; } - size_t flags() const override { return DASMFLAG_STEP_OVER; } + size_t flags() const override { return util::disasm_interface::STEP_OVER; } }; // CHKAAU : 0000 0000 0000 0100 : A-58 ///////////////////////////////////////// @@ -1597,7 +1597,7 @@ public: void evaluate(dsp56k_core* cpustate) override {} size_t size() const override { return 2; } size_t accumulatorBitsModified() const override { return BM_HIGH | BM_MIDDLE | BM_LOW; } - size_t flags() const override { return DASMFLAG_STEP_OVER; } + size_t flags() const override { return util::disasm_interface::STEP_OVER; } private: op_mnem m_mnem; @@ -1628,7 +1628,7 @@ public: void evaluate(dsp56k_core* cpustate) override {} size_t size() const override { return 1; } size_t accumulatorBitsModified() const override { return BM_HIGH | BM_MIDDLE | BM_LOW; } - size_t flags() const override { return DASMFLAG_STEP_OVER; } + size_t flags() const override { return util::disasm_interface::STEP_OVER; } private: op_mnem m_mnem; @@ -1658,7 +1658,7 @@ public: void evaluate(dsp56k_core* cpustate) override {} size_t size() const override { return 2; } size_t accumulatorBitsModified() const override { return BM_HIGH | BM_MIDDLE | BM_LOW; } - size_t flags() const override { return DASMFLAG_STEP_OVER; } + size_t flags() const override { return util::disasm_interface::STEP_OVER; } private: uint16_t m_displacement; @@ -1688,7 +1688,7 @@ public: void evaluate(dsp56k_core* cpustate) override {} size_t size() const override { return 1; } size_t accumulatorBitsModified() const override { return BM_HIGH | BM_MIDDLE | BM_LOW; } - size_t flags() const override { return DASMFLAG_STEP_OVER; } + size_t flags() const override { return util::disasm_interface::STEP_OVER; } private: uint8_t m_bAddr; @@ -1714,7 +1714,7 @@ public: void evaluate(dsp56k_core* cpustate) override {} size_t size() const override { return 1; } size_t accumulatorBitsModified() const override { return BM_HIGH | BM_MIDDLE | BM_LOW; } - size_t flags() const override { return DASMFLAG_STEP_OVER; } + size_t flags() const override { return util::disasm_interface::STEP_OVER; } }; // LEA : 0000 0001 11TT MMRR : A-116 /////////////////////////////////////////// @@ -3236,7 +3236,7 @@ public: void evaluate(dsp56k_core* cpustate) override {} size_t size() const override { return 1; } size_t accumulatorBitsModified() const override { return BM_HIGH | BM_MIDDLE | BM_LOW; } - size_t flags() const override { return DASMFLAG_STEP_OUT; } + size_t flags() const override { return util::disasm_interface::STEP_OUT; } }; // RTS : 0000 0000 0000 0110 : A-196 /////////////////////////////////////////// @@ -3258,7 +3258,7 @@ public: void evaluate(dsp56k_core* cpustate) override {} size_t size() const override { return 1; } size_t accumulatorBitsModified() const override { return BM_HIGH | BM_MIDDLE | BM_LOW; } - size_t flags() const override { return DASMFLAG_STEP_OUT; } + size_t flags() const override { return util::disasm_interface::STEP_OUT; } }; // SBC : .... .... 0101 F01J : A-198 /////////////////////////////////////////// diff --git a/src/devices/cpu/e0c6200/e0c6200.cpp b/src/devices/cpu/e0c6200/e0c6200.cpp index ad4e99ba8c6..46d169547e2 100644 --- a/src/devices/cpu/e0c6200/e0c6200.cpp +++ b/src/devices/cpu/e0c6200/e0c6200.cpp @@ -20,6 +20,7 @@ #include "emu.h" #include "e0c6200.h" +#include "e0c6200d.h" #include "debugger.h" @@ -49,10 +50,9 @@ void e0c6200_cpu_device::state_string_export(const device_state_entry &entry, st } } -offs_t e0c6200_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +util::disasm_interface *e0c6200_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE(e0c6200); - return CPU_DISASSEMBLE_NAME(e0c6200)(this, stream, pc, oprom, opram, options); + return new e0c6200_disassembler; } diff --git a/src/devices/cpu/e0c6200/e0c6200.h b/src/devices/cpu/e0c6200/e0c6200.h index 2a8c02734ec..9328aed7cf1 100644 --- a/src/devices/cpu/e0c6200/e0c6200.h +++ b/src/devices/cpu/e0c6200/e0c6200.h @@ -34,9 +34,8 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual u32 disasm_min_opcode_bytes() const override { return 2; } - virtual u32 disasm_max_opcode_bytes() const override { return 2; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; + virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; address_space_config m_program_config; diff --git a/src/devices/cpu/e0c6200/e0c6200d.cpp b/src/devices/cpu/e0c6200/e0c6200d.cpp index fde754ef051..be2a4ea4d6d 100644 --- a/src/devices/cpu/e0c6200/e0c6200d.cpp +++ b/src/devices/cpu/e0c6200/e0c6200d.cpp @@ -7,21 +7,9 @@ */ #include "emu.h" -#include "debugger.h" -#include "e0c6200.h" +#include "e0c6200d.h" -// opcode mnemonics -enum e_mnemonics -{ - em_JP, em_RETD, em_CALL, em_CALZ, - em_LD, em_LBPX, em_ADC, em_CP, em_ADD, em_SUB, em_SBC, em_AND, em_OR, em_XOR, - em_RLC, em_FAN, em_PSET, em_LDPX, em_LDPY, em_SET, em_RST, em_INC, em_DEC, - em_RRC, em_ACPX, em_ACPY, em_SCPX, em_SCPY, em_PUSH, em_POP, - em_RETS, em_RET, em_JPBA, em_HALT, em_SLP, em_NOP5, em_NOP7, - em_NOT, em_SCF, em_SZF, em_SDF, em_EI, em_DI, em_RDF, em_RZF, em_RCF, em_ILL -}; - -static const char *const em_name[] = +const char *const e0c6200_disassembler::em_name[] = { "JP", "RETD", "CALL", "CALZ", "LD", "LBPX", "ADC", "CP", "ADD", "SUB", "SBC", "AND", "OR", "XOR", @@ -31,32 +19,20 @@ static const char *const em_name[] = "NOT", "SCF", "SZF", "SDF", "EI", "DI", "RDF", "RZF", "RCF", "?" }; -#define _OVER DASMFLAG_STEP_OVER -#define _OUT DASMFLAG_STEP_OUT - -static const u32 em_flags[] = +const u32 e0c6200_disassembler::em_flags[] = { - 0, _OUT, _OVER, _OVER, + 0, STEP_OUT, STEP_OVER, STEP_OVER, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - _OUT, _OUT, 0, _OVER, _OVER, 0, 0, + STEP_OUT, STEP_OUT, 0, STEP_OVER, STEP_OVER, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; -// opcode params -enum e_params -{ - ep_S, ep_E, ep_I, ep_R0, ep_R2, ep_R4, ep_Q, - ep_cC, ep_cNC, ep_cZ, ep_cNZ, - ep_A, ep_B, ep_X, ep_Y, ep_MX, ep_MY, ep_XP, ep_XH, ep_XL, ep_YP, ep_YH, ep_YL, - ep_P, ep_F, ep_MN, ep_SP, ep_SPH, ep_SPL -}; - // 0-digit is number of bits per opcode parameter, 0 bits is literal, // 0x10-digit is for shift-right, 0x100-digit is special flag for r/q param -static const u16 ep_bits[] = +const u16 e0c6200_disassembler::ep_bits[] = { 8, 8, 4, 0x102, 0x122, 0x142, 0x102, 0, 0, 0, 0, @@ -65,10 +41,10 @@ static const u16 ep_bits[] = }; // redirect for r/q param -static const u8 ep_redirect_r[4] = { ep_A, ep_B, ep_MX, ep_MY }; +const u8 e0c6200_disassembler::ep_redirect_r[4] = { ep_A, ep_B, ep_MX, ep_MY }; // literal opcode parameter -static const char *const ep_name[] = +const char *const e0c6200_disassembler::ep_name[] = { " ", " ", " ", " ", " ", " ", " ", "C", "NC", "Z", "NZ", @@ -77,7 +53,7 @@ static const char *const ep_name[] = }; -static char* decode_param(u16 opcode, int param, char* buffer) +std::string e0c6200_disassembler::decode_param(u16 opcode, int param) { int bits = ep_bits[param] & 0xf; int shift = ep_bits[param] >> 4 & 0xf; @@ -89,30 +65,22 @@ static char* decode_param(u16 opcode, int param, char* buffer) // literal param if (ep_bits[param] == 0) - { - strcpy(buffer, ep_name[param]); - return buffer; - } + return ep_name[param]; // print value like how it's documented in the manual - char val[10]; - if (bits > 4 || opmask > 9) - sprintf(val, "%02XH", opmask); - else - sprintf(val, "%d", opmask); + std::string val = (bits > 4 || opmask > 9) ? + util::string_format("%02XH", opmask) : + util::string_format("%d", opmask); if (param == ep_MN) - sprintf(buffer, "M%s", val); + return 'M' + val; else - strcpy(buffer, val); - - return buffer; + return val; } - -CPU_DISASSEMBLE(e0c6200) +offs_t e0c6200_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - u16 op = (oprom[1] | oprom[0] << 8) & 0xfff; + u16 op = opcodes.r16(pc) & 0xfff; int m; int p1 = -1; @@ -693,15 +661,34 @@ CPU_DISASSEMBLE(e0c6200) util::stream_format(stream, "%-6s", em_name[m]); // fetch param(s) - char pbuffer[10]; if (p1 != -1) { - util::stream_format(stream, "%s", decode_param(op, p1, pbuffer)); + util::stream_format(stream, "%s", decode_param(op, p1)); if (p2 != -1) { - util::stream_format(stream, ",%s", decode_param(op, p2, pbuffer)); + util::stream_format(stream, ",%s", decode_param(op, p2)); } } - return 1 | em_flags[m] | DASMFLAG_SUPPORTED; + return 1 | em_flags[m] | SUPPORTED; +} + +u32 e0c6200_disassembler::opcode_alignment() const +{ + return 1; +} + +u32 e0c6200_disassembler::interface_flags() const +{ + return PAGED2LEVEL; +} + +u32 e0c6200_disassembler::page_address_bits() const +{ + return 8; +} + +u32 e0c6200_disassembler::page2_address_bits() const +{ + return 4; } diff --git a/src/devices/cpu/e0c6200/e0c6200d.h b/src/devices/cpu/e0c6200/e0c6200d.h new file mode 100644 index 00000000000..d2555c4ead8 --- /dev/null +++ b/src/devices/cpu/e0c6200/e0c6200d.h @@ -0,0 +1,55 @@ +// license:BSD-3-Clause +// copyright-holders:hap +/* + + Seiko Epson E0C6200 disassembler + +*/ + +#ifndef MAME_CPU_E0C6200_E0C6200D_H +#define MAME_CPU_E0C6200_E0C6200D_H + +#pragma once + +class e0c6200_disassembler : public util::disasm_interface +{ +public: + e0c6200_disassembler() = default; + virtual ~e0c6200_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual u32 interface_flags() const override; + virtual u32 page_address_bits() const override; + virtual u32 page2_address_bits() const override; + + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum e_mnemonics + { + em_JP, em_RETD, em_CALL, em_CALZ, + em_LD, em_LBPX, em_ADC, em_CP, em_ADD, em_SUB, em_SBC, em_AND, em_OR, em_XOR, + em_RLC, em_FAN, em_PSET, em_LDPX, em_LDPY, em_SET, em_RST, em_INC, em_DEC, + em_RRC, em_ACPX, em_ACPY, em_SCPX, em_SCPY, em_PUSH, em_POP, + em_RETS, em_RET, em_JPBA, em_HALT, em_SLP, em_NOP5, em_NOP7, + em_NOT, em_SCF, em_SZF, em_SDF, em_EI, em_DI, em_RDF, em_RZF, em_RCF, em_ILL + }; + + enum e_params + { + ep_S, ep_E, ep_I, ep_R0, ep_R2, ep_R4, ep_Q, + ep_cC, ep_cNC, ep_cZ, ep_cNZ, + ep_A, ep_B, ep_X, ep_Y, ep_MX, ep_MY, ep_XP, ep_XH, ep_XL, ep_YP, ep_YH, ep_YL, + ep_P, ep_F, ep_MN, ep_SP, ep_SPH, ep_SPL + }; + + static const char *const em_name[]; + static const u32 em_flags[]; + static const u16 ep_bits[]; + static const u8 ep_redirect_r[4]; + static const char *const ep_name[]; + + std::string decode_param(u16 opcode, int param); +}; + +#endif diff --git a/src/devices/cpu/e132xs/32xsdasm.cpp b/src/devices/cpu/e132xs/32xsdasm.cpp index ec853983346..2060350c5b8 100644 --- a/src/devices/cpu/e132xs/32xsdasm.cpp +++ b/src/devices/cpu/e132xs/32xsdasm.cpp @@ -8,13 +8,11 @@ */ #include "emu.h" -#include "e132xs.h" -#include "debugger.h" - +#include "32xsdasm.h" #include "32xsdefs.h" -static const char *const L_REG[] = +const char *const hyperstone_disassembler::L_REG[] = { "L0", "L1", "L2", "L3", "L4", "L5", "L6", "L7", "L8", "L9", "L10", "L11", "L12", "L13", "L14", "L15", "L16", "L17", "L18", "L19", @@ -25,7 +23,7 @@ static const char *const L_REG[] = "L60", "L61", "L62", "L63" }; -static const char *const G_REG[] = +const char *const hyperstone_disassembler::G_REG[] = { "PC", "SR", "FER", "G03", "G04", "G05", "G06", "G07", "G08", "G09", "G10", "G11", "G12", "G13", "G14", "G15", "G16", "G17", "SP", "UB", @@ -33,7 +31,7 @@ static const char *const G_REG[] = "G30", "G31" }; -static const char *const SETxx[] = +const char *const hyperstone_disassembler::SETxx[] = { "SETADR", "Reserved", "SET1", "SET0", "SETLE", "SETGT", "SETLT", "SETGE", "SETSE", "SETHT", "SETST", "SETHE", "SETE", "SETNE", "SETV", "SETNV", @@ -49,20 +47,13 @@ static const char *const SETxx[] = #define N_VALUE(op) ((((op & 0x100) >> 8) << 4 ) | (op & 0x0f)) -static int size, global_fp; - -static offs_t base_pc; -static const uint8_t *base_oprom; -#define READ_OP_DASM(p) ((base_oprom[(p) - base_pc] << 8) | base_oprom[(p) + 1 - base_pc]) - - -static void LL_format(char *source, char *dest, uint16_t op) +void hyperstone_disassembler::LL_format(char *source, char *dest, uint16_t op) { strcpy(source, L_REG[(SOURCECODE(op)+global_fp)%64]); strcpy(dest, L_REG[(DESTCODE(op)+global_fp)%64]); } -static void LR_format(char *source, char *dest, uint16_t op) +void hyperstone_disassembler::LR_format(char *source, char *dest, uint16_t op) { if( SOURCEBIT(op) ) { @@ -76,7 +67,7 @@ static void LR_format(char *source, char *dest, uint16_t op) strcpy(dest, L_REG[(DESTCODE(op)+global_fp)%64]); } -static void RR_format(char *source, char *dest, uint16_t op, unsigned h_flag) +void hyperstone_disassembler::RR_format(char *source, char *dest, uint16_t op, unsigned h_flag) { if( SOURCEBIT(op) ) { @@ -97,7 +88,7 @@ static void RR_format(char *source, char *dest, uint16_t op, unsigned h_flag) } } -static uint32_t LRconst_format(char *source, char *dest, uint16_t op, unsigned *pc) +uint32_t hyperstone_disassembler::LRconst_format(char *source, char *dest, uint16_t op, offs_t &pc, const data_buffer &opcodes) { uint16_t next_op; uint32_t const_val; @@ -115,8 +106,8 @@ static uint32_t LRconst_format(char *source, char *dest, uint16_t op, unsigned * size = 4; - *pc += 2; - next_op = READ_OP_DASM(*pc); + pc += 2; + next_op = opcodes.r16(pc); if( E_BIT(next_op) ) { @@ -124,8 +115,8 @@ static uint32_t LRconst_format(char *source, char *dest, uint16_t op, unsigned * size = 6; - *pc += 2; - next_op2 = READ_OP_DASM(*pc); + pc += 2; + next_op2 = opcodes.r16(pc); const_val = next_op2; const_val |= ((next_op & 0x3fff) << 16 ); @@ -147,7 +138,7 @@ static uint32_t LRconst_format(char *source, char *dest, uint16_t op, unsigned * return const_val; } -static uint32_t RRconst_format(char *source, char *dest, uint16_t op, unsigned *pc) +uint32_t hyperstone_disassembler::RRconst_format(char *source, char *dest, uint16_t op, offs_t &pc, const data_buffer &opcodes) { uint16_t next_op; uint32_t const_val; @@ -172,8 +163,8 @@ static uint32_t RRconst_format(char *source, char *dest, uint16_t op, unsigned * size = 4; - *pc += 2; - next_op = READ_OP_DASM(*pc); + pc += 2; + next_op = opcodes.r16(pc); if( E_BIT(next_op) ) { @@ -181,8 +172,8 @@ static uint32_t RRconst_format(char *source, char *dest, uint16_t op, unsigned * size = 6; - *pc += 2; - next_op2 = READ_OP_DASM(*pc); + pc += 2; + next_op2 = opcodes.r16(pc); const_val = next_op2; const_val |= ((next_op & 0x3fff) << 16 ); @@ -204,7 +195,7 @@ static uint32_t RRconst_format(char *source, char *dest, uint16_t op, unsigned * return const_val; } -static int32_t Rimm_format(char *dest, uint16_t op, unsigned *pc, unsigned h_flag) +int32_t hyperstone_disassembler::Rimm_format(char *dest, uint16_t op, offs_t &pc, const data_buffer &opcodes, unsigned h_flag) { uint16_t imm1, imm2; int32_t ret; @@ -227,10 +218,10 @@ static int32_t Rimm_format(char *dest, uint16_t op, unsigned *pc, unsigned h_fla return n; case 17: - *pc += 2; - imm1 = READ_OP_DASM(*pc); - *pc += 2; - imm2 = READ_OP_DASM(*pc); + pc += 2; + imm1 = opcodes.r16(pc); + pc += 2; + imm2 = opcodes.r16(pc); ret = (imm1 << 16) | imm2; size = 6; @@ -238,15 +229,15 @@ static int32_t Rimm_format(char *dest, uint16_t op, unsigned *pc, unsigned h_fla case 18: - *pc += 2; - ret = READ_OP_DASM(*pc); + pc += 2; + ret = opcodes.r16(pc); size = 4; return ret; case 19: - *pc += 2; - ret = (int32_t) (0xffff0000 | READ_OP_DASM(*pc)); + pc += 2; + ret = (int32_t) (0xffff0000 | opcodes.r16(pc)); size = 4; return ret; @@ -292,14 +283,14 @@ static int32_t Rimm_format(char *dest, uint16_t op, unsigned *pc, unsigned h_fla } } -static uint8_t Ln_format(char *dest, uint16_t op) +uint8_t hyperstone_disassembler::Ln_format(char *dest, uint16_t op) { strcpy(dest, L_REG[(DESTCODE(op)+global_fp)%64]); return N_VALUE(op); } -static uint8_t Rn_format(char *dest, uint16_t op) +uint8_t hyperstone_disassembler::Rn_format(char *dest, uint16_t op) { if( DESTBIT(op) ) { @@ -313,7 +304,7 @@ static uint8_t Rn_format(char *dest, uint16_t op) return N_VALUE(op); } -static int32_t PCrel_format(uint16_t op, unsigned pc) +int32_t hyperstone_disassembler::PCrel_format(uint16_t op, offs_t pc, const data_buffer &opcodes) { int32_t ret; @@ -325,7 +316,7 @@ static int32_t PCrel_format(uint16_t op, unsigned pc) pc += 2; - next = READ_OP_DASM(pc); + next = opcodes.r16(pc); ret = (op & 0x7f) << 16; @@ -345,7 +336,7 @@ static int32_t PCrel_format(uint16_t op, unsigned pc) return (pc + ret); } -static uint32_t RRdis_format(char *source, char *dest, uint16_t op, uint16_t next_op, unsigned pc) +uint32_t hyperstone_disassembler::RRdis_format(char *source, char *dest, uint16_t op, uint16_t next_op, offs_t pc, const data_buffer &opcodes) { uint32_t ret; @@ -373,7 +364,7 @@ static uint32_t RRdis_format(char *source, char *dest, uint16_t op, uint16_t nex size = 6; - next = READ_OP_DASM(pc + 4); + next = opcodes.r16(pc + 4); ret = next; ret |= ( ( next_op & 0xfff ) << 16 ); @@ -395,7 +386,15 @@ static uint32_t RRdis_format(char *source, char *dest, uint16_t op, uint16_t nex return ret; } -unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom, unsigned h_flag, int private_fp) +u32 hyperstone_disassembler::opcode_alignment() const +{ + return 2; +} + +/*****************************/ +/* Main disassembly function */ +/*****************************/ +offs_t hyperstone_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { uint16_t op; uint8_t op_num; @@ -405,10 +404,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom char source[5] = "\0", dest[5] = "\0"; uint32_t flags = 0; - base_pc = pc; - base_oprom = oprom; - - op = READ_OP_DASM(pc); + op = opcodes.r16(pc); size = 2; @@ -417,7 +413,8 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom source_bit = SOURCEBIT(op); dest_bit = DESTBIT(op); - global_fp = private_fp; + global_fp = 0; + int h_flag = 0; op_num = (op & 0xff00) >> 8; @@ -456,7 +453,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom global_fp = 0; RR_format(source, dest, op, 0); util::stream_format(stream, "RET PC, %s", source); - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; } else if( source_code == SR_REGISTER && !source_bit ) { @@ -495,7 +492,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom size = 4; pc += 2; - op = READ_OP_DASM(pc); + op = opcodes.r16(pc); xcode = X_CODE(op); @@ -510,7 +507,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom size = 6; pc += 2; - next_op = READ_OP_DASM(pc); + next_op = opcodes.r16(pc); lim = ((op & 0xfff) << 16) | next_op; } @@ -533,7 +530,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // MASK case 0x14: case 0x15: case 0x16: case 0x17: { - uint32_t const_val = RRconst_format(source, dest, op, &pc); + uint32_t const_val = RRconst_format(source, dest, op, pc, opcodes); util::stream_format(stream, "MASK %s, %s, $%x", dest, source, const_val); @@ -543,7 +540,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // SUM case 0x18: case 0x19: case 0x1a: case 0x1b: { - uint32_t const_val = RRconst_format(source, dest, op, &pc); + uint32_t const_val = RRconst_format(source, dest, op, pc, opcodes); if( source_code == SR_REGISTER && !source_bit ) { @@ -560,7 +557,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // SUMS case 0x1c: case 0x1d: case 0x1e: case 0x1f: { - uint32_t const_val = RRconst_format(source, dest, op, &pc); + uint32_t const_val = RRconst_format(source, dest, op, pc, opcodes); if( source_code == SR_REGISTER && !source_bit ) { @@ -778,7 +775,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // CMPI case 0x60: case 0x61: case 0x62: case 0x63: { - uint32_t imm = Rimm_format(dest, op, &pc, 0); + uint32_t imm = Rimm_format(dest, op, pc, opcodes, 0); util::stream_format(stream, "CMPI %s, $%x", dest, imm); @@ -788,7 +785,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // MOVI case 0x64: case 0x65: case 0x66: case 0x67: { - uint32_t imm = Rimm_format(dest, op, &pc, h_flag); + uint32_t imm = Rimm_format(dest, op, pc, opcodes, h_flag); util::stream_format(stream, "MOVI %s, $%x", dest, imm); @@ -798,7 +795,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // ADDI case 0x68: case 0x69: case 0x6a: case 0x6b: { - uint32_t imm = Rimm_format(dest, op, &pc, 0); + uint32_t imm = Rimm_format(dest, op, pc, opcodes, 0); if( !N_VALUE(op) ) { @@ -815,7 +812,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // ADDSI case 0x6c: case 0x6d: case 0x6e: case 0x6f: { - uint32_t imm = Rimm_format(dest, op, &pc, 0); + uint32_t imm = Rimm_format(dest, op, pc, opcodes, 0); if( !N_VALUE(op) ) { @@ -832,7 +829,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // CMPBI case 0x70: case 0x71: case 0x72: case 0x73: { - uint32_t imm = Rimm_format(dest, op, &pc, 0); + uint32_t imm = Rimm_format(dest, op, pc, opcodes, 0); if( !N_VALUE(op) ) { @@ -852,7 +849,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // ANDNI case 0x74: case 0x75: case 0x76: case 0x77: { - uint32_t imm = Rimm_format(dest, op, &pc, 0); + uint32_t imm = Rimm_format(dest, op, pc, opcodes, 0); if( N_VALUE(op) == 31 ) imm = 0x7fffffff; //bit 31 = 0, others = 1 @@ -865,7 +862,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // ORI case 0x78: case 0x79: case 0x7a: case 0x7b: { - uint32_t imm = Rimm_format(dest, op, &pc, 0); + uint32_t imm = Rimm_format(dest, op, pc, opcodes, 0); util::stream_format(stream, "ORI %s, $%x", dest, imm); @@ -875,7 +872,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // XORI case 0x7c: case 0x7d: case 0x7e: case 0x7f: { - uint32_t imm = Rimm_format(dest, op, &pc, 0); + uint32_t imm = Rimm_format(dest, op, pc, opcodes, 0); util::stream_format(stream, "XORI %s, $%x", dest, imm); @@ -995,8 +992,8 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // LDxx.D/A/IOD/IOA case 0x90: case 0x91: case 0x92: case 0x93: { - uint16_t next_op = READ_OP_DASM(pc + 2); - uint32_t dis = RRdis_format(source, dest, op, next_op, pc); + uint16_t next_op = opcodes.r16(pc + 2); + uint32_t dis = RRdis_format(source, dest, op, next_op, pc, opcodes); if( size == 2 ) size = 4; @@ -1113,8 +1110,8 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // LDxx.N/S case 0x94: case 0x95: case 0x96: case 0x97: { - uint16_t next_op = READ_OP_DASM(pc + 2); - uint32_t dis = RRdis_format(source, dest, op, next_op, pc); + uint16_t next_op = opcodes.r16(pc + 2); + uint32_t dis = RRdis_format(source, dest, op, next_op, pc, opcodes); if( size == 2 ) size = 4; @@ -1182,8 +1179,8 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // STxx.D/A/IOD/IOA case 0x98: case 0x99: case 0x9a: case 0x9b: { - uint16_t next_op = READ_OP_DASM(pc + 2); - uint32_t dis = RRdis_format(source, dest, op, next_op, pc); + uint16_t next_op = opcodes.r16(pc + 2); + uint32_t dis = RRdis_format(source, dest, op, next_op, pc, opcodes); if( size == 2 ) size = 4; @@ -1303,8 +1300,8 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // STxx.N/S case 0x9c: case 0x9d: case 0x9e: case 0x9f: { - uint16_t next_op = READ_OP_DASM(pc + 2); - uint32_t dis = RRdis_format(source, dest, op, next_op, pc); + uint16_t next_op = opcodes.r16(pc + 2); + uint32_t dis = RRdis_format(source, dest, op, next_op, pc, opcodes); if( size == 2 ) size = 4; @@ -1584,7 +1581,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom LL_format(source, dest, op); pc += 2; - extended_op = READ_OP_DASM(pc); + extended_op = opcodes.r16(pc); size = 4; @@ -1752,10 +1749,10 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // DBV case 0xe0: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "DBV $%x", rel); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; } @@ -1763,10 +1760,10 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // DBNV case 0xe1: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "DBNV $%x", rel); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; } @@ -1774,10 +1771,10 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // DBE case 0xe2: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "DBE $%x", rel); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; } @@ -1785,10 +1782,10 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // DBNE case 0xe3: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "DBNE $%x", rel); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; } @@ -1796,10 +1793,10 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // DBC case 0xe4: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "DBC $%x", rel); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; } @@ -1807,10 +1804,10 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // DBNC case 0xe5: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "DBNC $%x", rel); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; } @@ -1818,10 +1815,10 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // DBSE case 0xe6: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "DBSE $%x", rel); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; } @@ -1829,10 +1826,10 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // DBHT case 0xe7: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "DBHT $%x", rel); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; } @@ -1840,10 +1837,10 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // DBN case 0xe8: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "DBN $%x", rel); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; } @@ -1851,10 +1848,10 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // DBNN case 0xe9: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "DBNN $%x", rel); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; } @@ -1862,10 +1859,10 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // DBLE case 0xea: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "DBLE $%x", rel); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; } @@ -1873,10 +1870,10 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // DBGT case 0xeb: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "DBGT $%x", rel); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; } @@ -1884,10 +1881,10 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // DBR case 0xec: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "DBR $%x", rel); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; } @@ -1905,17 +1902,17 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // CALL case 0xee: case 0xef: { - uint32_t const_val = LRconst_format(source, dest, op, &pc); + uint32_t const_val = LRconst_format(source, dest, op, pc, opcodes); if( source_code == SR_REGISTER && !source_bit ) { util::stream_format(stream, "CALL %s, 0, $%x", dest, const_val); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; } else { util::stream_format(stream, "CALL %s, %s, $%x", dest, source, const_val); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; } break; @@ -1924,7 +1921,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // BV case 0xf0: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "BV $%x", rel); @@ -1934,7 +1931,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // BNV case 0xf1: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "BNV $%x", rel); @@ -1944,7 +1941,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // BE case 0xf2: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "BE $%x", rel); @@ -1954,7 +1951,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // BNE case 0xf3: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "BNE $%x", rel); @@ -1964,7 +1961,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // BC case 0xf4: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "BC $%x", rel); @@ -1974,7 +1971,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // BNC case 0xf5: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "BNC $%x", rel); @@ -1984,7 +1981,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // BSE case 0xf6: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "BSE $%x", rel); @@ -1994,7 +1991,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // BHT case 0xf7: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "BHT $%x", rel); @@ -2004,7 +2001,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // BN case 0xf8: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "BN $%x", rel); @@ -2014,7 +2011,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // BNN case 0xf9: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "BNN $%x", rel); @@ -2024,7 +2021,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // BLE case 0xfa: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "BLE $%x", rel); @@ -2034,7 +2031,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // BGT case 0xfb: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "BGT $%x", rel); @@ -2044,7 +2041,7 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom // BR case 0xfc: { - int32_t rel = PCrel_format(op, pc) + 2; + int32_t rel = PCrel_format(op, pc, opcodes) + 2; util::stream_format(stream, "BR $%x", rel); @@ -2061,73 +2058,73 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom { case TRAPLE: util::stream_format(stream, "TRAPLE %d", trapno); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case TRAPGT: util::stream_format(stream, "TRAPGT %d", trapno); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case TRAPLT: util::stream_format(stream, "TRAPLT %d", trapno); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case TRAPGE: util::stream_format(stream, "TRAPGE %d", trapno); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case TRAPSE: util::stream_format(stream, "TRAPSE %d", trapno); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case TRAPHT: util::stream_format(stream, "TRAPHT %d", trapno); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case TRAPST: util::stream_format(stream, "TRAPST %d", trapno); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case TRAPHE: util::stream_format(stream, "TRAPHE %d", trapno); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case TRAPE: util::stream_format(stream, "TRAPE %d", trapno); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case TRAPNE: util::stream_format(stream, "TRAPNE %d", trapno); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case TRAPV: util::stream_format(stream, "TRAPV %d", trapno); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case TRAP: util::stream_format(stream, "TRAP %d", trapno); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; } @@ -2136,10 +2133,5 @@ unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom } } - return size | flags | DASMFLAG_SUPPORTED; -} - -CPU_DISASSEMBLE( hyperstone_generic ) -{ - return dasm_hyperstone( stream, pc, oprom, 0, 0 ); + return size | flags | SUPPORTED; } diff --git a/src/devices/cpu/e132xs/32xsdasm.h b/src/devices/cpu/e132xs/32xsdasm.h new file mode 100644 index 00000000000..6c5b0fa4482 --- /dev/null +++ b/src/devices/cpu/e132xs/32xsdasm.h @@ -0,0 +1,43 @@ +// license:BSD-3-Clause +// copyright-holders:Pierpaolo Prazzoli +/* + + Hyperstone disassembler + written by Pierpaolo Prazzoli + +*/ + +#ifndef MAME_CPU_E132XS_32XSDASM_H +#define MAME_CPU_E132XS_32XSDASM_H + +#pragma once + +class hyperstone_disassembler : public util::disasm_interface +{ +public: + hyperstone_disassembler() = default; + virtual ~hyperstone_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *const L_REG[]; + static const char *const G_REG[]; + static const char *const SETxx[]; + + int size, global_fp; + + void LL_format(char *source, char *dest, uint16_t op); + void LR_format(char *source, char *dest, uint16_t op); + void RR_format(char *source, char *dest, uint16_t op, unsigned h_flag); + uint32_t LRconst_format(char *source, char *dest, uint16_t op, offs_t &pc, const data_buffer &opcodes); + uint32_t RRconst_format(char *source, char *dest, uint16_t op, offs_t &pc, const data_buffer &opcodes); + int32_t Rimm_format(char *dest, uint16_t op, offs_t &pc, const data_buffer &opcodes, unsigned h_flag); + uint8_t Ln_format(char *dest, uint16_t op); + uint8_t Rn_format(char *dest, uint16_t op); + int32_t PCrel_format(uint16_t op, offs_t pc, const data_buffer &opcodes); + uint32_t RRdis_format(char *source, char *dest, uint16_t op, uint16_t next_op, offs_t pc, const data_buffer &opcodes); +}; + +#endif diff --git a/src/devices/cpu/e132xs/e132xs.cpp b/src/devices/cpu/e132xs/e132xs.cpp index a56b4c2444d..bfeac9a702b 100644 --- a/src/devices/cpu/e132xs/e132xs.cpp +++ b/src/devices/cpu/e132xs/e132xs.cpp @@ -147,6 +147,7 @@ #include "debugger.h" #include "32xsdefs.h" +#include "32xsdasm.h" //#define VERBOSE 1 #include "logmacro.h" @@ -1349,36 +1350,13 @@ void hyperstone_device::state_string_export(const device_state_entry &entry, std //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t hyperstone_device::disasm_min_opcode_bytes() const -{ - return 2; -} - - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t hyperstone_device::disasm_max_opcode_bytes() const -{ - return 6; -} - - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t hyperstone_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *hyperstone_device::create_disassembler() { - extern CPU_DISASSEMBLE( hyperstone ); - return dasm_hyperstone(stream, pc, oprom, GET_H, GET_FP); + return new hyperstone_disassembler; } /* Opcodes */ diff --git a/src/devices/cpu/e132xs/e132xs.h b/src/devices/cpu/e132xs/e132xs.h index 56efefd05df..e0a3819e0c0 100644 --- a/src/devices/cpu/e132xs/e132xs.h +++ b/src/devices/cpu/e132xs/e132xs.h @@ -24,12 +24,6 @@ /* Functions */ -/*************************************************************************** - REGISTER ENUMERATION -***************************************************************************/ - -extern unsigned dasm_hyperstone(std::ostream &stream, unsigned pc, const uint8_t *oprom, unsigned h_flag, int private_fp); - //************************************************************************** // TYPE DEFINITIONS //************************************************************************** @@ -142,9 +136,7 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // device_state_interface overrides virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; diff --git a/src/devices/cpu/es5510/es5510.cpp b/src/devices/cpu/es5510/es5510.cpp index 5848ccc05e2..61a94d8316f 100644 --- a/src/devices/cpu/es5510/es5510.cpp +++ b/src/devices/cpu/es5510/es5510.cpp @@ -9,6 +9,7 @@ #include "emu.h" #include "es5510.h" +#include "es5510d.h" #include "cpu/m68000/m68000.h" #include "debugger.h" @@ -924,19 +925,9 @@ void es5510_device::execute_run() { } } -uint32_t es5510_device::disasm_min_opcode_bytes() const +util::disasm_interface *es5510_device::create_disassembler() { - return 6; -} - -uint32_t es5510_device::disasm_max_opcode_bytes() const -{ - return 6; -} - -offs_t es5510_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) -{ - return pc; + return new es5510_disassembler; } #if VERBOSE_EXEC diff --git a/src/devices/cpu/es5510/es5510.h b/src/devices/cpu/es5510/es5510.h index 56045a4e769..0fd41807684 100644 --- a/src/devices/cpu/es5510/es5510.h +++ b/src/devices/cpu/es5510/es5510.h @@ -131,10 +131,8 @@ protected: virtual uint32_t execute_max_cycles() const override; virtual uint32_t execute_input_lines() const override; virtual void execute_run() override; - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; virtual void execute_set_input(int linenum, int state) override; + virtual util::disasm_interface *create_disassembler() override; int32_t alu_operation(uint8_t op, int32_t aValue, int32_t bValue, uint8_t &flags); void alu_operation_end(); diff --git a/src/devices/cpu/es5510/es5510d.cpp b/src/devices/cpu/es5510/es5510d.cpp new file mode 100644 index 00000000000..3436ba39fca --- /dev/null +++ b/src/devices/cpu/es5510/es5510d.cpp @@ -0,0 +1,20 @@ +// license:BSD-3-Clause +// copyright-holders:Christian Brunschen +/*************************************************************************** + * + * es5510.c - Ensoniq ES5510 (ESP) emulation + * by Christian Brunschen + * + ***************************************************************************/ + +#include "es5510d.h" + +u32 es5510_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t es5510_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + return 1; +} diff --git a/src/devices/cpu/es5510/es5510d.h b/src/devices/cpu/es5510/es5510d.h new file mode 100644 index 00000000000..e80b4a3fe36 --- /dev/null +++ b/src/devices/cpu/es5510/es5510d.h @@ -0,0 +1,25 @@ +// license:BSD-3-Clause +// copyright-holders:Christian Brunschen +/*************************************************************************** + * + * es5510.c - Ensoniq ES5510 (ESP) emulation + * by Christian Brunschen + * + ***************************************************************************/ + +#ifndef MAME_CPU_ES5510_ES5510DASM_H +#define MAME_CPU_ES5510_ES5510DASM_H + +#pragma once + +class es5510_disassembler : public util::disasm_interface +{ +public: + es5510_disassembler() = default; + virtual ~es5510_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/esrip/esrip.cpp b/src/devices/cpu/esrip/esrip.cpp index ee8416304c7..9f85cc2cdf3 100644 --- a/src/devices/cpu/esrip/esrip.cpp +++ b/src/devices/cpu/esrip/esrip.cpp @@ -11,6 +11,7 @@ #include "emu.h" #include "esrip.h" +#include "esripdsm.h" #include "debugger.h" #include "screen.h" @@ -372,39 +373,15 @@ void esrip_device::state_string_export(const device_state_entry &entry, std::str //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t esrip_device::disasm_min_opcode_bytes() const -{ - return 8; -} - - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t esrip_device::disasm_max_opcode_bytes() const -{ - return 8; -} - - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t esrip_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *esrip_device::create_disassembler() { - extern CPU_DISASSEMBLE( esrip ); - return CPU_DISASSEMBLE_NAME(esrip)(this, stream, pc, oprom, opram, options); + return new esrip_disassembler; } - /*************************************************************************** PRIVATE FUNCTIONS ***************************************************************************/ diff --git a/src/devices/cpu/esrip/esrip.h b/src/devices/cpu/esrip/esrip.h index 8aaa0f1d071..69e03139704 100644 --- a/src/devices/cpu/esrip/esrip.h +++ b/src/devices/cpu/esrip/esrip.h @@ -136,9 +136,7 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // device_state_interface overrides virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; @@ -266,7 +264,4 @@ private: void am29116_execute(uint16_t inst, int _sre); }; - -CPU_DISASSEMBLE( esrip ); - #endif // MAME_CPU_ESRIP_ESRIP_H diff --git a/src/devices/cpu/esrip/esripdsm.cpp b/src/devices/cpu/esrip/esripdsm.cpp index 04890fba2e4..43ecd616539 100644 --- a/src/devices/cpu/esrip/esripdsm.cpp +++ b/src/devices/cpu/esrip/esripdsm.cpp @@ -10,14 +10,18 @@ ***************************************************************************/ #include "emu.h" -#include "debugger.h" +#include "esripdsm.h" +u32 esrip_disassembler::opcode_alignment() const +{ + return 1; +} /*************************************************************************** DISASSEMBLY HOOK (TODO: FINISH) ***************************************************************************/ -CPU_DISASSEMBLE(esrip) +offs_t esrip_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { #if 0 static const char* const jmp_types[] = @@ -45,7 +49,7 @@ CPU_DISASSEMBLE(esrip) }; #endif - uint64_t inst = big_endianize_int64(*(uint64_t *)oprom); + uint64_t inst = opcodes.r64(pc); uint32_t inst_hi = inst >> 32; uint32_t inst_lo = inst & 0xffffffff; @@ -91,5 +95,5 @@ CPU_DISASSEMBLE(esrip) ctrl3 & 0x80 ? ' ' : '7' ); - return 1 | DASMFLAG_SUPPORTED; + return 1 | SUPPORTED; } diff --git a/src/devices/cpu/esrip/esripdsm.h b/src/devices/cpu/esrip/esripdsm.h new file mode 100644 index 00000000000..0491a02bf29 --- /dev/null +++ b/src/devices/cpu/esrip/esripdsm.h @@ -0,0 +1,27 @@ +// license:BSD-3-Clause +// copyright-holders:Philip Bennett +/*************************************************************************** + + esripdsm.c + + Implementation of the Entertainment Sciences + AM29116-based Real Time Image Processor + +***************************************************************************/ + +#ifndef MAME_CPU_ESRIP_ESRIPDSM_H +#define MAME_CPU_ESRIP_ESRIPDSM_H + +#pragma once + +class esrip_disassembler : public util::disasm_interface +{ +public: + esrip_disassembler() = default; + virtual ~esrip_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/f8/f8.cpp b/src/devices/cpu/f8/f8.cpp index 4d5f420fe62..17db2883556 100644 --- a/src/devices/cpu/f8/f8.cpp +++ b/src/devices/cpu/f8/f8.cpp @@ -16,6 +16,7 @@ #include "emu.h" #include "f8.h" +#include "f8dasm.h" #include "debugger.h" #define S 0x01 @@ -2070,10 +2071,9 @@ void f8_cpu_device::state_string_export(const device_state_entry &entry, std::st } -offs_t f8_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *f8_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( f8 ); - return CPU_DISASSEMBLE_NAME(f8)(this, stream, pc, oprom, opram, options); + return new f8_disassembler; } diff --git a/src/devices/cpu/f8/f8.h b/src/devices/cpu/f8/f8.h index 5be9090ec2b..ebe0fde3eb3 100644 --- a/src/devices/cpu/f8/f8.h +++ b/src/devices/cpu/f8/f8.h @@ -54,9 +54,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 3; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/f8/f8dasm.cpp b/src/devices/cpu/f8/f8dasm.cpp index 4c44aa2c424..49827760cd7 100644 --- a/src/devices/cpu/f8/f8dasm.cpp +++ b/src/devices/cpu/f8/f8dasm.cpp @@ -1,18 +1,22 @@ // license:BSD-3-Clause // copyright-holders:Juergen Buchmueller #include "emu.h" -#include "debugger.h" -#include "f8.h" +#include "f8dasm.h" -static const char *const rname[16] = { +const char *const f8_disassembler::rname[16] = { "R0", "R1", "R2", "R3", "R4", "R5", "R6", "R7", "R8", "J", "HU", "HL", "KU", "KL", "QU", "QL" }; -CPU_DISASSEMBLE(f8) +u32 f8_disassembler::opcode_alignment() const { - unsigned size = 0; - uint8_t op = oprom[size++]; + return 1; +} + +offs_t f8_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + offs_t base_pc = pc; + uint8_t op = opcodes.r8(pc++); switch( op ) { @@ -116,40 +120,40 @@ CPU_DISASSEMBLE(f8) util::stream_format(stream, "INC"); break; case 0x20: /* 0010 0000 */ - util::stream_format(stream, "LI $%02X", oprom[size++]); + util::stream_format(stream, "LI $%02X", opcodes.r8(pc++)); break; case 0x21: /* 0010 0001 */ - util::stream_format(stream, "NI $%02X", oprom[size++]); + util::stream_format(stream, "NI $%02X", opcodes.r8(pc++)); break; case 0x22: /* 0010 0010 */ - util::stream_format(stream, "OI $%02X", oprom[size++]); + util::stream_format(stream, "OI $%02X", opcodes.r8(pc++)); break; case 0x23: /* 0010 0011 */ - util::stream_format(stream, "XI $%02X", oprom[size++]); + util::stream_format(stream, "XI $%02X", opcodes.r8(pc++)); break; case 0x24: /* 0010 0100 */ - util::stream_format(stream, "AI $%02X", oprom[size++]); + util::stream_format(stream, "AI $%02X", opcodes.r8(pc++)); break; case 0x25: /* 0010 0101 */ - util::stream_format(stream, "CI $%02X", oprom[size++]); + util::stream_format(stream, "CI $%02X", opcodes.r8(pc++)); break; case 0x26: /* 0010 0110 */ - util::stream_format(stream, "IN $%02X", oprom[size++]); + util::stream_format(stream, "IN $%02X", opcodes.r8(pc++)); break; case 0x27: /* 0010 0111 */ - util::stream_format(stream, "OUT $%02X", oprom[size++]); + util::stream_format(stream, "OUT $%02X", opcodes.r8(pc++)); break; case 0x28: /* 0010 1000 */ - util::stream_format(stream, "PI $%02X%02X", oprom[size + 0], oprom[size + 1]); - size += 2; + util::stream_format(stream, "PI $%02X%02X", opcodes.r16(pc)); + pc += 2; break; case 0x29: /* 0010 1001 */ - util::stream_format(stream, "JMP $%02X%02X", oprom[size + 0], oprom[size + 1]); - size += 2; + util::stream_format(stream, "JMP $%02X%02X", opcodes.r16(pc)); + pc += 2; break; case 0x2a: /* 0010 1010 */ - util::stream_format(stream, "DCI $%02X%02X", oprom[size + 0], oprom[size + 1]); - size += 2; + util::stream_format(stream, "DCI $%02X%02X", opcodes.r16(pc)); + pc += 2; break; case 0x2b: /* 0010 1011 */ util::stream_format(stream, "NOP"); @@ -286,22 +290,22 @@ CPU_DISASSEMBLE(f8) case 0x81: /* 1000 0001 */ case 0x85: /* 1000 0101 */ - util::stream_format(stream, "BP $%04X", pc + (int8_t)oprom[size++] + 1); + util::stream_format(stream, "BP $%04X", base_pc + (int8_t)opcodes.r8(pc++) + 1); break; case 0x82: /* 1000 0010 */ - util::stream_format(stream, "BC $%04X", pc + (int8_t)oprom[size++] + 1); + util::stream_format(stream, "BC $%04X", base_pc + (int8_t)opcodes.r8(pc++) + 1); break; case 0x84: /* 1000 0100 */ - util::stream_format(stream, "BZ $%04X", pc + (int8_t)oprom[size++] + 1); + util::stream_format(stream, "BZ $%04X", base_pc + (int8_t)opcodes.r8(pc++) + 1); break; case 0x80: /* 1000 0000 */ case 0x83: /* 1000 0011 */ case 0x86: /* 1000 0110 */ case 0x87: /* 1000 0111 */ - util::stream_format(stream, "BT $%02X,$%04X", op & 0x07, pc + (int8_t)oprom[size++] + 1); + util::stream_format(stream, "BT $%02X,$%04X", op & 0x07, base_pc + (int8_t)opcodes.r8(pc++) + 1); break; case 0x88: /* 1000 1000 */ @@ -333,28 +337,28 @@ CPU_DISASSEMBLE(f8) break; case 0x8f: /* 1000 1111 */ - util::stream_format(stream, "BR7 $%04X", pc + (int8_t)oprom[size++] + 1); + util::stream_format(stream, "BR7 $%04X", base_pc + (int8_t)opcodes.r8(pc++) + 1); break; case 0x90: /* 1001 0000 */ - util::stream_format(stream, "BR $%04X", pc + (int8_t)oprom[size++] + 1); + util::stream_format(stream, "BR $%04X", base_pc + (int8_t)opcodes.r8(pc++) + 1); break; case 0x91: /* 1001 0001 */ case 0x95: /* 1001 0101 */ - util::stream_format(stream, "BM $%04X", pc + (int8_t)oprom[size++] + 1); + util::stream_format(stream, "BM $%04X", base_pc + (int8_t)opcodes.r8(pc++) + 1); break; case 0x92: /* 1001 0010 */ - util::stream_format(stream, "BNC $%04X", pc + (int8_t)oprom[size++] + 1); + util::stream_format(stream, "BNC $%04X", base_pc + (int8_t)opcodes.r8(pc++) + 1); break; case 0x94: /* 1001 0100 */ - util::stream_format(stream, "BNZ $%04X", pc + (int8_t)oprom[size++] + 1); + util::stream_format(stream, "BNZ $%04X", base_pc + (int8_t)opcodes.r8(pc++) + 1); break; case 0x98: /* 1001 1000 */ - util::stream_format(stream, "BNO $%04X", pc + (int8_t)oprom[size++] + 1); + util::stream_format(stream, "BNO $%04X", base_pc + (int8_t)opcodes.r8(pc++) + 1); break; case 0x93: /* 1001 0011 */ @@ -367,7 +371,7 @@ CPU_DISASSEMBLE(f8) case 0x9d: /* 1001 1101 */ case 0x9e: /* 1001 1110 */ case 0x9f: /* 1001 1111 */ - util::stream_format(stream, "BF $%02X,$%04X", op & 0x0f, pc + (int8_t)oprom[size++] + 1); + util::stream_format(stream, "BF $%02X,$%04X", op & 0x0f, base_pc + (int8_t)opcodes.r8(pc++) + 1); break; case 0xa0: /* 1010 0000 */ @@ -530,5 +534,5 @@ CPU_DISASSEMBLE(f8) break; } - return size; + return pc - base_pc; } diff --git a/src/devices/cpu/f8/f8dasm.h b/src/devices/cpu/f8/f8dasm.h new file mode 100644 index 00000000000..112cf35dc0f --- /dev/null +++ b/src/devices/cpu/f8/f8dasm.h @@ -0,0 +1,21 @@ +// license:BSD-3-Clause +// copyright-holders:Juergen Buchmueller + +#ifndef MAME_CPU_F8_F8DASM_H +#define MAME_CPU_F8_F8DASM_H + +#pragma once + +class f8_disassembler : public util::disasm_interface +{ +public: + f8_disassembler() = default; + virtual ~f8_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +private: + static const char *const rname[16]; +}; + +#endif diff --git a/src/devices/cpu/g65816/g65816.cpp b/src/devices/cpu/g65816/g65816.cpp index b121fba081a..6514f113b05 100644 --- a/src/devices/cpu/g65816/g65816.cpp +++ b/src/devices/cpu/g65816/g65816.cpp @@ -767,18 +767,19 @@ void g65816_device::execute_set_input(int line, int state) (this->*FTABLE_SET_LINE)(line, state); } -/* Disassemble an instruction */ -#include "g65816ds.h" - +util::disasm_interface *g65816_device::create_disassembler() +{ + return new g65816_disassembler(this); +} -offs_t g65816_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +bool g65816_device::get_m_flag() const { - return g65816_disassemble(stream, (pc & 0x00ffff), (pc & 0xff0000) >> 16, oprom, FLAG_M, FLAG_X); + return FLAG_M; } -CPU_DISASSEMBLE( g65816 ) +bool g65816_device::get_x_flag() const { - return g65816_disassemble(stream, (pc & 0x00ffff), (pc & 0xff0000) >> 16, oprom, 0/*FLAG_M*/, 0/*FLAG_X*/); + return FLAG_X; } void g65816_device::g65816_restore_state() diff --git a/src/devices/cpu/g65816/g65816.h b/src/devices/cpu/g65816/g65816.h index 67f21b780bc..cfacba32927 100644 --- a/src/devices/cpu/g65816/g65816.h +++ b/src/devices/cpu/g65816/g65816.h @@ -5,6 +5,7 @@ #pragma once +#include "g65816ds.h" #include "g65816cm.h" /* ======================================================================== */ @@ -45,7 +46,7 @@ enum #define G65816_INT_NMI G65816_LINE_NMI -class g65816_device : public cpu_device +class g65816_device : public cpu_device, public g65816_disassembler::config { public: // construction/destruction @@ -85,9 +86,9 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; + virtual bool get_m_flag() const override; + virtual bool get_x_flag() const override; address_space_config m_program_config; diff --git a/src/devices/cpu/g65816/g65816ds.cpp b/src/devices/cpu/g65816/g65816ds.cpp index aad24ceb545..5fde19e4218 100644 --- a/src/devices/cpu/g65816/g65816ds.cpp +++ b/src/devices/cpu/g65816/g65816ds.cpp @@ -12,102 +12,55 @@ All rights reserved. */ - #include "emu.h" #include "g65816ds.h" -#ifdef SEC -#undef SEC -#endif - -#define ADDRESS_65816(A) ((A)&0xffffff) - - -namespace { - -class g65816_opcode_struct +g65816_disassembler::g65816_disassembler(config *conf) : m_config(conf) { -public: - const char *name() const - { - return s_opnames[unsigned(m_name)]; - } +} - bool is_call() const - { - switch (m_name) - { - case op::JSR: - case op::JSL: - return true; - default: - return false; - } - } +u32 g65816_disassembler::opcode_alignment() const +{ + return 1; +} - bool is_return() const - { - switch (m_name) - { - case op::RTI: - case op::RTL: - case op::RTS: - return true; - default: - return false; - } - } +const char *g65816_disassembler::opcode_struct::name() const +{ + return g65816_disassembler::s_opnames[unsigned(m_name)]; +} - static const g65816_opcode_struct &get(unsigned char ins) +bool g65816_disassembler::opcode_struct::is_call() const +{ + switch (m_name) { - return s_opcodes[ins]; + case op::JSR: + case op::JSL: + return true; + default: + return false; } +} - unsigned char flag; - unsigned char ea; - -protected: - enum class op : unsigned - { - ADC , AND , ASL , BCC , BCS , BEQ , BIT , BMI , BNE , BPL , BRA , - BRK , BRL , BVC , BVS , CLC , CLD , CLI , CLV , CMP , COP , CPX , - CPY , DEA , DEC , DEX , DEY , EOR , INA , INC , INX , INY , JML , - JMP , JSL , JSR , LDA , LDX , LDY , LSR , MVN , MVP , NOP , ORA , - PEA , PEI , PER , PHA , PHB , PHD , PHK , PHP , PHX , PHY , PLA , - PLB , PLD , PLP , PLX , PLY , REP , ROL , ROR , RTI , RTL , RTS , - SBC , SEC , SED , SEI , SEP , STA , STP , STX , STY , STZ , TAX , - TAY , TCS , TCD , TDC , TRB , TSB , TSC , TSX , TXA , TXS , TXY , - TYA , TYX , WAI , WDM , XBA , XCE - }; - - g65816_opcode_struct(op n, unsigned char f, unsigned char e) - : flag(f) - , ea(e) - , m_name(n) +bool g65816_disassembler::opcode_struct::is_return() const +{ + switch (m_name) { + case op::RTI: + case op::RTL: + case op::RTS: + return true; + default: + return false; } +} - op m_name; - - static const char *const s_opnames[]; - static const g65816_opcode_struct s_opcodes[256]; -}; - -enum +g65816_disassembler::opcode_struct::opcode_struct(op n, u8 f, u8 e) : m_name(n), flag(f), ea(e) { - IMP , ACC , RELB, RELW, IMM , A , AI , AL , ALX , AX , AXI , - AY , D , DI , DIY , DLI , DLIY, DX , DXI , DY , S , SIY , - SIG , MVN , MVP , PEA , PEI , PER -}; +} + -enum -{ - I, /* ignore */ - M, /* check m bit */ - X /* check x bit */ -}; -const char *const g65816_opcode_struct::s_opnames[] = +const char *const g65816_disassembler::s_opnames[] = { "ADC", "AND", "ASL", "BCC", "BCS", "BEQ", "BIT", "BMI", "BNE", "BPL", "BRA", "BRK", "BRL", "BVC", "BVS", "CLC", "CLD", "CLI", "CLV", "CMP", "COP", "CPX", @@ -120,7 +73,7 @@ const char *const g65816_opcode_struct::s_opnames[] = "TYA", "TYX", "WAI", "WDM", "XBA", "XCE" }; -const g65816_opcode_struct g65816_opcode_struct::s_opcodes[256] = +const g65816_disassembler::opcode_struct g65816_disassembler::s_opcodes[256] = { {op::BRK, I, SIG }, {op::ORA, M, DXI }, {op::COP, I, SIG }, {op::ORA, M, S }, {op::TSB, M, D }, {op::ORA, M, D }, {op::ASL, M, D }, {op::ORA, M, DLI }, @@ -188,83 +141,38 @@ const g65816_opcode_struct g65816_opcode_struct::s_opcodes[256] = {op::JSR, I, AXI }, {op::SBC, M, AX }, {op::INC, M, AX }, {op::SBC, M, ALX } }; -} // anonymous namespace - -static const uint8_t *base_oprom; -static uint32_t base_pc; - -static inline unsigned int read_8(unsigned int address) -{ - address = ADDRESS_65816(address); - return base_oprom[address - base_pc]; -} - -static inline unsigned int read_16(unsigned int address) -{ - unsigned int val = read_8(address); - return val | (read_8(address+1)<<8); -} - -static inline unsigned int read_24(unsigned int address) -{ - unsigned int val = read_8(address); - val |= (read_8(address+1)<<8); - return val | (read_8(address+2)<<16); -} - -static inline char* int_8_str(unsigned int val) +std::string g65816_disassembler::int_8_str(u8 val) { - static char str[20]; - - val &= 0xff; - if(val & 0x80) - sprintf(str, "-$%x", (0-val) & 0x7f); + return util::string_format("-$%x", (0-val) & 0x7f); else - sprintf(str, "$%x", val & 0x7f); - - return str; + return util::string_format("$%x", val & 0x7f); } -static inline char* int_16_str(unsigned int val) +std::string g65816_disassembler::int_16_str(u16 val) { - static char str[20]; - - val &= 0xffff; - if(val & 0x8000) - sprintf(str, "-$%x", (0-val) & 0x7fff); + return util::string_format("-$%x", (0-val) & 0x7fff); else - sprintf(str, "$%x", val & 0x7fff); - - return str; + return util::string_format("$%x", val & 0x7fff); } -unsigned g65816_disassemble(std::ostream &stream, unsigned int pc, unsigned int pb, const uint8_t *oprom, int m_flag, int x_flag) +offs_t g65816_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - unsigned int instruction; - const g65816_opcode_struct* opcode; int var; int length = 1; - unsigned int address; - unsigned dasm_flags; - - pb <<= 16; - address = pc | pb; - - base_oprom = oprom; - base_pc = address; + offs_t dasm_flags; - instruction = read_8(address); - opcode = &g65816_opcode_struct::get(instruction); + u8 instruction = opcodes.r8(pc & 0xffffff); + const opcode_struct *opcode = &s_opcodes[instruction]; stream << opcode->name(); if (opcode->is_call()) - dasm_flags = DASMFLAG_STEP_OVER; + dasm_flags = STEP_OVER; else if (opcode->is_return()) - dasm_flags = DASMFLAG_STEP_OUT; + dasm_flags = STEP_OUT; else dasm_flags = 0; @@ -276,113 +184,108 @@ unsigned g65816_disassemble(std::ostream &stream, unsigned int pc, unsigned int util::stream_format(stream, "A"); break; case RELB: - var = (int8_t) read_8(address+1); + var = (int8_t) opcodes.r8((pc+1) & 0xffffff); length++; - util::stream_format(stream, " %06x (%s)", pb | ((pc + length + var)&0xffff), int_8_str(var)); + util::stream_format(stream, " %06x (%s)", (pc & 0xff0000) | ((pc + length + var)&0xffff), int_8_str(var)); break; case RELW: case PER : - var = read_16(address+1); + var = opcodes.r16((pc+1) & 0xffffff); length += 2; - util::stream_format(stream, " %06x (%s)", pb | ((pc + length + var)&0xffff), int_16_str(var)); + util::stream_format(stream, " %06x (%s)", (pc & 0xff0000) | ((pc + length + var)&0xffff), int_16_str(var)); break; case IMM : - if((opcode->flag == M && !m_flag) || (opcode->flag == X && !x_flag)) + if((opcode->flag == M && !m_config->get_m_flag()) || (opcode->flag == X && !m_config->get_x_flag())) { - util::stream_format(stream, " #$%04x", read_16(address+1)); + util::stream_format(stream, " #$%04x", opcodes.r16((pc+1) & 0xffffff)); length += 2; } else { - util::stream_format(stream, " #$%02x", read_8(address+1)); + util::stream_format(stream, " #$%02x", opcodes.r8((pc+1) & 0xffffff)); length++; } break; case A : case PEA : - util::stream_format(stream, " $%04x", read_16(address+1)); + util::stream_format(stream, " $%04x", opcodes.r16((pc+1) & 0xffffff)); length += 2; break; case AI : - util::stream_format(stream, " ($%04x)", read_16(address+1)); + util::stream_format(stream, " ($%04x)", opcodes.r16((pc+1) & 0xffffff)); length += 2; break; case AL : - util::stream_format(stream, " $%06x", read_24(address+1)); + util::stream_format(stream, " $%06x", opcodes.r32((pc+1) & 0xffffff) & 0xffffff); length += 3; break; case ALX : - util::stream_format(stream, " $%06x,X", read_24(address+1)); + util::stream_format(stream, " $%06x,X", opcodes.r32((pc+1) & 0xffffff) & 0xffffff); length += 3; break; case AX : - util::stream_format(stream, " $%04x,X", read_16(address+1)); + util::stream_format(stream, " $%04x,X", opcodes.r16((pc+1) & 0xffffff)); length += 2; break; case AXI : - util::stream_format(stream, " ($%04x,X)", read_16(address+1)); + util::stream_format(stream, " ($%04x,X)", opcodes.r16((pc+1) & 0xffffff)); length += 2; break; case AY : - util::stream_format(stream, " $%04x,Y", read_16(address+1)); + util::stream_format(stream, " $%04x,Y", opcodes.r16((pc+1) & 0xffffff)); length += 2; break; case D : - util::stream_format(stream, " $%02x", read_8(address+1)); + util::stream_format(stream, " $%02x", opcodes.r8((pc+1) & 0xffffff)); length++; break; case DI : case PEI : - util::stream_format(stream, " ($%02x)", read_8(address+1)); + util::stream_format(stream, " ($%02x)", opcodes.r8((pc+1) & 0xffffff)); length++; break; case DIY : - util::stream_format(stream, " ($%02x),Y", read_8(address+1)); + util::stream_format(stream, " ($%02x),Y", opcodes.r8((pc+1) & 0xffffff)); length++; break; case DLI : - util::stream_format(stream, " [$%02x]", read_8(address+1)); + util::stream_format(stream, " [$%02x]", opcodes.r8((pc+1) & 0xffffff)); length++; break; case DLIY: - util::stream_format(stream, " [$%02x],Y", read_8(address+1)); + util::stream_format(stream, " [$%02x],Y", opcodes.r8((pc+1) & 0xffffff)); length++; break; case DX : - util::stream_format(stream, " $%02x,X", read_8(address+1)); + util::stream_format(stream, " $%02x,X", opcodes.r8((pc+1) & 0xffffff)); length++; break; case DXI : - util::stream_format(stream, " ($%02x,X)", read_8(address+1)); + util::stream_format(stream, " ($%02x,X)", opcodes.r8((pc+1) & 0xffffff)); length++; break; case DY : - util::stream_format(stream, " $%02x,Y", read_8(address+1)); + util::stream_format(stream, " $%02x,Y", opcodes.r8((pc+1) & 0xffffff)); length++; break; case S : - util::stream_format(stream, " %s,S", int_8_str(read_8(address+1))); + util::stream_format(stream, " %s,S", int_8_str(opcodes.r8((pc+1) & 0xffffff))); length++; break; case SIY : - util::stream_format(stream, " (%s,S),Y", int_8_str(read_8(address+1))); + util::stream_format(stream, " (%s,S),Y", int_8_str(opcodes.r8((pc+1) & 0xffffff))); length++; break; case SIG : - util::stream_format(stream, " #$%02x", read_8(address+1)); + util::stream_format(stream, " #$%02x", opcodes.r8((pc+1) & 0xffffff)); length++; break; case MVN : case MVP : - util::stream_format(stream, " $%02x, $%02x", read_8(address+2), read_8(address+1)); + util::stream_format(stream, " $%02x, $%02x", opcodes.r8((pc+2) & 0xffffff), opcodes.r8((pc+1) & 0xffffff)); length += 2; break; } - return length | DASMFLAG_SUPPORTED | dasm_flags; -} - -CPU_DISASSEMBLE( g65816_generic ) -{ - return g65816_disassemble(stream, (pc & 0x00ffff), (pc & 0xff0000) >> 16, oprom, 0, 0); + return length | SUPPORTED | dasm_flags; } diff --git a/src/devices/cpu/g65816/g65816ds.h b/src/devices/cpu/g65816/g65816ds.h index 892dd065a10..832754de4cd 100644 --- a/src/devices/cpu/g65816/g65816ds.h +++ b/src/devices/cpu/g65816/g65816ds.h @@ -16,7 +16,68 @@ All rights reserved. */ -unsigned g65816_disassemble(std::ostream &stream, unsigned int pc, unsigned int pb, const uint8_t *oprom, int m_flag, int x_flag); +class g65816_disassembler : public util::disasm_interface +{ +public: + class config { + public: + virtual ~config() = default; + virtual bool get_m_flag() const = 0; + virtual bool get_x_flag() const = 0; + }; + g65816_disassembler(config *conf); + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum class op : unsigned + { + ADC , AND , ASL , BCC , BCS , BEQ , BIT , BMI , BNE , BPL , BRA , + BRK , BRL , BVC , BVS , CLC , CLD , CLI , CLV , CMP , COP , CPX , + CPY , DEA , DEC , DEX , DEY , EOR , INA , INC , INX , INY , JML , + JMP , JSL , JSR , LDA , LDX , LDY , LSR , MVN , MVP , NOP , ORA , + PEA , PEI , PER , PHA , PHB , PHD , PHK , PHP , PHX , PHY , PLA , + PLB , PLD , PLP , PLX , PLY , REP , ROL , ROR , RTI , RTL , RTS , + SBC , SEC , SED , SEI , SEP , STA , STP , STX , STY , STZ , TAX , + TAY , TCS , TCD , TDC , TRB , TSB , TSC , TSX , TXA , TXS , TXY , + TYA , TYX , WAI , WDM , XBA , XCE + }; + + enum + { + IMP , ACC , RELB, RELW, IMM , A , AI , AL , ALX , AX , AXI , + AY , D , DI , DIY , DLI , DLIY, DX , DXI , DY , S , SIY , + SIG , MVN , MVP , PEA , PEI , PER + }; + + enum + { + I, /* ignore */ + M, /* check m bit */ + X /* check x bit */ + }; + + class opcode_struct { + public: + op m_name; + u8 flag; + u8 ea; + + opcode_struct(op n, u8 f, u8 e); + const char *name() const; + bool is_call() const; + bool is_return() const; + }; + + static const char *const s_opnames[]; + static const opcode_struct s_opcodes[256]; + + config *m_config; + + std::string int_8_str(u8 val); + std::string int_16_str(u16 val); +}; #endif /* __G65816DS_H__ */ diff --git a/src/devices/cpu/h6280/6280dasm.cpp b/src/devices/cpu/h6280/6280dasm.cpp index c214a058c52..35b1b60c165 100644 --- a/src/devices/cpu/h6280/6280dasm.cpp +++ b/src/devices/cpu/h6280/6280dasm.cpp @@ -18,69 +18,10 @@ ******************************************************************************/ -#ifdef __OS2__ -/* To avoid name clash of _brk */ -#define __STRICT_ANSI__ -#endif - #include "emu.h" +#include "6280dasm.h" -#define RDOP(addr) (oprom[addr - pc]) -#define RDBYTE(addr) (opram[addr - pc]) -#define RDWORD(addr) (opram[addr - pc] | ( oprom[(addr) + 1 - pc] << 8 )) - -enum addr_mode { - _non=0, /* no additional arguments */ - _acc, /* accumulator */ - _imp, /* implicit */ - _imm, /* immediate */ - _abs, /* absolute */ - _zpg, /* zero page */ - _zpx, /* zero page + X */ - _zpy, /* zero page + Y */ - _zpi, /* zero page indirect */ - _abx, /* absolute + X */ - _aby, /* absolute + Y */ - _rel, /* relative */ - _idx, /* zero page pre indexed */ - _idy, /* zero page post indexed */ - _ind, /* indirect */ - _iax, /* indirect + X */ - _blk, /* block */ - _zrl, /* zero page relative */ - _imz, /* immediate, zero page */ - _izx, /* immediate, zero page + X */ - _ima, /* immediate, absolute */ - _imx /* immediate, absolute + X */ -}; - -enum opcodes { - /* 6502 opcodes */ - _adc=0,_and, _asl, _bcc, _bcs, _beq, _bit, _bmi, - _bne, _bpl, _brk, _bvc, _bvs, _clc, _cld, _cli, - _clv, _cmp, _cpx, _cpy, _dec, _dex, _dey, _eor, - _inc, _inx, _iny, _jmp, _jsr, _lda, _ldx, _ldy, - _lsr, _nop, _ora, _pha, _php, _pla, _plp, _rol, - _ror, _rti, _rts, _sbc, _sec, _sed, _sei, _sta, - _stx, _sty, _tax, _tay, _tsx, _txa, _txs, _tya, - _ill, - - /* Hu6280 extensions */ - _bra, _stz, _trb, _tsb, _dea, _ina, _sax, _bsr, - _phx, _phy, _plx, _ply, _csh, _csl, _tam, _tma, - _cla, _cly, _clx, _st0, _st1, _st2, _tst, _set, - _tdd, _tia, _tii, _tin, _tai, _say, _sxy, - - _sm0, _sm1, _sm2, _sm3, _sm4, _sm5, _sm6, _sm7, - _rm0, _rm1, _rm2, _rm3, _rm4, _rm5, _rm6, _rm7, - - _bs0, _bs1, _bs2, _bs3, _bs4, _bs5, _bs6, _bs7, - _br0, _br1, _br2, _br3, _br4, _br5, _br6, _br7 - -}; - - -static const char *const token[]= +const char *const h6280_disassembler::token[]= { /* 6502 opcodes */ "adc", "and", "asl", "bcc", "bcs", "beq", "bit", "bmi", @@ -105,7 +46,7 @@ static const char *const token[]= "bbr0", "bbr1", "bbr2", "bbr3", "bbr4", "bbr5", "bbr6", "bbr7" }; -static const unsigned char op6280[512]= +const unsigned char h6280_disassembler::op6280[512]= { _brk,_imp, _ora,_idx, _sxy,_imp, _st0,_imm, _tsb,_zpg, _ora,_zpg, _asl,_zpg, _rm0,_zpg, /* 00 */ _php,_imp, _ora,_imm, _asl,_acc, _ill,_non, _tsb,_abs, _ora,_abs, _asl,_abs, _br0,_zrl, @@ -141,16 +82,22 @@ static const unsigned char op6280[512]= _sed,_imp, _sbc,_aby, _plx,_imp, _ill,_non, _ill,_non, _sbc,_abx, _inc,_abx, _bs7,_zrl }; +u32 h6280_disassembler::opcode_alignment() const +{ + return 1; +} + /***************************************************************************** * Disassemble a single command and return the number of bytes it uses. *****************************************************************************/ -CPU_DISASSEMBLE(h6280) +offs_t h6280_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { uint32_t flags = 0; - int PC, OP, opc, arg; + offs_t PC; + int OP, opc, arg; PC = pc; - OP = RDOP(PC); + OP = opcodes.r8(PC); OP = OP << 1; PC++; @@ -158,9 +105,9 @@ CPU_DISASSEMBLE(h6280) arg = op6280[OP+1]; if (opc == _jsr || opc == _bsr) - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; else if (opc == _rts) - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; switch(arg) { @@ -171,84 +118,84 @@ CPU_DISASSEMBLE(h6280) util::stream_format(stream, "%s", token[opc]); break; case _rel: - util::stream_format(stream, "%-5s$%04X", token[opc], (PC + 1 + (signed char)RDBYTE(PC)) & 0xffff); + util::stream_format(stream, "%-5s$%04X", token[opc], (PC + 1 + (signed char)params.r8(PC)) & 0xffff); PC+=1; break; case _imm: - util::stream_format(stream, "%-5s#$%02X", token[opc], RDBYTE(PC)); + util::stream_format(stream, "%-5s#$%02X", token[opc], params.r8(PC)); PC+=1; break; case _zpg: - util::stream_format(stream, "%-5s$%02X", token[opc], RDBYTE(PC)); + util::stream_format(stream, "%-5s$%02X", token[opc], params.r8(PC)); PC+=1; break; case _zpx: - util::stream_format(stream, "%-5s$%02X,x", token[opc], RDBYTE(PC)); + util::stream_format(stream, "%-5s$%02X,x", token[opc], params.r8(PC)); PC+=1; break; case _zpy: - util::stream_format(stream, "%-5s$%02X,y", token[opc], RDBYTE(PC)); + util::stream_format(stream, "%-5s$%02X,y", token[opc], params.r8(PC)); PC+=1; break; case _idx: - util::stream_format(stream, "%-5s($%02X,x)", token[opc], RDBYTE(PC)); + util::stream_format(stream, "%-5s($%02X,x)", token[opc], params.r8(PC)); PC+=1; break; case _idy: - util::stream_format(stream, "%-5s($%02X),y", token[opc], RDBYTE(PC)); + util::stream_format(stream, "%-5s($%02X),y", token[opc], params.r8(PC)); PC+=1; break; case _zpi: - util::stream_format(stream, "%-5s($%02X)", token[opc], RDBYTE(PC)); + util::stream_format(stream, "%-5s($%02X)", token[opc], params.r8(PC)); PC+=1; break; case _abs: - util::stream_format(stream, "%-5s$%04X", token[opc], RDWORD(PC)); + util::stream_format(stream, "%-5s$%04X", token[opc], params.r16(PC)); PC+=2; break; case _abx: - util::stream_format(stream, "%-5s$%04X,x", token[opc], RDWORD(PC)); + util::stream_format(stream, "%-5s$%04X,x", token[opc], params.r16(PC)); PC+=2; break; case _aby: - util::stream_format(stream, "%-5s$%04X,y", token[opc], RDWORD(PC)); + util::stream_format(stream, "%-5s$%04X,y", token[opc], params.r16(PC)); PC+=2; break; case _ind: - util::stream_format(stream, "%-5s($%04X)", token[opc], RDWORD(PC)); + util::stream_format(stream, "%-5s($%04X)", token[opc], params.r16(PC)); PC+=2; break; case _iax: - util::stream_format(stream, "%-5s($%04X),X", token[opc], RDWORD(PC)); + util::stream_format(stream, "%-5s($%04X),X", token[opc], params.r16(PC)); PC+=2; break; case _blk: - util::stream_format(stream, "%-5s$%04X $%04X $%04X", token[opc], RDWORD(PC), RDWORD(PC+2), RDWORD(PC+4)); + util::stream_format(stream, "%-5s$%04X $%04X $%04X", token[opc], params.r16(PC), params.r16(PC+2), params.r16(PC+4)); PC+=6; break; case _zrl: - util::stream_format(stream, "%-5s$%02X $%04X", token[opc], RDBYTE(PC), (PC + 2 + (signed char)RDBYTE(PC+1)) & 0xffff); + util::stream_format(stream, "%-5s$%02X $%04X", token[opc], params.r8(PC), (PC + 2 + (signed char)params.r8(PC+1)) & 0xffff); PC+=2; break; case _imz: - util::stream_format(stream, "%-5s#$%02X $%02X", token[opc], RDBYTE(PC), RDBYTE(PC+1)); + util::stream_format(stream, "%-5s#$%02X $%02X", token[opc], params.r8(PC), params.r8(PC+1)); PC+=2; break; case _izx: - util::stream_format(stream, "%-5s#$%02X $%02X,x", token[opc], RDBYTE(PC), RDBYTE(PC+1)); + util::stream_format(stream, "%-5s#$%02X $%02X,x", token[opc], params.r8(PC), params.r8(PC+1)); PC+=2; break; case _ima: - util::stream_format(stream, "%-5s#$%02X $%04X", token[opc], RDBYTE(PC), RDWORD(PC+1)); + util::stream_format(stream, "%-5s#$%02X $%04X", token[opc], params.r8(PC), params.r16(PC+1)); PC+=3; break; case _imx: - util::stream_format(stream, "%-5s#$%02X $%04X,x", token[opc], RDBYTE(PC), RDWORD(PC+1)); + util::stream_format(stream, "%-5s#$%02X $%04X,x", token[opc], params.r8(PC), params.r16(PC+1)); PC+=3; break; default: util::stream_format(stream, "%-5s$%02X", token[opc], OP >> 1); } - return (PC - pc) | flags | DASMFLAG_SUPPORTED; + return (PC - pc) | flags | SUPPORTED; } diff --git a/src/devices/cpu/h6280/6280dasm.h b/src/devices/cpu/h6280/6280dasm.h new file mode 100644 index 00000000000..5186720dfa8 --- /dev/null +++ b/src/devices/cpu/h6280/6280dasm.h @@ -0,0 +1,90 @@ +// license:BSD-3-Clause +// copyright-holders:Bryan McPhail +/***************************************************************************** + + 6280dasm.c Hudsonsoft Hu6280 (HuC6280/Hu6280a) disassembler + + Copyright Bryan McPhail, mish@tendril.co.uk + + This source code is based (with permission!) on the 6502 emulator by + Juergen Buchmueller. It is released as part of the Mame emulator project. + Let me know if you intend to use this code in any other project. + + + Notes relating to Mame: + + The dasm window shows 'real' memory, as executed by the cpu + The data windows show 'physical' memory, as defined in the memory map + +******************************************************************************/ + +#ifndef MAME_CPU_H6280_6280DASM_H +#define MAME_CPU_H6280_6280DASM_H + +#pragma once + +class h6280_disassembler : public util::disasm_interface +{ +public: + h6280_disassembler() = default; + virtual ~h6280_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum addr_mode { + _non=0, /* no additional arguments */ + _acc, /* accumulator */ + _imp, /* implicit */ + _imm, /* immediate */ + _abs, /* absolute */ + _zpg, /* zero page */ + _zpx, /* zero page + X */ + _zpy, /* zero page + Y */ + _zpi, /* zero page indirect */ + _abx, /* absolute + X */ + _aby, /* absolute + Y */ + _rel, /* relative */ + _idx, /* zero page pre indexed */ + _idy, /* zero page post indexed */ + _ind, /* indirect */ + _iax, /* indirect + X */ + _blk, /* block */ + _zrl, /* zero page relative */ + _imz, /* immediate, zero page */ + _izx, /* immediate, zero page + X */ + _ima, /* immediate, absolute */ + _imx /* immediate, absolute + X */ + }; + + enum opcodes { + /* 6502 opcodes */ + _adc=0,_and, _asl, _bcc, _bcs, _beq, _bit, _bmi, + _bne, _bpl, _brk, _bvc, _bvs, _clc, _cld, _cli, + _clv, _cmp, _cpx, _cpy, _dec, _dex, _dey, _eor, + _inc, _inx, _iny, _jmp, _jsr, _lda, _ldx, _ldy, + _lsr, _nop, _ora, _pha, _php, _pla, _plp, _rol, + _ror, _rti, _rts, _sbc, _sec, _sed, _sei, _sta, + _stx, _sty, _tax, _tay, _tsx, _txa, _txs, _tya, + _ill, + + /* Hu6280 extensions */ + _bra, _stz, _trb, _tsb, _dea, _ina, _sax, _bsr, + _phx, _phy, _plx, _ply, _csh, _csl, _tam, _tma, + _cla, _cly, _clx, _st0, _st1, _st2, _tst, _set, + _tdd, _tia, _tii, _tin, _tai, _say, _sxy, + + _sm0, _sm1, _sm2, _sm3, _sm4, _sm5, _sm6, _sm7, + _rm0, _rm1, _rm2, _rm3, _rm4, _rm5, _rm6, _rm7, + + _bs0, _bs1, _bs2, _bs3, _bs4, _bs5, _bs6, _bs7, + _br0, _br1, _br2, _br3, _br4, _br5, _br6, _br7 + }; + + static const char *const token[]; + static const unsigned char op6280[512]; + +}; + +#endif diff --git a/src/devices/cpu/h6280/h6280.cpp b/src/devices/cpu/h6280/h6280.cpp index 4c5091b502e..8922bac892e 100644 --- a/src/devices/cpu/h6280/h6280.cpp +++ b/src/devices/cpu/h6280/h6280.cpp @@ -112,6 +112,7 @@ #include "emu.h" #include "h6280.h" +#include "6280dasm.h" #include "debugger.h" /* 6280 flags */ @@ -2220,36 +2221,13 @@ void h6280_device::state_string_export(const device_state_entry &entry, std::str //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t h6280_device::disasm_min_opcode_bytes() const -{ - return 1; -} - - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t h6280_device::disasm_max_opcode_bytes() const -{ - return 7; -} - - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t h6280_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *h6280_device::create_disassembler() { - extern CPU_DISASSEMBLE( h6280 ); - return CPU_DISASSEMBLE_NAME(h6280)(this, stream, pc, oprom, opram, options); + return new h6280_disassembler; } diff --git a/src/devices/cpu/h6280/h6280.h b/src/devices/cpu/h6280/h6280.h index dc6a3ddb47f..6ac69b3100b 100644 --- a/src/devices/cpu/h6280/h6280.h +++ b/src/devices/cpu/h6280/h6280.h @@ -89,9 +89,7 @@ protected: virtual bool memory_translate(int spacenum, int intention, offs_t &address) override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // device_state_interface overrides virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; diff --git a/src/devices/cpu/h8/h8.cpp b/src/devices/cpu/h8/h8.cpp index 516c2253496..078e89c31d1 100644 --- a/src/devices/cpu/h8/h8.cpp +++ b/src/devices/cpu/h8/h8.cpp @@ -14,6 +14,7 @@ #include "h8.h" #include "h8_dma.h" #include "h8_dtc.h" +#include "h8d.h" h8_device::h8_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock, bool mode_a16, address_map_delegate map_delegate) : cpu_device(mconfig, type, tag, owner, clock), @@ -324,256 +325,6 @@ void h8_device::state_string_export(const device_state_entry &entry, std::string } } - -uint32_t h8_device::disasm_min_opcode_bytes() const -{ - return 2; -} - -uint32_t h8_device::disasm_max_opcode_bytes() const -{ - return 10; -} - -void h8_device::disassemble_am(std::ostream &stream, int am, offs_t pc, const uint8_t *oprom, uint32_t opcode, int slot, int offset) -{ - static const char *const r8_names[16] = { - "r0h", "r1h", "r2h", "r3h", "r4h", "r5h", "r6h", "r7h", - "r0l", "r1l", "r2l", "r3l", "r4l", "r5l", "r6l", "r7l" - }; - - static const char *const r16_names[16] = { - "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", - "e0", "e1", "e2", "e3", "e4", "e5", "e6", "e7", - }; - - static const char *const r32_names[8] = { - "er0", "er1", "er2", "er3", "er4", "er5", "er6", "sp", - }; - - switch(am) { - case DASM_r8l: - util::stream_format(stream, "%s", r8_names[opcode & 15]); - break; - - case DASM_r8h: - util::stream_format(stream, "%s", r8_names[(opcode >> 4) & 15]); - break; - - case DASM_r8u: - util::stream_format(stream, "%s", r8_names[(opcode >> 8) & 15]); - break; - - case DASM_r16l: - util::stream_format(stream, "%s", r16_names[opcode & 15]); - break; - - case DASM_r16h: - util::stream_format(stream, "%s", r16_names[(opcode >> 4) & 15]); - break; - - case DASM_r32l: - util::stream_format(stream, "%s", r32_names[opcode & 7]); - break; - - case DASM_r32h: - util::stream_format(stream, "%s", r32_names[(opcode >> 4) & 7]); - break; - - case DASM_r16ih: - util::stream_format(stream, "@%s", r16_names[(opcode >> 4) & 7]); - break; - - case DASM_r16ihh: - util::stream_format(stream, "@%s", r16_names[(opcode >> 20) & 7]); - break; - - case DASM_pr16h: - util::stream_format(stream, "@-%s", r16_names[(opcode >> 4) & 7]); - break; - - case DASM_r16ph: - util::stream_format(stream, "@%s+", r16_names[(opcode >> 4) & 7]); - break; - - case DASM_r16d16h: - util::stream_format(stream, "@(%x, %s)", (oprom[offset-2] << 8) | oprom[offset-1], r16_names[(opcode >> 4) & 7]); - break; - - case DASM_r32ih: - util::stream_format(stream, "@%s", r32_names[(opcode >> 4) & 7]); - break; - - case DASM_r32ihh: - util::stream_format(stream, "@%s", r32_names[(opcode >> 20) & 7]); - break; - - case DASM_pr32h: - util::stream_format(stream, "@-%s", r32_names[(opcode >> 4) & 7]); - break; - - case DASM_r32pl: - util::stream_format(stream, "@%s+", r32_names[opcode & 7]); - break; - - case DASM_r32ph: - util::stream_format(stream, "@%s+", r32_names[(opcode >> 4) & 7]); - break; - - case DASM_r32d16h: - util::stream_format(stream, "@(%x, %s)", (oprom[offset-2] << 8) | oprom[offset-1], r32_names[(opcode >> 4) & 7]); - break; - - case DASM_r32d32hh: - util::stream_format(stream, "@(%x, %s)", (oprom[offset-4] << 24) | (oprom[offset-3] << 16) | (oprom[offset-2] << 8) | oprom[offset-1], r32_names[(opcode >> 20) & 7]); - break; - - case DASM_psp: - util::stream_format(stream, "@-sp"); - break; - - case DASM_spp: - util::stream_format(stream, "@sp+"); - break; - - case DASM_r32n2l: - util::stream_format(stream, "%s-%s", r32_names[opcode & 6], r32_names[(opcode & 6) + 1]); - break; - - case DASM_r32n3l: - util::stream_format(stream, "%s-%s", r32_names[opcode & 4], r32_names[(opcode & 4) + 2]); - break; - - case DASM_r32n4l: - util::stream_format(stream, "%s-%s", r32_names[opcode & 4], r32_names[(opcode & 4) + 3]); - break; - - case DASM_abs8: - util::stream_format(stream, "@%08x", 0xffffff00 | oprom[1]); - break; - - case DASM_abs16: - if(offset >= 6) - util::stream_format(stream, "@%08x", int16_t((oprom[offset-4] << 8) | oprom[offset-3])); - else - util::stream_format(stream, "@%08x", int16_t((oprom[offset-2] << 8) | oprom[offset-1])); - break; - - case DASM_abs32: - if(slot == 3) - util::stream_format(stream, "@%08x", (oprom[offset-6] << 24) | (oprom[offset-5] << 16) | (oprom[offset-4] << 8) | oprom[offset-3]); - else - util::stream_format(stream, "@%08x", (oprom[offset-4] << 24) | (oprom[offset-3] << 16) | (oprom[offset-2] << 8) | oprom[offset-1]); - break; - - case DASM_abs8i: - util::stream_format(stream, "@%02x", oprom[1]); - break; - - case DASM_abs16e: - util::stream_format(stream, "%04x", (oprom[2] << 8) | oprom[3]); - break; - - case DASM_abs24e: - util::stream_format(stream, "%08x", (oprom[1] << 16) | (oprom[2] << 8) | oprom[3]); - break; - - case DASM_rel8: - util::stream_format(stream, "%08x", pc + 2 + int8_t(oprom[1])); - break; - - case DASM_rel16: - util::stream_format(stream, "%08x", pc + 4 + int16_t((oprom[2] << 8) | oprom[3])); - break; - - case DASM_one: - util::stream_format(stream, "#1"); - break; - - case DASM_two: - util::stream_format(stream, "#2"); - break; - - case DASM_four: - util::stream_format(stream, "#4"); - break; - - case DASM_imm2: - util::stream_format(stream, "#%x", (opcode >> 4) & 3); - break; - - case DASM_imm3: - util::stream_format(stream, "#%x", (opcode >> 4) & 7); - break; - - case DASM_imm8: - util::stream_format(stream, "#%02x", oprom[1]); - break; - - case DASM_imm16: - util::stream_format(stream, "#%04x", (oprom[2] << 8) | oprom[3]); - break; - - case DASM_imm32: - util::stream_format(stream, "#%08x", (oprom[2] << 16) | (oprom[3] << 16) | (oprom[4] << 8) | oprom[5]); - break; - - case DASM_ccr: - util::stream_format(stream, "ccr"); - break; - - case DASM_exr: - util::stream_format(stream, "exr"); - break; - - case DASM_macl: - util::stream_format(stream, "macl"); - break; - - case DASM_mach: - util::stream_format(stream, "mach"); - break; - - default: - util::stream_format(stream, "<%d>", am); - break; - } -} - -offs_t h8_device::disassemble_generic(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options, const disasm_entry *table) -{ - uint32_t slot[5]; - slot[0] = (oprom[0] << 8) | oprom[1]; - slot[1] = (oprom[0] << 24) | (oprom[1] << 16) | (oprom[2] << 8) | oprom[3]; - slot[2] = (oprom[0] << 24) | (oprom[1] << 16) | (oprom[4] << 8) | oprom[5]; - slot[3] = (oprom[0] << 24) | (oprom[1] << 16) | (oprom[6] << 8) | oprom[7]; - slot[4] = (oprom[2] << 24) | (oprom[3] << 16) | (oprom[4] << 8) | oprom[5]; - - int inst; - for(inst=0;; inst++) { - const disasm_entry &e = table[inst]; - if((slot[e.slot] & e.mask) == e.val && (slot[0] & e.mask0) == e.val0) - break; - } - const disasm_entry &e = table[inst]; - stream << e.opcode; - - if(e.am1 != DASM_none) { - stream << ' '; - disassemble_am(stream, e.am1, pc, oprom, slot[e.slot], e.slot, e.flags & DASMFLAG_LENGTHMASK); - } - if(e.am2 != DASM_none) { - stream << ", "; - disassemble_am(stream, e.am2, pc, oprom, slot[e.slot], e.slot, e.flags & DASMFLAG_LENGTHMASK); - } - return e.flags | DASMFLAG_SUPPORTED; -} - -offs_t h8_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) -{ - return disassemble_generic(stream, pc, oprom, opram, options, disasm_entries); -} - uint16_t h8_device::read16i(uint32_t adr) { icount--; @@ -1592,4 +1343,9 @@ void h8_device::set_nz32(uint32_t v) CCR |= F_N; } +util::disasm_interface *h8_device::create_disassembler() +{ + return new h8_disassembler; +} + #include "cpu/h8/h8.hxx" diff --git a/src/devices/cpu/h8/h8.h b/src/devices/cpu/h8/h8.h index 3df33f8de1b..920d71c7663 100644 --- a/src/devices/cpu/h8/h8.h +++ b/src/devices/cpu/h8/h8.h @@ -72,15 +72,6 @@ public: bool access_is_dma() const { return inst_state == STATE_DMA || inst_state == STATE_DTC; } protected: - struct disasm_entry { - int slot; - uint32_t val, mask; - uint16_t val0, mask0; - const char *opcode; - int am1, am2; - offs_t flags; - }; - enum { F_I = 0x80, F_UI = 0x40, @@ -96,64 +87,6 @@ protected: EXR_I = 0x07 }; - enum { - DASM_none, /* no additional arguments */ - - DASM_r8l, /* 8-bits register in bits 0-3 */ - DASM_r8h, /* 8-bits register in bits 4-7 */ - DASM_r8u, /* 8-bits register in bits 8-15 */ - DASM_r16l, /* 16-bits register in bits 0-3 */ - DASM_r16h, /* 16-bits register in bits 4-7 */ - DASM_r32l, /* 32-bits register in bits 0-3 */ - DASM_r32h, /* 32-bits register in bits 4-7 */ - - DASM_r16ih, /* indexed through 16-bits register in bits 4-6 */ - DASM_r16ihh, /* indexed through 16-bits register in bits 4-6 in 4-bytes instruction */ - DASM_pr16h, /* indexed through predecremented 16-bits register in bits 4-6 */ - DASM_r16ph, /* indexed through postincremented 16-bits register in bits 4-6 */ - DASM_r16d16h, /* indexed through 16-bits register in bits 4-6 with 16-bits displacement at end of instruction */ - - DASM_r32ih, /* indexed through 32-bits register in bits 4-6 */ - DASM_r32ihh, /* indexed through 32-bits register in bits 4-6 in 4-bytes instruction */ - DASM_pr32h, /* indexed through predecremented 32-bits register in bits 4-6 */ - DASM_r32pl, /* indexed through postincremented 32-bits register in bits 0-2 */ - DASM_r32ph, /* indexed through postincremented 32-bits register in bits 4-6 */ - DASM_r32d16h, /* indexed through 32-bits register in bits 4-6 with 16-bits displacement at end of instruction */ - DASM_r32d32hh, /* indexed through 32-bits register in bits 20-22 with 32-bits displacement at end of instruction */ - - DASM_psp, /* indexed through predecremented stack pointer */ - DASM_spp, /* indexed through postincremented stack pointer */ - - DASM_r32n2l, /* Block of 2 registers */ - DASM_r32n3l, /* Block of 3 registers */ - DASM_r32n4l, /* Block of 4 registers */ - - DASM_abs8, /* 8-bit address present at +1 */ - DASM_abs16, /* 16-bit address present at end of instruction */ - DASM_abs32, /* 32-bit address present at end of instruction */ - DASM_abs8i, /* 8-bit indirect jump address present at +1 */ - DASM_abs16e, /* 16-bit jump address present at +2 */ - DASM_abs24e, /* 24-bit jump address present at +1 */ - - DASM_rel8, /* 8-bit pc-relative jump address at +1, offset=2 */ - DASM_rel16, /* 16-bit pc-relative jump address at +2, offset=4 */ - - DASM_one, /* immediate value 1 */ - DASM_two, /* immediate value 2 */ - DASM_four, /* immediate value 4 */ - - DASM_imm2, /* 2-bit immediate in bits 4-5 (trapa) */ - DASM_imm3, /* 3-bit immediate in bits 4-6 (bit selection */ - DASM_imm8, /* 8-bit immediate at +1 */ - DASM_imm16, /* 16-bit immediate at +2 */ - DASM_imm32, /* 32-bit immediate at +2 */ - - DASM_ccr, /* internal register ccr */ - DASM_exr, /* internal register exr */ - DASM_macl, /* internal register macl */ - DASM_mach /* internal register mach */ - }; - h8_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock, bool mode_a16, address_map_delegate map_delegate); // device-level overrides @@ -175,9 +108,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; address_space_config program_config, io_config; address_space *program, *io; @@ -208,11 +139,6 @@ protected: int irq_level, taken_irq_level; bool irq_required, irq_nmi; - static const disasm_entry disasm_entries[]; - - offs_t disassemble_generic(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options, const disasm_entry *table); - void disassemble_am(std::ostream &stream, int am, offs_t pc, const uint8_t *oprom, uint32_t opcode, int slot, int offset); - virtual void do_exec_full(); virtual void do_exec_partial(); static void add_event(uint64_t &event_time, uint64_t new_event); diff --git a/src/devices/cpu/h8/h8d.cpp b/src/devices/cpu/h8/h8d.cpp new file mode 100644 index 00000000000..b157aedd3c7 --- /dev/null +++ b/src/devices/cpu/h8/h8d.cpp @@ -0,0 +1,262 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + h8d.h + + H8-300 base cpu emulation, disassembler + +***************************************************************************/ + +#include "emu.h" +#include "h8d.h" +#include "cpu/h8/h8d.hxx" + +h8_disassembler::h8_disassembler(const disasm_entry *_table) : table(_table) +{ +} + +h8_disassembler::h8_disassembler() : h8_disassembler(disasm_entries) +{ +} + +u32 h8_disassembler::opcode_alignment() const +{ + return 2; +} + +void h8_disassembler::disassemble_am(std::ostream &stream, int am, offs_t pc, const data_buffer &opcodes, u32 opcode, int slot, int offset) +{ + static const char *const r8_names[16] = { + "r0h", "r1h", "r2h", "r3h", "r4h", "r5h", "r6h", "r7h", + "r0l", "r1l", "r2l", "r3l", "r4l", "r5l", "r6l", "r7l" + }; + + static const char *const r16_names[16] = { + "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", + "e0", "e1", "e2", "e3", "e4", "e5", "e6", "e7", + }; + + static const char *const r32_names[8] = { + "er0", "er1", "er2", "er3", "er4", "er5", "er6", "sp", + }; + + offs_t epc = pc + offset; + + switch(am) { + case DASM_r8l: + util::stream_format(stream, "%s", r8_names[opcode & 15]); + break; + + case DASM_r8h: + util::stream_format(stream, "%s", r8_names[(opcode >> 4) & 15]); + break; + + case DASM_r8u: + util::stream_format(stream, "%s", r8_names[(opcode >> 8) & 15]); + break; + + case DASM_r16l: + util::stream_format(stream, "%s", r16_names[opcode & 15]); + break; + + case DASM_r16h: + util::stream_format(stream, "%s", r16_names[(opcode >> 4) & 15]); + break; + + case DASM_r32l: + util::stream_format(stream, "%s", r32_names[opcode & 7]); + break; + + case DASM_r32h: + util::stream_format(stream, "%s", r32_names[(opcode >> 4) & 7]); + break; + + case DASM_r16ih: + util::stream_format(stream, "@%s", r16_names[(opcode >> 4) & 7]); + break; + + case DASM_r16ihh: + util::stream_format(stream, "@%s", r16_names[(opcode >> 20) & 7]); + break; + + case DASM_pr16h: + util::stream_format(stream, "@-%s", r16_names[(opcode >> 4) & 7]); + break; + + case DASM_r16ph: + util::stream_format(stream, "@%s+", r16_names[(opcode >> 4) & 7]); + break; + + case DASM_r16d16h: + util::stream_format(stream, "@(%x, %s)", opcodes.r16(epc-2), r16_names[(opcode >> 4) & 7]); + break; + + case DASM_r32ih: + util::stream_format(stream, "@%s", r32_names[(opcode >> 4) & 7]); + break; + + case DASM_r32ihh: + util::stream_format(stream, "@%s", r32_names[(opcode >> 20) & 7]); + break; + + case DASM_pr32h: + util::stream_format(stream, "@-%s", r32_names[(opcode >> 4) & 7]); + break; + + case DASM_r32pl: + util::stream_format(stream, "@%s+", r32_names[opcode & 7]); + break; + + case DASM_r32ph: + util::stream_format(stream, "@%s+", r32_names[(opcode >> 4) & 7]); + break; + + case DASM_r32d16h: + util::stream_format(stream, "@(%x, %s)", opcodes.r16(epc-2), r32_names[(opcode >> 4) & 7]); + break; + + case DASM_r32d32hh: + util::stream_format(stream, "@(%x, %s)", opcodes.r32(epc-4), r32_names[(opcode >> 20) & 7]); + break; + + case DASM_psp: + util::stream_format(stream, "@-sp"); + break; + + case DASM_spp: + util::stream_format(stream, "@sp+"); + break; + + case DASM_r32n2l: + util::stream_format(stream, "%s-%s", r32_names[opcode & 6], r32_names[(opcode & 6) + 1]); + break; + + case DASM_r32n3l: + util::stream_format(stream, "%s-%s", r32_names[opcode & 4], r32_names[(opcode & 4) + 2]); + break; + + case DASM_r32n4l: + util::stream_format(stream, "%s-%s", r32_names[opcode & 4], r32_names[(opcode & 4) + 3]); + break; + + case DASM_abs8: + util::stream_format(stream, "@%08x", 0xffffff00 | opcodes.r8(pc+1)); + break; + + case DASM_abs16: + if(offset >= 6) + util::stream_format(stream, "@%08x", s16(opcodes.r16(epc-4))); + else + util::stream_format(stream, "@%08x", s16(opcodes.r16(epc-2))); + break; + + case DASM_abs32: + if(slot == 3) + util::stream_format(stream, "@%08x", opcodes.r32(epc-6)); + else + util::stream_format(stream, "@%08x", opcodes.r32(epc-4)); + break; + + case DASM_abs8i: + util::stream_format(stream, "@%02x", opcodes.r8(pc+1)); + break; + + case DASM_abs16e: + util::stream_format(stream, "%04x", opcodes.r16(pc+2)); + break; + + case DASM_abs24e: + util::stream_format(stream, "%08x", opcodes.r32(pc) & 0xffffff); + break; + + case DASM_rel8: + util::stream_format(stream, "%08x", pc + 2 + s8(opcodes.r8(pc+1))); + break; + + case DASM_rel16: + util::stream_format(stream, "%08x", pc + 4 + s16(opcodes.r16(pc+2))); + break; + + case DASM_one: + util::stream_format(stream, "#1"); + break; + + case DASM_two: + util::stream_format(stream, "#2"); + break; + + case DASM_four: + util::stream_format(stream, "#4"); + break; + + case DASM_imm2: + util::stream_format(stream, "#%x", (opcode >> 4) & 3); + break; + + case DASM_imm3: + util::stream_format(stream, "#%x", (opcode >> 4) & 7); + break; + + case DASM_imm8: + util::stream_format(stream, "#%02x", opcodes.r8(pc+1)); + break; + + case DASM_imm16: + util::stream_format(stream, "#%04x", opcodes.r16(pc+2)); + break; + + case DASM_imm32: + util::stream_format(stream, "#%08x", opcodes.r32(pc+2)); + break; + + case DASM_ccr: + util::stream_format(stream, "ccr"); + break; + + case DASM_exr: + util::stream_format(stream, "exr"); + break; + + case DASM_macl: + util::stream_format(stream, "macl"); + break; + + case DASM_mach: + util::stream_format(stream, "mach"); + break; + + default: + util::stream_format(stream, "<%d>", am); + break; + } +} + +offs_t h8_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + u32 slot[5]; + slot[0] = opcodes.r16(pc); + slot[1] = opcodes.r32(pc); + slot[2] = (opcodes.r16(pc) << 16) | opcodes.r16(pc+4); + slot[3] = (opcodes.r16(pc) << 16) | opcodes.r16(pc+6); + slot[4] = opcodes.r32(pc+2); + + int inst; + for(inst=0;; inst++) { + const disasm_entry &e = table[inst]; + if((slot[e.slot] & e.mask) == e.val && (slot[0] & e.mask0) == e.val0) + break; + } + const disasm_entry &e = table[inst]; + stream << e.opcode; + + if(e.am1 != DASM_none) { + stream << ' '; + disassemble_am(stream, e.am1, pc, opcodes, slot[e.slot], e.slot, e.flags & LENGTHMASK); + } + if(e.am2 != DASM_none) { + stream << ", "; + disassemble_am(stream, e.am2, pc, opcodes, slot[e.slot], e.slot, e.flags & LENGTHMASK); + } + return e.flags | SUPPORTED; +} diff --git a/src/devices/cpu/h8/h8d.h b/src/devices/cpu/h8/h8d.h new file mode 100644 index 00000000000..65ba1d7fd97 --- /dev/null +++ b/src/devices/cpu/h8/h8d.h @@ -0,0 +1,101 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + h8d.h + + H8-300 base cpu emulation, disassembler + +***************************************************************************/ + +#ifndef MAME_CPU_H8_H8D_H +#define MAME_CPU_H8_H8D_H + +#pragma once + +class h8_disassembler : public util::disasm_interface +{ +protected: + struct disasm_entry { + int slot; + u32 val, mask; + u16 val0, mask0; + const char *opcode; + int am1, am2; + offs_t flags; + }; + +public: + h8_disassembler(const disasm_entry *_table); + h8_disassembler(); + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +protected: + enum { + DASM_none, /* no additional arguments */ + + DASM_r8l, /* 8-bits register in bits 0-3 */ + DASM_r8h, /* 8-bits register in bits 4-7 */ + DASM_r8u, /* 8-bits register in bits 8-15 */ + DASM_r16l, /* 16-bits register in bits 0-3 */ + DASM_r16h, /* 16-bits register in bits 4-7 */ + DASM_r32l, /* 32-bits register in bits 0-3 */ + DASM_r32h, /* 32-bits register in bits 4-7 */ + + DASM_r16ih, /* indexed through 16-bits register in bits 4-6 */ + DASM_r16ihh, /* indexed through 16-bits register in bits 4-6 in 4-bytes instruction */ + DASM_pr16h, /* indexed through predecremented 16-bits register in bits 4-6 */ + DASM_r16ph, /* indexed through postincremented 16-bits register in bits 4-6 */ + DASM_r16d16h, /* indexed through 16-bits register in bits 4-6 with 16-bits displacement at end of instruction */ + + DASM_r32ih, /* indexed through 32-bits register in bits 4-6 */ + DASM_r32ihh, /* indexed through 32-bits register in bits 4-6 in 4-bytes instruction */ + DASM_pr32h, /* indexed through predecremented 32-bits register in bits 4-6 */ + DASM_r32pl, /* indexed through postincremented 32-bits register in bits 0-2 */ + DASM_r32ph, /* indexed through postincremented 32-bits register in bits 4-6 */ + DASM_r32d16h, /* indexed through 32-bits register in bits 4-6 with 16-bits displacement at end of instruction */ + DASM_r32d32hh, /* indexed through 32-bits register in bits 20-22 with 32-bits displacement at end of instruction */ + + DASM_psp, /* indexed through predecremented stack pointer */ + DASM_spp, /* indexed through postincremented stack pointer */ + + DASM_r32n2l, /* Block of 2 registers */ + DASM_r32n3l, /* Block of 3 registers */ + DASM_r32n4l, /* Block of 4 registers */ + + DASM_abs8, /* 8-bit address present at +1 */ + DASM_abs16, /* 16-bit address present at end of instruction */ + DASM_abs32, /* 32-bit address present at end of instruction */ + DASM_abs8i, /* 8-bit indirect jump address present at +1 */ + DASM_abs16e, /* 16-bit jump address present at +2 */ + DASM_abs24e, /* 24-bit jump address present at +1 */ + + DASM_rel8, /* 8-bit pc-relative jump address at +1, offset=2 */ + DASM_rel16, /* 16-bit pc-relative jump address at +2, offset=4 */ + + DASM_one, /* immediate value 1 */ + DASM_two, /* immediate value 2 */ + DASM_four, /* immediate value 4 */ + + DASM_imm2, /* 2-bit immediate in bits 4-5 (trapa) */ + DASM_imm3, /* 3-bit immediate in bits 4-6 (bit selection */ + DASM_imm8, /* 8-bit immediate at +1 */ + DASM_imm16, /* 16-bit immediate at +2 */ + DASM_imm32, /* 32-bit immediate at +2 */ + + DASM_ccr, /* internal register ccr */ + DASM_exr, /* internal register exr */ + DASM_macl, /* internal register macl */ + DASM_mach /* internal register mach */ + }; + + void disassemble_am(std::ostream &stream, int am, offs_t pc, const data_buffer &opcodes, u32 opcode, int slot, int offset); + + const disasm_entry *table; + + static const disasm_entry disasm_entries[]; +}; + +#endif diff --git a/src/devices/cpu/h8/h8h.cpp b/src/devices/cpu/h8/h8h.cpp index 37756da3d12..97b945d8166 100644 --- a/src/devices/cpu/h8/h8h.cpp +++ b/src/devices/cpu/h8/h8h.cpp @@ -2,6 +2,7 @@ // copyright-holders:Olivier Galibert #include "emu.h" #include "h8h.h" +#include "h8hd.h" h8h_device::h8h_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock, address_map_delegate map_delegate) : h8_device(mconfig, type, tag, owner, clock, false, map_delegate) @@ -10,9 +11,9 @@ h8h_device::h8h_device(const machine_config &mconfig, device_type type, const ch mode_advanced = true; } -offs_t h8h_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *h8h_device::create_disassembler() { - return disassemble_generic(stream, pc, oprom, opram, options, disasm_entries); + return new h8h_disassembler; } #include "cpu/h8/h8h.hxx" diff --git a/src/devices/cpu/h8/h8h.h b/src/devices/cpu/h8/h8h.h index 460ddcefc3a..4c8c226a516 100644 --- a/src/devices/cpu/h8/h8h.h +++ b/src/devices/cpu/h8/h8h.h @@ -20,11 +20,9 @@ class h8h_device : public h8_device { protected: - static const disasm_entry disasm_entries[]; - h8h_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock, address_map_delegate map_delegate); - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void do_exec_full() override; virtual void do_exec_partial() override; diff --git a/src/devices/cpu/h8/h8hd.cpp b/src/devices/cpu/h8/h8hd.cpp new file mode 100644 index 00000000000..c6cb3238784 --- /dev/null +++ b/src/devices/cpu/h8/h8hd.cpp @@ -0,0 +1,17 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + h8d.h + + H8-300H base cpu emulation, disassembler + +***************************************************************************/ + +#include "emu.h" +#include "h8hd.h" +#include "cpu/h8/h8hd.hxx" + +h8h_disassembler::h8h_disassembler() : h8_disassembler(disasm_entries) +{ +} diff --git a/src/devices/cpu/h8/h8hd.h b/src/devices/cpu/h8/h8hd.h new file mode 100644 index 00000000000..5123ee32563 --- /dev/null +++ b/src/devices/cpu/h8/h8hd.h @@ -0,0 +1,28 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + h8hd.h + + H8-300H base cpu emulation, disassembler + +***************************************************************************/ + +#ifndef MAME_CPU_H8_H8HD_H +#define MAME_CPU_H8_H8HD_H + +#pragma once + +#include "h8d.h" + +class h8h_disassembler : public h8_disassembler +{ +public: + h8h_disassembler(); + virtual ~h8h_disassembler() = default; + +protected: + static const disasm_entry disasm_entries[]; +}; + +#endif diff --git a/src/devices/cpu/h8/h8make.py b/src/devices/cpu/h8/h8make.py index e5aee1dbb96..99883e92c2a 100644 --- a/src/devices/cpu/h8/h8make.py +++ b/src/devices/cpu/h8/h8make.py @@ -5,7 +5,7 @@ from __future__ import print_function USAGE = """ Usage: -%s h8.lst h8.inc (type = o/h/s20/s26) +%s h8.lst h8.inc (mode = s/d, type = o/h/s20/s26) """ import sys @@ -21,14 +21,23 @@ def name_to_type(name): sys.stderr.write("Unknown chip type name %s\n" % name) sys.exit(1) -def type_to_device(dtype): - if dtype == 0: - return "h8_device" - if dtype == 1: - return "h8h_device" - if dtype == 2: - return "h8s2000_device" - return "h8s2600_device" +def type_to_device(dtype, mode): + if mode == 's': + if dtype == 0: + return "h8_device" + if dtype == 1: + return "h8h_device" + if dtype == 2: + return "h8s2000_device" + return "h8s2600_device" + else: + if dtype == 0: + return "h8_disassembler" + if dtype == 1: + return "h8h_disassembler" + if dtype == 2: + return "h8s2000_disassembler" + return "h8s2600_disassembler" def hexsplit(str): res = [] @@ -182,9 +191,9 @@ class Opcode: size = len(self.val) + 2*self.skip + 2*self.extra_words if self.name == "jsr" or self.name == "bsr": - flags = "%d | DASMFLAG_STEP_OVER" % size + flags = "%d | STEP_OVER" % size elif self.name == "rts" or self.name == "rte": - flags = "%d | DASMFLAG_STEP_OUT" % size + flags = "%d | STEP_OUT" % size else: flags = "%d" % size @@ -445,28 +454,31 @@ class OpcodeList: print("}", file=f) def main(argv): - if len(argv) != 4: + if len(argv) != 5: print(USAGE % argv[0]) return 1 - dtype = name_to_type(argv[2]) - dname = type_to_device(dtype) + mode = argv[2] + dtype = name_to_type(argv[3]) + dname = type_to_device(dtype, mode) opcodes = OpcodeList(argv[1], dtype) try: - f = open(argv[3], "w") + f = open(argv[4], "w") except Exception: err = sys.exc_info()[1] - sys.stderr.write("cannot write file %s [%s]\n" % (argv[3], err)) + sys.stderr.write("cannot write file %s [%s]\n" % (argv[4], err)) sys.exit(1) - opcodes.build_dispatch() - opcodes.save_dasm(f, dname) - opcodes.save_opcodes(f, dname) - if dtype == 0: - opcodes.save_dispatch(f, dname) - opcodes.save_exec(f, dname, dtype, "full") - opcodes.save_exec(f, dname, dtype, "partial") + if mode == 's': + opcodes.build_dispatch() + opcodes.save_opcodes(f, dname) + if dtype == 0: + opcodes.save_dispatch(f, dname) + opcodes.save_exec(f, dname, dtype, "full") + opcodes.save_exec(f, dname, dtype, "partial") + else: + opcodes.save_dasm(f, dname) f.close() # ====================================================================== diff --git a/src/devices/cpu/h8/h8s2000.cpp b/src/devices/cpu/h8/h8s2000.cpp index 2af090f5867..95e10cc2c50 100644 --- a/src/devices/cpu/h8/h8s2000.cpp +++ b/src/devices/cpu/h8/h8s2000.cpp @@ -2,6 +2,7 @@ // copyright-holders:Olivier Galibert #include "emu.h" #include "h8s2000.h" +#include "h8s2000d.h" h8s2000_device::h8s2000_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock, address_map_delegate map_delegate) : h8h_device(mconfig, type, tag, owner, clock, map_delegate) @@ -9,9 +10,9 @@ h8s2000_device::h8s2000_device(const machine_config &mconfig, device_type type, has_exr = true; } -offs_t h8s2000_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *h8s2000_device::create_disassembler() { - return disassemble_generic(stream, pc, oprom, opram, options, disasm_entries); + return new h8s2000_disassembler; } #include "cpu/h8/h8s2000.hxx" diff --git a/src/devices/cpu/h8/h8s2000.h b/src/devices/cpu/h8/h8s2000.h index e28e640baec..8aa195df7ad 100644 --- a/src/devices/cpu/h8/h8s2000.h +++ b/src/devices/cpu/h8/h8s2000.h @@ -24,9 +24,7 @@ class h8s2000_device : public h8h_device { protected: h8s2000_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock, address_map_delegate map_delegate); - static const disasm_entry disasm_entries[]; - - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void do_exec_full() override; virtual void do_exec_partial() override; diff --git a/src/devices/cpu/h8/h8s2000d.cpp b/src/devices/cpu/h8/h8s2000d.cpp new file mode 100644 index 00000000000..1e0b3830f53 --- /dev/null +++ b/src/devices/cpu/h8/h8s2000d.cpp @@ -0,0 +1,17 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + h8d.h + + H8S-2000 base cpu emulation, disassembler + +***************************************************************************/ + +#include "emu.h" +#include "h8s2000d.h" +#include "cpu/h8/h8s2000d.hxx" + +h8s2000_disassembler::h8s2000_disassembler() : h8_disassembler(disasm_entries) +{ +} diff --git a/src/devices/cpu/h8/h8s2000d.h b/src/devices/cpu/h8/h8s2000d.h new file mode 100644 index 00000000000..cf6bc5bfa9e --- /dev/null +++ b/src/devices/cpu/h8/h8s2000d.h @@ -0,0 +1,28 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + h8s2000d.h + + H8S-2000 base cpu emulation, disassembler + +***************************************************************************/ + +#ifndef MAME_CPU_H8_H8S2000D_H +#define MAME_CPU_H8_H8S2000D_H + +#pragma once + +#include "h8d.h" + +class h8s2000_disassembler : public h8_disassembler +{ +public: + h8s2000_disassembler(); + virtual ~h8s2000_disassembler() = default; + +protected: + static const disasm_entry disasm_entries[]; +}; + +#endif diff --git a/src/devices/cpu/h8/h8s2600.cpp b/src/devices/cpu/h8/h8s2600.cpp index 188f879279d..171dfef2d9b 100644 --- a/src/devices/cpu/h8/h8s2600.cpp +++ b/src/devices/cpu/h8/h8s2600.cpp @@ -2,15 +2,16 @@ // copyright-holders:Olivier Galibert #include "emu.h" #include "h8s2600.h" +#include "h8s2600d.h" h8s2600_device::h8s2600_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock, address_map_delegate map_delegate) : h8s2000_device(mconfig, type, tag, owner, clock, map_delegate) { } -offs_t h8s2600_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *h8s2600_device::create_disassembler() { - return disassemble_generic(stream, pc, oprom, opram, options, disasm_entries); + return new h8s2600_disassembler; } #include "cpu/h8/h8s2600.hxx" diff --git a/src/devices/cpu/h8/h8s2600.h b/src/devices/cpu/h8/h8s2600.h index 45b84bb2f8c..e3b4b7e44a9 100644 --- a/src/devices/cpu/h8/h8s2600.h +++ b/src/devices/cpu/h8/h8s2600.h @@ -20,11 +20,9 @@ class h8s2600_device : public h8s2000_device { protected: - static const disasm_entry disasm_entries[]; - h8s2600_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock, address_map_delegate map_delegate); - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void do_exec_full() override; virtual void do_exec_partial() override; diff --git a/src/devices/cpu/h8/h8s2600d.cpp b/src/devices/cpu/h8/h8s2600d.cpp new file mode 100644 index 00000000000..7e55784bed0 --- /dev/null +++ b/src/devices/cpu/h8/h8s2600d.cpp @@ -0,0 +1,17 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + h8d.h + + H8S-2600 base cpu emulation, disassembler + +***************************************************************************/ + +#include "emu.h" +#include "h8s2600d.h" +#include "cpu/h8/h8s2600d.hxx" + +h8s2600_disassembler::h8s2600_disassembler() : h8_disassembler(disasm_entries) +{ +} diff --git a/src/devices/cpu/h8/h8s2600d.h b/src/devices/cpu/h8/h8s2600d.h new file mode 100644 index 00000000000..3ee3fbfe133 --- /dev/null +++ b/src/devices/cpu/h8/h8s2600d.h @@ -0,0 +1,28 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + h8s2600d.h + + H8S-2600 base cpu emulation, disassembler + +***************************************************************************/ + +#ifndef MAME_CPU_H8_H8S2600D_H +#define MAME_CPU_H8_H8S2600D_H + +#pragma once + +#include "h8d.h" + +class h8s2600_disassembler : public h8_disassembler +{ +public: + h8s2600_disassembler(); + virtual ~h8s2600_disassembler() = default; + +protected: + static const disasm_entry disasm_entries[]; +}; + +#endif diff --git a/src/devices/cpu/hcd62121/hcd62121.cpp b/src/devices/cpu/hcd62121/hcd62121.cpp index 2c42e7881f6..efdb53ba2cd 100644 --- a/src/devices/cpu/hcd62121/hcd62121.cpp +++ b/src/devices/cpu/hcd62121/hcd62121.cpp @@ -21,6 +21,7 @@ TODO: #include "emu.h" #include "hcd62121.h" +#include "hcd62121d.h" #include "debugger.h" @@ -1751,9 +1752,7 @@ void hcd62121_cpu_device::execute_run() } while (m_icount > 0); } - -offs_t hcd62121_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, uint32_t options) +util::disasm_interface *hcd62121_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE(hcd62121); - return CPU_DISASSEMBLE_NAME(hcd62121)(this, stream, pc, oprom, opram, options); + return new hcd62121_disassembler; } diff --git a/src/devices/cpu/hcd62121/hcd62121.h b/src/devices/cpu/hcd62121/hcd62121.h index 13956e97d3b..1b7fb74feba 100644 --- a/src/devices/cpu/hcd62121/hcd62121.h +++ b/src/devices/cpu/hcd62121/hcd62121.h @@ -61,9 +61,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual u32 disasm_min_opcode_bytes() const override { return 1; } - virtual u32 disasm_max_opcode_bytes() const override { return 18; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; private: u8 read_op(); diff --git a/src/devices/cpu/hcd62121/hcd62121d.cpp b/src/devices/cpu/hcd62121/hcd62121d.cpp index 5e76b090782..2b7ea7b1150 100644 --- a/src/devices/cpu/hcd62121/hcd62121d.cpp +++ b/src/devices/cpu/hcd62121/hcd62121d.cpp @@ -2,49 +2,9 @@ // copyright-holders:Wilbert Pol #include "emu.h" +#include "hcd62121d.h" -enum -{ - ARG_NONE=0, /* no argument or unknown */ - ARG_REG, /* register */ - ARG_REGREG, /* register1, register2, or register2, register1 or register1, imm byte */ - ARG_IRG, /* register indirect */ - ARG_IRGREG, /* 2 register indirect */ - ARG_A16, /* 16bit address */ - ARG_A24, /* seg:address */ - ARG_F, /* flag register */ - ARG_CS, /* cs register */ - ARG_DS, /* ds register */ - ARG_SS, /* ss register */ - ARG_PC, /* program counter */ - ARG_SP, /* stack pointer */ - ARG_I8, /* immediate 8 bit value */ - ARG_I16, /* immediate 16 bit value */ - ARG_I64, /* immediate 64 bit value */ - ARG_I80, /* immediate 80 bit value */ - ARG_ILR, /* indirect last address register access */ - ARG_LAR, /* last address register */ - ARG_DSZ, /* dsize register? */ - ARG_OPT, /* OPTx (output) pins */ - ARG_PORT, /* PORTx (output) pins */ - ARG_TIM, /* timing related register? */ - ARG_KLO, /* KO1 - KO8 output lines */ - ARG_KHI, /* KO9 - KO14(?) output lines */ - ARG_KI, /* K input lines */ - ARG_S1, /* shift by 1 */ - ARG_S4, /* shift by 4 */ - ARG_S8, /* shift by 8 */ -}; - -struct hcd62121_dasm -{ - const char *str; - u8 arg1; - u8 arg2; -}; - - -static const hcd62121_dasm hcd62121_ops[256] = +const hcd62121_disassembler::dasm hcd62121_disassembler::ops[256] = { /* 0x00 */ { "sh?b", ARG_REG, ARG_S8 }, { "sh?w", ARG_REG, ARG_S8 }, @@ -207,30 +167,34 @@ static const hcd62121_dasm hcd62121_ops[256] = { "unFE?", ARG_NONE, ARG_NONE }, { "nop", ARG_NONE, ARG_NONE } }; +u32 hcd62121_disassembler::opcode_alignment() const +{ + return 1; +} -CPU_DISASSEMBLE(hcd62121) +offs_t hcd62121_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { u8 op; u8 op1; u8 op2; - u32 pos = 0; - const hcd62121_dasm *inst; + offs_t base_pc = pc; + const dasm *inst; - op = oprom[pos++]; + op = opcodes.r8(pc++); - inst = &hcd62121_ops[op]; + inst = &ops[op]; /* Special cases for shift and rotate instructions */ if (inst->arg2 == ARG_S4 || inst->arg2 == ARG_S8) - util::stream_format(stream, "%c%c%c%c ", inst->str[0], inst->str[1], (oprom[pos] & 0x80) ? 'r' : 'l', inst->str[3]); + util::stream_format(stream, "%c%c%c%c ", inst->str[0], inst->str[1], (opcodes.r8(pc) & 0x80) ? 'r' : 'l', inst->str[3]); else util::stream_format(stream, "%-8s", inst->str); switch(inst->arg1) { case ARG_REGREG: - op1 = oprom[pos++]; - op2 = oprom[pos++]; + op1 = opcodes.r8(pc++); + op2 = opcodes.r8(pc++); if (op1 & 0x80) { util::stream_format(stream, "r%02x,0x%02x", op1 & 0x7f, op2); @@ -244,12 +208,12 @@ CPU_DISASSEMBLE(hcd62121) } break; case ARG_REG: - util::stream_format(stream, "r%02x", oprom[pos++] & 0x7f); + util::stream_format(stream, "r%02x", opcodes.r8(pc++) & 0x7f); break; case ARG_IRGREG: /* bit 6 = direction. 0 - regular, 1 - reverse */ - op1 = oprom[pos++]; - op2 = oprom[pos++]; + op1 = opcodes.r8(pc++); + op2 = opcodes.r8(pc++); if (op1 & 0x80) { util::stream_format(stream, "(r%02x),0x%02x", 0x40 | (op1 & 0x3f), op2); @@ -264,7 +228,7 @@ CPU_DISASSEMBLE(hcd62121) break; case ARG_IRG: /* bit 6 = direction. 0 - regular, 1 - reverse */ - op1 = oprom[pos++]; + op1 = opcodes.r8(pc++); util::stream_format(stream, "(r%02x%s)", 0x40 | (op1 & 0x3f), (op1 & 0x40) ? ".r" : ""); break; case ARG_F: @@ -286,43 +250,43 @@ CPU_DISASSEMBLE(hcd62121) util::stream_format(stream, "SP"); break; case ARG_I8: - util::stream_format(stream, "0x%02x", oprom[pos++]); + util::stream_format(stream, "0x%02x", opcodes.r8(pc++)); break; case ARG_I16: case ARG_A16: - util::stream_format(stream, "0x%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); + util::stream_format(stream, "0x%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); break; case ARG_I64: - util::stream_format(stream, "0x%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); + util::stream_format(stream, "0x%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); break; case ARG_I80: - util::stream_format(stream, "0x%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); + util::stream_format(stream, "0x%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); break; case ARG_A24: - util::stream_format(stream, "0x%02x:", oprom[pos++]); - util::stream_format(stream, "0x%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); + util::stream_format(stream, "0x%02x:", opcodes.r8(pc++)); + util::stream_format(stream, "0x%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); break; case ARG_ILR: - op1 = oprom[pos++]; - op2 = oprom[pos++]; + op1 = opcodes.r8(pc++); + op2 = opcodes.r8(pc++); if ((op1 & 0x80) || (op2 & 0x80)) { if (op1 & 0x80) @@ -370,7 +334,7 @@ CPU_DISASSEMBLE(hcd62121) switch(inst->arg2) { case ARG_REG: - util::stream_format(stream, ",r%02x", oprom[pos++] & 0x7f); + util::stream_format(stream, ",r%02x", opcodes.r8(pc++) & 0x7f); break; case ARG_F: util::stream_format(stream, ",F"); @@ -391,43 +355,43 @@ CPU_DISASSEMBLE(hcd62121) util::stream_format(stream, ",SP"); break; case ARG_I8: - util::stream_format(stream, ",0x%02x", oprom[pos++]); + util::stream_format(stream, ",0x%02x", opcodes.r8(pc++)); break; case ARG_I16: - util::stream_format(stream, ",0x%02x", oprom[pos+1]); - util::stream_format(stream, "%02x", oprom[pos]); - pos += 2; + util::stream_format(stream, ",0x%02x", opcodes.r8(pc+1)); + util::stream_format(stream, "%02x", opcodes.r8(pc)); + pc += 2; break; case ARG_A16: - util::stream_format(stream, ",0x%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); + util::stream_format(stream, ",0x%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); break; case ARG_I64: - util::stream_format(stream, ",0x%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); + util::stream_format(stream, ",0x%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); break; case ARG_I80: - util::stream_format(stream, ",0x%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); + util::stream_format(stream, ",0x%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); break; case ARG_A24: - util::stream_format(stream, ",0x%02x:", oprom[pos++]); - util::stream_format(stream, "0x%02x", oprom[pos++]); - util::stream_format(stream, "%02x", oprom[pos++]); + util::stream_format(stream, ",0x%02x:", opcodes.r8(pc++)); + util::stream_format(stream, "0x%02x", opcodes.r8(pc++)); + util::stream_format(stream, "%02x", opcodes.r8(pc++)); break; case ARG_ILR: /* Implemented by ARG_ILR section for arg1 */ @@ -460,6 +424,6 @@ CPU_DISASSEMBLE(hcd62121) break; } - return pos | DASMFLAG_SUPPORTED; + return (pc - base_pc) | SUPPORTED; } diff --git a/src/devices/cpu/hcd62121/hcd62121d.h b/src/devices/cpu/hcd62121/hcd62121d.h new file mode 100644 index 00000000000..c03d10dd410 --- /dev/null +++ b/src/devices/cpu/hcd62121/hcd62121d.h @@ -0,0 +1,62 @@ +// license:BSD-3-Clause +// copyright-holders:Wilbert Pol + +#ifndef MAME_CPU_HCD62121_HCD62121D_H +#define MAME_CPU_HCD62121_HCD62121D_H + +#pragma once + +class hcd62121_disassembler : public util::disasm_interface +{ +public: + hcd62121_disassembler() = default; + virtual ~hcd62121_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + struct dasm + { + const char *str; + u8 arg1; + u8 arg2; + }; + + enum + { + ARG_NONE=0, /* no argument or unknown */ + ARG_REG, /* register */ + ARG_REGREG, /* register1, register2, or register2, register1 or register1, imm byte */ + ARG_IRG, /* register indirect */ + ARG_IRGREG, /* 2 register indirect */ + ARG_A16, /* 16bit address */ + ARG_A24, /* seg:address */ + ARG_F, /* flag register */ + ARG_CS, /* cs register */ + ARG_DS, /* ds register */ + ARG_SS, /* ss register */ + ARG_PC, /* program counter */ + ARG_SP, /* stack pointer */ + ARG_I8, /* immediate 8 bit value */ + ARG_I16, /* immediate 16 bit value */ + ARG_I64, /* immediate 64 bit value */ + ARG_I80, /* immediate 80 bit value */ + ARG_ILR, /* indirect last address register access */ + ARG_LAR, /* last address register */ + ARG_DSZ, /* dsize register? */ + ARG_OPT, /* OPTx (output) pins */ + ARG_PORT, /* PORTx (output) pins */ + ARG_TIM, /* timing related register? */ + ARG_KLO, /* KO1 - KO8 output lines */ + ARG_KHI, /* KO9 - KO14(?) output lines */ + ARG_KI, /* K input lines */ + ARG_S1, /* shift by 1 */ + ARG_S4, /* shift by 4 */ + ARG_S8, /* shift by 8 */ + }; + + static const dasm ops[256]; +}; + +#endif diff --git a/src/devices/cpu/hd61700/hd61700.cpp b/src/devices/cpu/hd61700/hd61700.cpp index cc27d85850f..dfa496d528b 100644 --- a/src/devices/cpu/hd61700/hd61700.cpp +++ b/src/devices/cpu/hd61700/hd61700.cpp @@ -24,6 +24,7 @@ #include "emu.h" #include "hd61700.h" +#include "hd61700d.h" #include "debugger.h" @@ -296,18 +297,15 @@ void hd61700_cpu_device::state_string_export(const device_state_entry &entry, st //------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t hd61700_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *hd61700_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( hd61700 ); - return CPU_DISASSEMBLE_NAME(hd61700)(this, stream, pc, oprom, opram, options); + return new hd61700_disassembler; } - - //------------------------------------------------- // check_irqs - check if need interrupts //------------------------------------------------- diff --git a/src/devices/cpu/hd61700/hd61700.h b/src/devices/cpu/hd61700/hd61700.h index dba81ba0205..12da10dece3 100644 --- a/src/devices/cpu/hd61700/hd61700.h +++ b/src/devices/cpu/hd61700/hd61700.h @@ -90,9 +90,7 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 16; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // interrupts bool check_irqs(); diff --git a/src/devices/cpu/hd61700/hd61700d.cpp b/src/devices/cpu/hd61700/hd61700d.cpp index 53a98be2145..44bbcd5b1a5 100644 --- a/src/devices/cpu/hd61700/hd61700d.cpp +++ b/src/devices/cpu/hd61700/hd61700d.cpp @@ -1,55 +1,15 @@ // license:BSD-3-Clause // copyright-holders:Sandro Ronco -#include "emu.h" -#include "debugger.h" -#include "hd61700.h" - -#define EXT_ROM (pc > 0x0c00) -#define INC_POS pos += (type+1) -#define POS (pos + type) -static const char *const reg_5b[4] = {"sx", "sy", "sz", "sz"}; -static const char *const reg_8b[8] = {"pe", "pd", "ib", "ua", "ia", "ie", "tm", "tm"}; -static const char *const reg_16b[8] = {"ix", "iy", "iz", "us", "ss", "ky", "ky", "ky"}; -static const char *const jp_cond[8] = {"z", "nc", "lz", "uz", "nz", "c", "nlz"}; - -enum -{ - OP_NULL=0, - OP_IM16, - OP_IM16A, - OP_IM3, - OP_IM5, - OP_IM7, - OP_IM8, - OP_IM8I, - OP_IM8_, - OP_IR_IM3, - OP_IR_IM8, - OP_IR_IM8_, - OP_JX_COND, - OP_MREG, - OP_MREG2, - OP_MR_SIR, - OP_MR_SIRI, - OP_REG16, - OP_REG16_, - OP_REG8, - OP_REG8_, - OP_REGIM8, - OP_RMSIM3, - OP_RSIR -}; +#include "emu.h" +#include "hd61700d.h" -struct hd61700_dasm -{ - const char *str; - uint8_t arg1; - uint8_t arg2; - bool optjr; -}; +const char *const hd61700_disassembler::reg_5b[4] = {"sx", "sy", "sz", "sz"}; +const char *const hd61700_disassembler::reg_8b[8] = {"pe", "pd", "ib", "ua", "ia", "ie", "tm", "tm"}; +const char *const hd61700_disassembler::reg_16b[8] = {"ix", "iy", "iz", "us", "ss", "ky", "ky", "ky"}; +const char *const hd61700_disassembler::jp_cond[8] = {"z", "nc", "lz", "uz", "nz", "c", "nlz"}; -static const hd61700_dasm hd61700_ops[256] = +const hd61700_disassembler::dasm hd61700_disassembler::ops[256] = { // 0x00 { "adc", OP_MREG, OP_MR_SIR, 1 }, { "sbc", OP_MREG, OP_MR_SIR, 1 }, @@ -212,13 +172,20 @@ static const hd61700_dasm hd61700_ops[256] = { "off", OP_NULL, OP_NULL, 0 }, { "trp", OP_NULL, OP_NULL, 0 }, }; +u8 hd61700_disassembler::opread(offs_t pc, offs_t pos, const data_buffer &opcodes) +{ + if(pc >= 0x0c00) + return opcodes.r16(pc + pos) & 0xff; + else + return pos & 1 ? opcodes.r16(pc + (pos >> 1)) & 0xff : opcodes.r16(pc + (pos >> 1)) >> 8; +} -static void dasm_im8(std::ostream &stream, uint16_t pc, int arg, const uint8_t *oprom, int &pos, int type) +void hd61700_disassembler::dasm_im8(std::ostream &stream, offs_t pc, int arg, offs_t &pos, const data_buffer &opcodes) { if (((arg>>5) & 0x03) == 0x03) { - INC_POS; - util::stream_format(stream, "0x%02x", oprom[POS] & 0x1f); + pos ++; + util::stream_format(stream, "0x%02x", opread(pc, pos, opcodes) & 0x1f); } else { @@ -227,7 +194,7 @@ static void dasm_im8(std::ostream &stream, uint16_t pc, int arg, const uint8_t * } -static void dasm_im8(std::ostream &stream, uint16_t pc, int arg, int arg1, const uint8_t *oprom, int &pos) +void hd61700_disassembler::dasm_im8(std::ostream &stream, offs_t pc, int arg, int arg1, offs_t &pos, const data_buffer &opcodes) { if (((arg>>5) & 0x03) == 0x03) { @@ -240,57 +207,55 @@ static void dasm_im8(std::ostream &stream, uint16_t pc, int arg, int arg1, const } -static void dasm_arg(std::ostream &stream, uint8_t op, uint16_t pc, int arg, const uint8_t *oprom, int &pos) +void hd61700_disassembler::dasm_arg(std::ostream &stream, uint8_t op, offs_t pc, int arg, offs_t &pos, const data_buffer &opcodes) { - int type = EXT_ROM; - switch( arg ) { case OP_MREG: case OP_MREG2: - util::stream_format( stream, "$%02u", oprom[POS] & 0x1f ); - if (arg == OP_MREG2) INC_POS; + util::stream_format( stream, "$%02u", opread(pc, pos, opcodes) & 0x1f ); + if (arg == OP_MREG2) pos ++; break; case OP_RSIR: - util::stream_format( stream, "%s", reg_5b[(oprom[POS]>>5) & 0x03] ); + util::stream_format( stream, "%s", reg_5b[(opread(pc, pos, opcodes)>>5) & 0x03] ); break; case OP_REG8: case OP_REG8_: - util::stream_format( stream, "%s", reg_8b[(BIT(op,0)<<2) + ((oprom[POS]>>5&3))]); - if (arg == OP_REG8_) INC_POS; + util::stream_format( stream, "%s", reg_8b[(BIT(op,0)<<2) + ((opread(pc, pos, opcodes)>>5&3))]); + if (arg == OP_REG8_) pos ++; break; case OP_MR_SIR: - dasm_im8(stream, pc, oprom[POS], oprom, pos, type); - INC_POS; + dasm_im8(stream, pc, opread(pc, pos, opcodes), pos, opcodes); + pos ++; break; case OP_IR_IM8: case OP_IR_IM8_: - util::stream_format( stream, "(%s%s", (op&1) ? "iz": "ix", (oprom[POS]&0x80) ? "-": "+"); - dasm_im8(stream, pc, oprom[POS], oprom, pos, type); + util::stream_format( stream, "(%s%s", (op&1) ? "iz": "ix", (opread(pc, pos, opcodes)&0x80) ? "-": "+"); + dasm_im8(stream, pc, opread(pc, pos, opcodes), pos, opcodes); util::stream_format( stream, ")"); - if (arg == OP_IR_IM8_) INC_POS; + if (arg == OP_IR_IM8_) pos ++; break; case OP_IM8_: - INC_POS; + pos ++; case OP_IM8: - util::stream_format( stream, "0x%02x", oprom[POS] ); - INC_POS; + util::stream_format( stream, "0x%02x", opread(pc, pos, opcodes) ); + pos ++; break; case OP_IM8I: - util::stream_format( stream, "(0x%02x)", oprom[POS] ); - INC_POS; + util::stream_format( stream, "(0x%02x)", opread(pc, pos, opcodes) ); + pos ++; break; case OP_REGIM8: - util::stream_format( stream, "(%s%s", (op&1) ? "iz": "ix", (oprom[POS]&0x80) ? "-": "+"); - util::stream_format( stream, "%x)", oprom[POS] & 0x1f); - INC_POS; + util::stream_format( stream, "(%s%s", (op&1) ? "iz": "ix", (opread(pc, pos, opcodes)&0x80) ? "-": "+"); + util::stream_format( stream, "%x)", opread(pc, pos, opcodes) & 0x1f); + pos ++; break; case OP_JX_COND: @@ -300,67 +265,67 @@ static void dasm_arg(std::ostream &stream, uint8_t op, uint16_t pc, int arg, con case OP_RMSIM3: { - uint8_t tmp = oprom[POS]; - INC_POS; - dasm_im8(stream, pc, tmp, oprom[POS], oprom, pos); + uint8_t tmp = opread(pc, pos, opcodes); + pos ++; + dasm_im8(stream, pc, tmp, opread(pc, pos, opcodes), pos, opcodes); util::stream_format( stream, ", 0x%02x", ((tmp>>5)&7)+1); - INC_POS; + pos ++; } break; case OP_IR_IM3: { - uint8_t tmp = oprom[POS]; - INC_POS; + uint8_t tmp = opread(pc, pos, opcodes); + pos ++; util::stream_format( stream, "(%s%s", (op&1) ? "iz": "ix", (tmp&0x80) ? "-": "+"); - dasm_im8(stream, pc, tmp, oprom[POS], oprom, pos); - util::stream_format( stream, "), 0x%02x", ((oprom[POS]>>5)&7)+1 ); - INC_POS; + dasm_im8(stream, pc, tmp, opread(pc, pos, opcodes), pos, opcodes); + util::stream_format( stream, "), 0x%02x", ((opread(pc, pos, opcodes)>>5)&7)+1 ); + pos ++; } break; case OP_IM3: - util::stream_format( stream, "0x%02x", ((oprom[POS]>>5)&7)+1 ); - INC_POS; + util::stream_format( stream, "0x%02x", ((opread(pc, pos, opcodes)>>5)&7)+1 ); + pos ++; break; case OP_MR_SIRI: util::stream_format( stream, "("); - dasm_im8(stream, pc, oprom[POS], oprom, pos, type); + dasm_im8(stream, pc, opread(pc, pos, opcodes), pos, opcodes); util::stream_format( stream, ")"); - INC_POS; + pos ++; break; case OP_IM7: { - int tmp = oprom[POS]; + int tmp = opread(pc, pos, opcodes); if (tmp&0x80) tmp = 0x80 - tmp; - util::stream_format( stream, "0x%04x", (pc + tmp + EXT_ROM) & 0xffff ); - INC_POS; + util::stream_format( stream, "0x%04x", (pc + tmp + (pc >= 0x0c00)) & 0xffff ); + pos ++; } break; case OP_IM5: - util::stream_format( stream, "0x%02x", oprom[POS]&0x1f ); - INC_POS; + util::stream_format( stream, "0x%02x", opread(pc, pos, opcodes)&0x1f ); + pos ++; break; case OP_REG16: case OP_REG16_: - util::stream_format(stream, "%s", reg_16b[(BIT(op,0)<<2) + ((oprom[POS]>>5&3))]); - if (arg == OP_REG16_) INC_POS; + util::stream_format(stream, "%s", reg_16b[(BIT(op,0)<<2) + ((opread(pc, pos, opcodes)>>5&3))]); + if (arg == OP_REG16_) pos ++; break; case OP_IM16: case OP_IM16A: { - uint8_t tmp1 = oprom[POS]; - INC_POS; - if (!EXT_ROM && arg == OP_IM16A) INC_POS; - uint8_t tmp2 = oprom[POS]; + uint8_t tmp1 = opread(pc, pos, opcodes); + pos ++; + if (pc < 0x0c00 && arg == OP_IM16A) pos ++; + uint8_t tmp2 = opread(pc, pos, opcodes); util::stream_format(stream, "0x%04x", ((tmp2<<8) | tmp1)); - INC_POS; + pos ++; } break; @@ -369,7 +334,7 @@ static void dasm_arg(std::ostream &stream, uint8_t op, uint16_t pc, int arg, con } } -uint32_t get_dasmflags(uint8_t op) +uint32_t hd61700_disassembler::get_dasmflags(uint8_t op) { switch (op) { @@ -381,55 +346,61 @@ uint32_t get_dasmflags(uint8_t op) case 0xb4: case 0xb5: case 0xb6: case 0xb7: //jr case 0xde: //jp case 0xdf: //jp - return DASMFLAG_STEP_OVER; + return STEP_OVER; case 0xf0: case 0xf1: case 0xf2: case 0xf3: //rtn case 0xf4: case 0xf5: case 0xf6: case 0xf7: //rtn case 0xfd: //rtni - return DASMFLAG_STEP_OUT; + return STEP_OUT; } return 0; } +u32 hd61700_disassembler::opcode_alignment() const +{ + return 1; +} -CPU_DISASSEMBLE(hd61700) +offs_t hd61700_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - const hd61700_dasm *inst; + const dasm *inst; uint32_t dasmflags; uint8_t op, op1; - int pos = 0, type = EXT_ROM; + offs_t pos = 0; + int type = pc >= 0x0c00; - op = oprom[POS]; - INC_POS; + op = opread(pc, pos, opcodes); + pos++; dasmflags = get_dasmflags(op); - op1 = oprom[POS]; + op1 = opread(pc, pos, opcodes); + pos++; - inst = &hd61700_ops[op]; + inst = &ops[op]; util::stream_format(stream, "%-8s", inst->str); //dasm first arg - dasm_arg(stream, op, pc, inst->arg1, oprom, pos); + dasm_arg(stream, op, pc, inst->arg1, pos, opcodes); //if present dasm second arg if (inst->arg2 != OP_NULL) { util::stream_format(stream, ", "); - dasm_arg(stream, op, pc, inst->arg2, oprom, pos); + dasm_arg(stream, op, pc, inst->arg2, pos, opcodes); } //if required add the optional jr if (inst->optjr == true && BIT(op1, 7)) { util::stream_format(stream, ", jr "); - dasm_arg(stream, op, pc+1, OP_IM7, oprom, pos); + dasm_arg(stream, op, pc+1, OP_IM7, pos, opcodes); - dasmflags = DASMFLAG_STEP_OVER; + dasmflags = STEP_OVER; } - if (pos&1) INC_POS; + if (pos&1) pos += type+1; - return (pos>>1) | dasmflags | DASMFLAG_SUPPORTED; + return (pos>>1) | dasmflags | SUPPORTED; } diff --git a/src/devices/cpu/hd61700/hd61700d.h b/src/devices/cpu/hd61700/hd61700d.h new file mode 100644 index 00000000000..f951bf540c8 --- /dev/null +++ b/src/devices/cpu/hd61700/hd61700d.h @@ -0,0 +1,70 @@ +// license:BSD-3-Clause +// copyright-holders:Sandro Ronco + + +#ifndef MAME_CPU_HD61700_HD61700D_H +#define MAME_CPU_HD61700_HD61700D_H + +#pragma once + +class hd61700_disassembler : public util::disasm_interface +{ +public: + hd61700_disassembler() = default; + virtual ~hd61700_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + struct dasm + { + const char *str; + uint8_t arg1; + uint8_t arg2; + bool optjr; + }; + + enum + { + OP_NULL=0, + OP_IM16, + OP_IM16A, + OP_IM3, + OP_IM5, + OP_IM7, + OP_IM8, + OP_IM8I, + OP_IM8_, + OP_IR_IM3, + OP_IR_IM8, + OP_IR_IM8_, + OP_JX_COND, + OP_MREG, + OP_MREG2, + OP_MR_SIR, + OP_MR_SIRI, + OP_REG16, + OP_REG16_, + OP_REG8, + OP_REG8_, + OP_REGIM8, + OP_RMSIM3, + OP_RSIR + }; + + static const char *const reg_5b[4]; + static const char *const reg_8b[8]; + static const char *const reg_16b[8]; + static const char *const jp_cond[8]; + + static const dasm ops[256]; + + u8 opread(offs_t pc, offs_t pos, const data_buffer &opcodes); + void dasm_im8(std::ostream &stream, offs_t pc, int arg, offs_t &pos, const data_buffer &opcodes); + void dasm_im8(std::ostream &stream, offs_t pc, int arg, int arg1, offs_t &pos, const data_buffer &opcodes); + void dasm_arg(std::ostream &stream, uint8_t op, offs_t pc, int arg, offs_t &pos, const data_buffer &opcodes); + uint32_t get_dasmflags(uint8_t op); +}; + +#endif diff --git a/src/devices/cpu/hmcs40/hmcs40.cpp b/src/devices/cpu/hmcs40/hmcs40.cpp index 2bc1860917c..e1260f36d7a 100644 --- a/src/devices/cpu/hmcs40/hmcs40.cpp +++ b/src/devices/cpu/hmcs40/hmcs40.cpp @@ -14,6 +14,7 @@ #include "emu.h" #include "hmcs40.h" #include "debugger.h" +#include "hmcs40d.h" #define IS_PMOS 0 #define IS_CMOS ~0 @@ -173,14 +174,12 @@ void hmcs40_cpu_device::state_string_export(const device_state_entry &entry, std } } -offs_t hmcs40_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +util::disasm_interface *hmcs40_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE(hmcs40); - return CPU_DISASSEMBLE_NAME(hmcs40)(this, stream, pc, oprom, opram, options); + return new hmcs40_disassembler; } - //------------------------------------------------- // device_start - device-specific startup //------------------------------------------------- diff --git a/src/devices/cpu/hmcs40/hmcs40.h b/src/devices/cpu/hmcs40/hmcs40.h index 33e439fc1f5..ca5f238ad9a 100644 --- a/src/devices/cpu/hmcs40/hmcs40.h +++ b/src/devices/cpu/hmcs40/hmcs40.h @@ -158,9 +158,7 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual u32 disasm_min_opcode_bytes() const override { return 2; } - virtual u32 disasm_max_opcode_bytes() const override { return 2; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; address_space_config m_program_config; diff --git a/src/devices/cpu/hmcs40/hmcs40d.cpp b/src/devices/cpu/hmcs40/hmcs40d.cpp index 7074bf5283a..48ae33ccfaa 100644 --- a/src/devices/cpu/hmcs40/hmcs40d.cpp +++ b/src/devices/cpu/hmcs40/hmcs40d.cpp @@ -9,27 +9,9 @@ */ #include "emu.h" -#include "debugger.h" -#include "hmcs40.h" +#include "hmcs40d.h" - -enum e_mnemonics -{ - mILL, - mLAB, mLBA, mLAY, mLASPX, mLASPY, mXAMR, - mLXA, mLYA, mLXI, mLYI, mIY, mDY, mAYY, mSYY, mXSP, - mLAM, mLBM, mXMA, mXMB, mLMAIY, mLMADY, - mLMIIY, mLAI, mLBI, - mAI, mIB, mDB, mAMC, mSMC, mAM, mDAA, mDAS, mNEGA, mCOMB, mSEC, mREC, mTC, mROTL, mROTR, mOR, - mMNEI, mYNEI, mANEM, mBNEM, mALEI, mALEM, mBLEM, - mSEM, mREM, mTM, - mBR, mCAL, mLPU, mTBR, mRTN, - mSEIE, mSEIF0, mSEIF1, mSETF, mSECF, mREIE, mREIF0, mREIF1, mRETF, mRECF, mTI0, mTI1, mTIF0, mTIF1, mTTF, mLTI, mLTA, mLAT, mRTNI, - mSED, mRED, mTD, mSEDD, mREDD, mLAR, mLBR, mLRA, mLRB, mP, - mNOP -}; - -static const char *const s_mnemonics[] = +const char *const hmcs40_disassembler::s_mnemonics[] = { "?", "LAB", "LBA", "LAY", "LASPX", "LASPY", "XAMR", @@ -46,7 +28,7 @@ static const char *const s_mnemonics[] = }; // number of bits per opcode parameter, 99 means (XY) parameter, negative means reversed bit-order -static const s8 s_bits[] = +const s8 hmcs40_disassembler::s_bits[] = { 0, 0, 0, 0, 0, 0, 4, @@ -62,10 +44,7 @@ static const s8 s_bits[] = 0 }; -#define _OVER DASMFLAG_STEP_OVER -#define _OUT DASMFLAG_STEP_OUT - -static const u32 s_flags[] = +const u32 hmcs40_disassembler::s_flags[] = { 0, 0, 0, 0, 0, 0, 0, @@ -75,14 +54,13 @@ static const u32 s_flags[] = 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, _OVER, 0, 0, _OUT, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, _OUT, + 0, STEP_OVER, 0, 0, STEP_OUT, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, STEP_OUT, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; - -static const u8 hmcs40_mnemonic[0x400] = +const u8 hmcs40_disassembler::hmcs40_mnemonic[0x400] = { /* 0 1 2 3 4 5 6 7 8 9 A B C D E F */ /* 0x000 */ @@ -175,9 +153,9 @@ static const u8 hmcs40_mnemonic[0x400] = -CPU_DISASSEMBLE(hmcs40) +offs_t hmcs40_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - u16 op = (oprom[0] | oprom[1] << 8) & 0x3ff; + u16 op = opcodes.r16(pc) & 0x3ff; u8 instr = hmcs40_mnemonic[op]; s8 bits = s_bits[instr]; @@ -217,5 +195,43 @@ CPU_DISASSEMBLE(hmcs40) } } - return 1 | s_flags[instr] | DASMFLAG_SUPPORTED; + return 1 | s_flags[instr] | SUPPORTED; +} + +u32 hmcs40_disassembler::opcode_alignment() const +{ + return 1; +} + +u32 hmcs40_disassembler::interface_flags() const +{ + return NONLINEAR_PC | PAGED; +} + +u32 hmcs40_disassembler::page_address_bits() const +{ + return 6; } + +offs_t hmcs40_disassembler::pc_linear_to_real(offs_t pc) const +{ + static const u8 l2r[64] = { + 0x00, 0x01, 0x03, 0x07, 0x0f, 0x1f, 0x3f, 0x3e, 0x3d, 0x3b, 0x37, 0x2f, 0x1e, 0x3c, 0x39, 0x33, + 0x27, 0x0e, 0x1d, 0x3a, 0x35, 0x2b, 0x16, 0x2c, 0x18, 0x30, 0x21, 0x02, 0x05, 0x0b, 0x17, 0x2e, + 0x1c, 0x38, 0x31, 0x23, 0x06, 0x0d, 0x1b, 0x36, 0x2d, 0x1a, 0x34, 0x29, 0x12, 0x24, 0x08, 0x11, + 0x22, 0x04, 0x09, 0x13, 0x26, 0x0c, 0x19, 0x32, 0x25, 0x0a, 0x15, 0x2a, 0x14, 0x28, 0x10, 0x20, + }; + return (pc & ~0x3f) | l2r[pc & 0x3f]; +} + +offs_t hmcs40_disassembler::pc_real_to_linear(offs_t pc) const +{ + static const u8 r2l[64] = { + 0x00, 0x01, 0x1b, 0x02, 0x31, 0x1c, 0x24, 0x03, 0x2e, 0x32, 0x39, 0x1d, 0x35, 0x25, 0x11, 0x04, + 0x3e, 0x2f, 0x2c, 0x33, 0x3c, 0x3a, 0x16, 0x1e, 0x18, 0x36, 0x29, 0x26, 0x20, 0x12, 0x0c, 0x05, + 0x3f, 0x1a, 0x30, 0x23, 0x2d, 0x38, 0x34, 0x10, 0x3d, 0x2b, 0x3b, 0x15, 0x17, 0x28, 0x1f, 0x0b, + 0x19, 0x22, 0x37, 0x0f, 0x2a, 0x14, 0x27, 0x0a, 0x21, 0x0e, 0x13, 0x09, 0x0d, 0x08, 0x07, 0x06, + }; + return (pc & ~0x3f) | r2l[pc & 0x3f]; +} + diff --git a/src/devices/cpu/hmcs40/hmcs40d.h b/src/devices/cpu/hmcs40/hmcs40d.h new file mode 100644 index 00000000000..04f534bdc4c --- /dev/null +++ b/src/devices/cpu/hmcs40/hmcs40d.h @@ -0,0 +1,50 @@ +// license:BSD-3-Clause +// copyright-holders:hap +/* + + Hitachi HMCS40 MCU family disassembler + +*/ + +#ifndef MAME_CPU_HMCS40_HMCS40D_H +#define MAME_CPU_HMCS40_HMCS40D_H + +#pragma once + +class hmcs40_disassembler : public util::disasm_interface +{ +public: + hmcs40_disassembler() = default; + virtual ~hmcs40_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual u32 interface_flags() const override; + virtual u32 page_address_bits() const override; + virtual offs_t pc_linear_to_real(offs_t pc) const override; + virtual offs_t pc_real_to_linear(offs_t pc) const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum e_mnemonics + { + mILL, + mLAB, mLBA, mLAY, mLASPX, mLASPY, mXAMR, + mLXA, mLYA, mLXI, mLYI, mIY, mDY, mAYY, mSYY, mXSP, + mLAM, mLBM, mXMA, mXMB, mLMAIY, mLMADY, + mLMIIY, mLAI, mLBI, + mAI, mIB, mDB, mAMC, mSMC, mAM, mDAA, mDAS, mNEGA, mCOMB, mSEC, mREC, mTC, mROTL, mROTR, mOR, + mMNEI, mYNEI, mANEM, mBNEM, mALEI, mALEM, mBLEM, + mSEM, mREM, mTM, + mBR, mCAL, mLPU, mTBR, mRTN, + mSEIE, mSEIF0, mSEIF1, mSETF, mSECF, mREIE, mREIF0, mREIF1, mRETF, mRECF, mTI0, mTI1, mTIF0, mTIF1, mTTF, mLTI, mLTA, mLAT, mRTNI, + mSED, mRED, mTD, mSEDD, mREDD, mLAR, mLBR, mLRA, mLRB, mP, + mNOP + }; + + static const char *const s_mnemonics[]; + static const s8 s_bits[]; + static const u32 s_flags[]; + static const u8 hmcs40_mnemonic[0x400]; +}; + +#endif diff --git a/src/devices/cpu/hphybrid/hphybrid.cpp b/src/devices/cpu/hphybrid/hphybrid.cpp index 6eb3f4b83d6..3974a862c95 100644 --- a/src/devices/cpu/hphybrid/hphybrid.cpp +++ b/src/devices/cpu/hphybrid/hphybrid.cpp @@ -33,6 +33,7 @@ #include "emu.h" #include "hphybrid.h" +#include "hphybrid_dasm.h" #include "debugger.h" #include "hphybrid_defs.h" @@ -681,10 +682,9 @@ void hp_hybrid_cpu_device::state_string_export(const device_state_entry &entry, } } -offs_t hp_hybrid_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *hp_hybrid_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE(hp_hybrid); - return CPU_DISASSEMBLE_NAME(hp_hybrid)(this, stream, pc, oprom, opram, options); + return new hp_hybrid_disassembler; } uint16_t hp_hybrid_cpu_device::remove_mae(uint32_t addr) @@ -1539,10 +1539,9 @@ uint16_t hp_5061_3001_cpu_device::execute_no_bpc_ioc(uint16_t opcode) return m_reg_P + 1; } -offs_t hp_5061_3001_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *hp_5061_3001_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE(hp_5061_3001); - return CPU_DISASSEMBLE_NAME(hp_5061_3001)(this, stream, pc, oprom, opram, options); + return new hp_5061_3001_disassembler; } uint32_t hp_5061_3001_cpu_device::add_mae(aec_cases_t aec_case , uint16_t addr) diff --git a/src/devices/cpu/hphybrid/hphybrid.h b/src/devices/cpu/hphybrid/hphybrid.h index 5962942b64c..8482712b476 100644 --- a/src/devices/cpu/hphybrid/hphybrid.h +++ b/src/devices/cpu/hphybrid/hphybrid.h @@ -85,9 +85,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 2; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // Different cases of memory access // See patent @ pg 361 @@ -181,7 +179,7 @@ protected: void do_mpy(); virtual uint16_t execute_no_bpc_ioc(uint16_t opcode) override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t add_mae(aec_cases_t aec_case, uint16_t addr) override; virtual uint16_t read_non_common_reg(uint16_t addr) override; virtual void write_non_common_reg(uint16_t addr , uint16_t v) override; diff --git a/src/devices/cpu/hphybrid/hphybrid_dasm.cpp b/src/devices/cpu/hphybrid/hphybrid_dasm.cpp index 58d800a3722..74d833803c0 100644 --- a/src/devices/cpu/hphybrid/hphybrid_dasm.cpp +++ b/src/devices/cpu/hphybrid/hphybrid_dasm.cpp @@ -5,23 +5,10 @@ // ******************************************************************************** #include "emu.h" -#include "hphybrid.h" -#include "debugger.h" - +#include "hphybrid_dasm.h" #include "hphybrid_defs.h" - -typedef void (*fn_dis_param)(std::ostream &stream , offs_t pc , uint16_t opcode , bool is_3001); - -typedef struct { - uint16_t m_op_mask; - uint16_t m_opcode; - const char *m_mnemonic; - fn_dis_param m_param_fn; - uint32_t m_dasm_flags; -} dis_entry_t; - -static void addr_2_str(std::ostream &stream, uint16_t addr , bool indirect , bool is_3001) +void hp_hybrid_disassembler::addr_2_str(std::ostream &stream, uint16_t addr , bool indirect , bool is_3001) { util::stream_format(stream, "$%04x" , addr); @@ -168,11 +155,11 @@ static void addr_2_str(std::ostream &stream, uint16_t addr , bool indirect , boo } } -static void param_none(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001) +void hp_hybrid_disassembler::param_none(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001) { } -static void param_loc(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001) +void hp_hybrid_disassembler::param_loc(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001) { uint16_t base; uint16_t off; @@ -193,12 +180,12 @@ static void param_loc(std::ostream &stream, offs_t pc , uint16_t opcode , bool i addr_2_str(stream, base + off , (opcode & 0x8000) != 0 , is_3001); } -static void param_addr32(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001) +void hp_hybrid_disassembler::param_addr32(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001) { addr_2_str(stream, opcode & 0x1f , (opcode & 0x8000) != 0 , is_3001); } -static void param_skip(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001) +void hp_hybrid_disassembler::param_skip(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001) { uint16_t off = opcode & 0x3f; if (off & 0x20) { @@ -207,7 +194,7 @@ static void param_skip(std::ostream &stream, offs_t pc , uint16_t opcode , bool addr_2_str(stream , pc + off , false , is_3001); } -static void param_skip_sc(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001) +void hp_hybrid_disassembler::param_skip_sc(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001) { param_skip(stream, pc, opcode , is_3001); @@ -220,7 +207,7 @@ static void param_skip_sc(std::ostream &stream, offs_t pc , uint16_t opcode , bo } } -static void param_ret(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001) +void hp_hybrid_disassembler::param_ret(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001) { int off = opcode & 0x3f; @@ -234,12 +221,12 @@ static void param_ret(std::ostream &stream, offs_t pc , uint16_t opcode , bool i } } -static void param_n16(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001) +void hp_hybrid_disassembler::param_n16(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001) { util::stream_format(stream , "%u" , (opcode & 0xf) + 1); } -static void param_reg_id(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001) +void hp_hybrid_disassembler::param_reg_id(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001) { addr_2_str(stream, opcode & 7, false , is_3001); @@ -250,133 +237,133 @@ static void param_reg_id(std::ostream &stream, offs_t pc , uint16_t opcode , boo } } -static const dis_entry_t dis_table[] = { +const hp_hybrid_disassembler::dis_entry_t hp_hybrid_disassembler::dis_table[] = { // *** BPC Instructions *** - {0xffff , 0x0000 , "NOP" , param_none , 0 }, - {0x7800 , 0x0000 , "LDA" , param_loc , 0 }, - {0x7800 , 0x0800 , "LDB" , param_loc , 0 }, - {0x7800 , 0x1000 , "CPA" , param_loc , 0 }, - {0x7800 , 0x1800 , "CPB" , param_loc , 0 }, - {0x7800 , 0x2000 , "ADA" , param_loc , 0 }, - {0x7800 , 0x2800 , "ADB" , param_loc , 0 }, - {0x7800 , 0x3000 , "STA" , param_loc , 0 }, - {0x7800 , 0x3800 , "STB" , param_loc , 0 }, - {0x7800 , 0x4000 , "JSM" , param_loc , DASMFLAG_STEP_OVER }, - {0x7800 , 0x4800 , "ISZ" , param_loc , 0 }, - {0x7800 , 0x5000 , "AND" , param_loc , 0 }, - {0x7800 , 0x5800 , "DSZ" , param_loc , 0 }, - {0x7800 , 0x6000 , "IOR" , param_loc , 0 }, - {0x7800 , 0x6800 , "JMP" , param_loc , 0 }, - {0x7fe0 , 0x7000 , "EXE" , param_addr32 , 0 }, - {0xffc0 , 0x7400 , "RZA" , param_skip , 0 }, - {0xffc0 , 0x7C00 , "RZB" , param_skip , 0 }, - {0xffc0 , 0x7440 , "RIA" , param_skip , 0 }, - {0xffc0 , 0x7C40 , "RIB" , param_skip , 0 }, - {0xffc0 , 0x7500 , "SZA" , param_skip , 0 }, - {0xffc0 , 0x7D00 , "SZB" , param_skip , 0 }, - {0xffc0 , 0x7540 , "SIA" , param_skip , 0 }, - {0xffc0 , 0x7D40 , "SIB" , param_skip , 0 }, - {0xffc0 , 0x7480 , "SFS" , param_skip , 0 }, - {0xffc0 , 0x7580 , "SFC" , param_skip , 0 }, - {0xffc0 , 0x7c80 , "SSS" , param_skip , 0 }, - {0xffc0 , 0x7d80 , "SSC" , param_skip , 0 }, - {0xffc0 , 0x7cc0 , "SHS" , param_skip , 0 }, - {0xffc0 , 0x7dc0 , "SHC" , param_skip , 0 }, - {0xff00 , 0x7600 , "SLA" , param_skip_sc , 0 }, - {0xff00 , 0x7e00 , "SLB" , param_skip_sc , 0 }, - {0xff00 , 0x7700 , "RLA" , param_skip_sc , 0 }, - {0xff00 , 0x7f00 , "RLB" , param_skip_sc , 0 }, - {0xff00 , 0xf400 , "SAP" , param_skip_sc , 0 }, - {0xff00 , 0xfc00 , "SBP" , param_skip_sc , 0 }, - {0xff00 , 0xf500 , "SAM" , param_skip_sc , 0 }, - {0xff00 , 0xfd00 , "SBM" , param_skip_sc , 0 }, - {0xff00 , 0xf600 , "SOC" , param_skip_sc , 0 }, - {0xff00 , 0xf700 , "SOS" , param_skip_sc , 0 }, - {0xff00 , 0xfe00 , "SEC" , param_skip_sc , 0 }, - {0xff00 , 0xff00 , "SES" , param_skip_sc , 0 }, - {0xffff , 0xf020 , "TCA" , param_none , 0 }, - {0xffff , 0xf820 , "TCB" , param_none , 0 }, - {0xffff , 0xf060 , "CMA" , param_none , 0 }, - {0xffff , 0xf860 , "CMB" , param_none , 0 }, - {0xff80 , 0xf080 , "RET" , param_ret , DASMFLAG_STEP_OUT }, - {0xfff0 , 0xf100 , "AAR" , param_n16 , 0 }, - {0xfff0 , 0xf900 , "ABR" , param_n16 , 0 }, - {0xffff , 0xf14f , "CLA" , param_none , 0 }, - {0xfff0 , 0xf140 , "SAR" , param_n16 , 0 }, - {0xffff , 0xf94f , "CLB" , param_none , 0 }, - {0xfff0 , 0xf940 , "SBR" , param_n16 , 0 }, - {0xfff0 , 0xf180 , "SAL" , param_n16 , 0 }, - {0xfff0 , 0xf980 , "SBL" , param_n16 , 0 }, - {0xfff0 , 0xf1c0 , "RAR" , param_n16 , 0 }, - {0xfff0 , 0xf9c0 , "RBR" , param_n16 , 0 }, + {0xffff , 0x0000 , "NOP" , &hp_hybrid_disassembler::param_none , 0 }, + {0x7800 , 0x0000 , "LDA" , &hp_hybrid_disassembler::param_loc , 0 }, + {0x7800 , 0x0800 , "LDB" , &hp_hybrid_disassembler::param_loc , 0 }, + {0x7800 , 0x1000 , "CPA" , &hp_hybrid_disassembler::param_loc , 0 }, + {0x7800 , 0x1800 , "CPB" , &hp_hybrid_disassembler::param_loc , 0 }, + {0x7800 , 0x2000 , "ADA" , &hp_hybrid_disassembler::param_loc , 0 }, + {0x7800 , 0x2800 , "ADB" , &hp_hybrid_disassembler::param_loc , 0 }, + {0x7800 , 0x3000 , "STA" , &hp_hybrid_disassembler::param_loc , 0 }, + {0x7800 , 0x3800 , "STB" , &hp_hybrid_disassembler::param_loc , 0 }, + {0x7800 , 0x4000 , "JSM" , &hp_hybrid_disassembler::param_loc , STEP_OVER }, + {0x7800 , 0x4800 , "ISZ" , &hp_hybrid_disassembler::param_loc , 0 }, + {0x7800 , 0x5000 , "AND" , &hp_hybrid_disassembler::param_loc , 0 }, + {0x7800 , 0x5800 , "DSZ" , &hp_hybrid_disassembler::param_loc , 0 }, + {0x7800 , 0x6000 , "IOR" , &hp_hybrid_disassembler::param_loc , 0 }, + {0x7800 , 0x6800 , "JMP" , &hp_hybrid_disassembler::param_loc , 0 }, + {0x7fe0 , 0x7000 , "EXE" , &hp_hybrid_disassembler::param_addr32 , 0 }, + {0xffc0 , 0x7400 , "RZA" , &hp_hybrid_disassembler::param_skip , 0 }, + {0xffc0 , 0x7C00 , "RZB" , &hp_hybrid_disassembler::param_skip , 0 }, + {0xffc0 , 0x7440 , "RIA" , &hp_hybrid_disassembler::param_skip , 0 }, + {0xffc0 , 0x7C40 , "RIB" , &hp_hybrid_disassembler::param_skip , 0 }, + {0xffc0 , 0x7500 , "SZA" , &hp_hybrid_disassembler::param_skip , 0 }, + {0xffc0 , 0x7D00 , "SZB" , &hp_hybrid_disassembler::param_skip , 0 }, + {0xffc0 , 0x7540 , "SIA" , &hp_hybrid_disassembler::param_skip , 0 }, + {0xffc0 , 0x7D40 , "SIB" , &hp_hybrid_disassembler::param_skip , 0 }, + {0xffc0 , 0x7480 , "SFS" , &hp_hybrid_disassembler::param_skip , 0 }, + {0xffc0 , 0x7580 , "SFC" , &hp_hybrid_disassembler::param_skip , 0 }, + {0xffc0 , 0x7c80 , "SSS" , &hp_hybrid_disassembler::param_skip , 0 }, + {0xffc0 , 0x7d80 , "SSC" , &hp_hybrid_disassembler::param_skip , 0 }, + {0xffc0 , 0x7cc0 , "SHS" , &hp_hybrid_disassembler::param_skip , 0 }, + {0xffc0 , 0x7dc0 , "SHC" , &hp_hybrid_disassembler::param_skip , 0 }, + {0xff00 , 0x7600 , "SLA" , &hp_hybrid_disassembler::param_skip_sc , 0 }, + {0xff00 , 0x7e00 , "SLB" , &hp_hybrid_disassembler::param_skip_sc , 0 }, + {0xff00 , 0x7700 , "RLA" , &hp_hybrid_disassembler::param_skip_sc , 0 }, + {0xff00 , 0x7f00 , "RLB" , &hp_hybrid_disassembler::param_skip_sc , 0 }, + {0xff00 , 0xf400 , "SAP" , &hp_hybrid_disassembler::param_skip_sc , 0 }, + {0xff00 , 0xfc00 , "SBP" , &hp_hybrid_disassembler::param_skip_sc , 0 }, + {0xff00 , 0xf500 , "SAM" , &hp_hybrid_disassembler::param_skip_sc , 0 }, + {0xff00 , 0xfd00 , "SBM" , &hp_hybrid_disassembler::param_skip_sc , 0 }, + {0xff00 , 0xf600 , "SOC" , &hp_hybrid_disassembler::param_skip_sc , 0 }, + {0xff00 , 0xf700 , "SOS" , &hp_hybrid_disassembler::param_skip_sc , 0 }, + {0xff00 , 0xfe00 , "SEC" , &hp_hybrid_disassembler::param_skip_sc , 0 }, + {0xff00 , 0xff00 , "SES" , &hp_hybrid_disassembler::param_skip_sc , 0 }, + {0xffff , 0xf020 , "TCA" , &hp_hybrid_disassembler::param_none , 0 }, + {0xffff , 0xf820 , "TCB" , &hp_hybrid_disassembler::param_none , 0 }, + {0xffff , 0xf060 , "CMA" , &hp_hybrid_disassembler::param_none , 0 }, + {0xffff , 0xf860 , "CMB" , &hp_hybrid_disassembler::param_none , 0 }, + {0xff80 , 0xf080 , "RET" , &hp_hybrid_disassembler::param_ret , STEP_OUT }, + {0xfff0 , 0xf100 , "AAR" , &hp_hybrid_disassembler::param_n16 , 0 }, + {0xfff0 , 0xf900 , "ABR" , &hp_hybrid_disassembler::param_n16 , 0 }, + {0xffff , 0xf14f , "CLA" , &hp_hybrid_disassembler::param_none , 0 }, + {0xfff0 , 0xf140 , "SAR" , &hp_hybrid_disassembler::param_n16 , 0 }, + {0xffff , 0xf94f , "CLB" , &hp_hybrid_disassembler::param_none , 0 }, + {0xfff0 , 0xf940 , "SBR" , &hp_hybrid_disassembler::param_n16 , 0 }, + {0xfff0 , 0xf180 , "SAL" , &hp_hybrid_disassembler::param_n16 , 0 }, + {0xfff0 , 0xf980 , "SBL" , &hp_hybrid_disassembler::param_n16 , 0 }, + {0xfff0 , 0xf1c0 , "RAR" , &hp_hybrid_disassembler::param_n16 , 0 }, + {0xfff0 , 0xf9c0 , "RBR" , &hp_hybrid_disassembler::param_n16 , 0 }, // *** IOC Instructions *** - {0xffff , 0x7100 , "SDO" , param_none , 0 }, - {0xffff , 0x7108 , "SDI" , param_none , 0 }, - {0xffff , 0x7110 , "EIR" , param_none , 0 }, - {0xffff , 0x7118 , "DIR" , param_none , 0 }, - {0xffff , 0x7120 , "DMA" , param_none , 0 }, - {0xffff , 0x7128 , "PCM" , param_none , 0 }, - {0xffff , 0x7138 , "DDR" , param_none , 0 }, - {0xffff , 0x7140 , "DBL" , param_none , 0 }, - {0xffff , 0x7148 , "CBL" , param_none , 0 }, - {0xffff , 0x7150 , "DBU" , param_none , 0 }, - {0xffff , 0x7158 , "CBU" , param_none , 0 }, - {0xff78 , 0x7160 , "PWC" , param_reg_id , 0 }, - {0xff78 , 0x7168 , "PWD" , param_reg_id , 0 }, - {0xff78 , 0x7960 , "PBC" , param_reg_id , 0 }, - {0xff78 , 0x7968 , "PBD" , param_reg_id , 0 }, - {0xff78 , 0x7170 , "WWC" , param_reg_id , 0 }, - {0xff78 , 0x7178 , "WWD" , param_reg_id , 0 }, - {0xff78 , 0x7970 , "WBC" , param_reg_id , 0 }, - {0xff78 , 0x7978 , "WBD" , param_reg_id , 0 }, + {0xffff , 0x7100 , "SDO" , &hp_hybrid_disassembler::param_none , 0 }, + {0xffff , 0x7108 , "SDI" , &hp_hybrid_disassembler::param_none , 0 }, + {0xffff , 0x7110 , "EIR" , &hp_hybrid_disassembler::param_none , 0 }, + {0xffff , 0x7118 , "DIR" , &hp_hybrid_disassembler::param_none , 0 }, + {0xffff , 0x7120 , "DMA" , &hp_hybrid_disassembler::param_none , 0 }, + {0xffff , 0x7128 , "PCM" , &hp_hybrid_disassembler::param_none , 0 }, + {0xffff , 0x7138 , "DDR" , &hp_hybrid_disassembler::param_none , 0 }, + {0xffff , 0x7140 , "DBL" , &hp_hybrid_disassembler::param_none , 0 }, + {0xffff , 0x7148 , "CBL" , &hp_hybrid_disassembler::param_none , 0 }, + {0xffff , 0x7150 , "DBU" , &hp_hybrid_disassembler::param_none , 0 }, + {0xffff , 0x7158 , "CBU" , &hp_hybrid_disassembler::param_none , 0 }, + {0xff78 , 0x7160 , "PWC" , &hp_hybrid_disassembler::param_reg_id , 0 }, + {0xff78 , 0x7168 , "PWD" , &hp_hybrid_disassembler::param_reg_id , 0 }, + {0xff78 , 0x7960 , "PBC" , &hp_hybrid_disassembler::param_reg_id , 0 }, + {0xff78 , 0x7968 , "PBD" , &hp_hybrid_disassembler::param_reg_id , 0 }, + {0xff78 , 0x7170 , "WWC" , &hp_hybrid_disassembler::param_reg_id , 0 }, + {0xff78 , 0x7178 , "WWD" , &hp_hybrid_disassembler::param_reg_id , 0 }, + {0xff78 , 0x7970 , "WBC" , &hp_hybrid_disassembler::param_reg_id , 0 }, + {0xff78 , 0x7978 , "WBD" , &hp_hybrid_disassembler::param_reg_id , 0 }, // *** END *** {0 , 0 , nullptr , nullptr , 0 } }; -static const dis_entry_t dis_table_emc[] = { +const hp_hybrid_disassembler::dis_entry_t hp_5061_3001_disassembler::dis_table_emc[] = { // *** EMC Instructions *** - {0xffff , 0x7200 , "MWA" , param_none , 0 }, - {0xffff , 0x7220 , "CMY" , param_none , 0 }, - {0xffff , 0x7260 , "CMX" , param_none , 0 }, - {0xffff , 0x7280 , "FXA" , param_none , 0 }, - {0xfff0 , 0x7300 , "XFR" , param_n16 , 0 }, - {0xffff , 0x7340 , "NRM" , param_none , 0 }, - {0xfff0 , 0x7380 , "CLR" , param_n16 , 0 }, - {0xffff , 0x73c0 , "CDC" , param_none , 0 }, - {0xffc0 , 0x74c0 , "SDS" , param_skip , 0 }, - {0xffc0 , 0x75c0 , "SDC" , param_skip , 0 }, - {0xffff , 0x7a00 , "FMP" , param_none , 0 }, - {0xffff , 0x7a21 , "FDV" , param_none , 0 }, - {0xffff , 0x7b00 , "MRX" , param_none , 0 }, - {0xffff , 0x7b21 , "DRS" , param_none , 0 }, - {0xffff , 0x7b40 , "MRY" , param_none , 0 }, - {0xffff , 0x7b61 , "MLY" , param_none , 0 }, - {0xffff , 0x7b8f , "MPY" , param_none , 0 }, + {0xffff , 0x7200 , "MWA" , &hp_5061_3001_disassembler::param_none , 0 }, + {0xffff , 0x7220 , "CMY" , &hp_5061_3001_disassembler::param_none , 0 }, + {0xffff , 0x7260 , "CMX" , &hp_5061_3001_disassembler::param_none , 0 }, + {0xffff , 0x7280 , "FXA" , &hp_5061_3001_disassembler::param_none , 0 }, + {0xfff0 , 0x7300 , "XFR" , &hp_5061_3001_disassembler::param_n16 , 0 }, + {0xffff , 0x7340 , "NRM" , &hp_5061_3001_disassembler::param_none , 0 }, + {0xfff0 , 0x7380 , "CLR" , &hp_5061_3001_disassembler::param_n16 , 0 }, + {0xffff , 0x73c0 , "CDC" , &hp_5061_3001_disassembler::param_none , 0 }, + {0xffc0 , 0x74c0 , "SDS" , &hp_5061_3001_disassembler::param_skip , 0 }, + {0xffc0 , 0x75c0 , "SDC" , &hp_5061_3001_disassembler::param_skip , 0 }, + {0xffff , 0x7a00 , "FMP" , &hp_5061_3001_disassembler::param_none , 0 }, + {0xffff , 0x7a21 , "FDV" , &hp_5061_3001_disassembler::param_none , 0 }, + {0xffff , 0x7b00 , "MRX" , &hp_5061_3001_disassembler::param_none , 0 }, + {0xffff , 0x7b21 , "DRS" , &hp_5061_3001_disassembler::param_none , 0 }, + {0xffff , 0x7b40 , "MRY" , &hp_5061_3001_disassembler::param_none , 0 }, + {0xffff , 0x7b61 , "MLY" , &hp_5061_3001_disassembler::param_none , 0 }, + {0xffff , 0x7b8f , "MPY" , &hp_5061_3001_disassembler::param_none , 0 }, // *** Undocumented instructions of 5061-3001 *** - {0xffff , 0x7026 , "CIM" , param_none , 0 }, - {0xffff , 0x7027 , "SIM" , param_none , 0 }, + {0xffff , 0x7026 , "CIM" , &hp_5061_3001_disassembler::param_none , 0 }, + {0xffff , 0x7027 , "SIM" , &hp_5061_3001_disassembler::param_none , 0 }, // *** END *** {0 , 0 , nullptr , nullptr , 0 } }; -static offs_t disassemble_table(uint16_t opcode , offs_t pc , const dis_entry_t *table , bool is_3001 , std::ostream &stream) +offs_t hp_hybrid_disassembler::disassemble_table(uint16_t opcode , offs_t pc , const dis_entry_t *table , bool is_3001 , std::ostream &stream) { const dis_entry_t *p; for (p = table; p->m_op_mask; p++) { if ((opcode & p->m_op_mask) == p->m_opcode) { stream << p->m_mnemonic << " "; - p->m_param_fn(stream , pc , opcode , is_3001); - return 1 | p->m_dasm_flags | DASMFLAG_SUPPORTED; + (this->*(p->m_param_fn))(stream , pc , opcode , is_3001); + return 1 | p->m_dasm_flags | SUPPORTED; } } return 0; } -CPU_DISASSEMBLE(hp_hybrid) +offs_t hp_hybrid_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - uint16_t opcode = ((uint16_t)oprom[ 0 ] << 8) | oprom[ 1 ]; + uint16_t opcode = opcodes.r16(pc); offs_t res; res = disassemble_table(opcode, pc, dis_table, false, stream); @@ -385,15 +372,15 @@ CPU_DISASSEMBLE(hp_hybrid) { // Unknown opcode stream << "???"; - res = 1 | DASMFLAG_SUPPORTED; + res = 1 | SUPPORTED; } return res; } -CPU_DISASSEMBLE(hp_5061_3001) +offs_t hp_5061_3001_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - uint16_t opcode = ((uint16_t)oprom[ 0 ] << 8) | oprom[ 1 ]; + uint16_t opcode = opcodes.r16(pc); offs_t res; res = disassemble_table(opcode, pc, dis_table_emc, true, stream); @@ -407,8 +394,13 @@ CPU_DISASSEMBLE(hp_5061_3001) { // Unknown opcode stream << "???"; - res = 1 | DASMFLAG_SUPPORTED; + res = 1 | SUPPORTED; } return res; } + +u32 hp_hybrid_disassembler::opcode_alignment() const +{ + return 1; +} diff --git a/src/devices/cpu/hphybrid/hphybrid_dasm.h b/src/devices/cpu/hphybrid/hphybrid_dasm.h new file mode 100644 index 00000000000..96994ae0632 --- /dev/null +++ b/src/devices/cpu/hphybrid/hphybrid_dasm.h @@ -0,0 +1,59 @@ +// license:BSD-3-Clause +// copyright-holders:F. Ulivi +// ******************************************************************************** +// * HP "hybrid" processor disassembler +// ******************************************************************************** + +#ifndef MAME_CPU_HPHYBRID_HPHYBRID_DASM_H +#define MAME_CPU_HPHYBRID_HPHYBRID_DASM_H + +#pragma once + +class hp_hybrid_disassembler : public util::disasm_interface +{ +public: + hp_hybrid_disassembler() = default; + virtual ~hp_hybrid_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +protected: + typedef void (hp_hybrid_disassembler::*fn_dis_param)(std::ostream &stream , offs_t pc , uint16_t opcode , bool is_3001); + + typedef struct { + uint16_t m_op_mask; + uint16_t m_opcode; + const char *m_mnemonic; + fn_dis_param m_param_fn; + uint32_t m_dasm_flags; + } dis_entry_t; + + static const dis_entry_t dis_table[]; + + void addr_2_str(std::ostream &stream, uint16_t addr , bool indirect , bool is_3001); + void param_none(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001); + void param_loc(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001); + void param_addr32(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001); + void param_skip(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001); + void param_skip_sc(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001); + void param_ret(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001); + void param_n16(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001); + void param_reg_id(std::ostream &stream, offs_t pc , uint16_t opcode , bool is_3001); + + offs_t disassemble_table(uint16_t opcode , offs_t pc , const dis_entry_t *table , bool is_3001 , std::ostream &stream); +}; + +class hp_5061_3001_disassembler : public hp_hybrid_disassembler +{ +public: + hp_5061_3001_disassembler() = default; + virtual ~hp_5061_3001_disassembler() = default; + + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +protected: + static const dis_entry_t dis_table_emc[]; +}; + +#endif diff --git a/src/devices/cpu/i386/i386.cpp b/src/devices/cpu/i386/i386.cpp index 5c403dc1163..ee0e49e7cf4 100644 --- a/src/devices/cpu/i386/i386.cpp +++ b/src/devices/cpu/i386/i386.cpp @@ -4021,11 +4021,15 @@ bool i386_device::memory_translate(int spacenum, int intention, offs_t &address) return ret; } -offs_t i386_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +int i386_device::get_mode() const { - return i386_dasm_one(stream, pc, oprom, m_sreg[CS].d ? 32 : 16); + return m_sreg[CS].d ? 32 : 16; } +util::disasm_interface *i386_device::create_disassembler() +{ + return new i386_disassembler(this); +} /*****************************************************************************/ /* Intel 486 */ diff --git a/src/devices/cpu/i386/i386.h b/src/devices/cpu/i386/i386.h index 3701f6c6704..cd406276e19 100644 --- a/src/devices/cpu/i386/i386.h +++ b/src/devices/cpu/i386/i386.h @@ -15,6 +15,7 @@ #include "debug/debugcpu.h" #include "divtlb.h" +#include "i386dasm.h" #define INPUT_LINE_A20 1 #define INPUT_LINE_SMI 2 @@ -29,7 +30,7 @@ #define X86_NUM_CPUS 4 -class i386_device : public cpu_device, public device_vtlb_interface +class i386_device : public cpu_device, public device_vtlb_interface, public i386_disassembler::config { public: // construction/destruction @@ -68,9 +69,8 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 15; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; + virtual int get_mode() const override; address_space_config m_program_config; address_space_config m_io_config; diff --git a/src/devices/cpu/i386/i386dasm.cpp b/src/devices/cpu/i386/i386dasm.cpp index 3c815612ffa..e201c4c02a4 100644 --- a/src/devices/cpu/i386/i386dasm.cpp +++ b/src/devices/cpu/i386/i386dasm.cpp @@ -7,117 +7,9 @@ */ #include "emu.h" +#include "i386dasm.h" -enum -{ - PARAM_REG = 1, /* 16 or 32-bit register */ - PARAM_REG8, /* 8-bit register */ - PARAM_REG16, /* 16-bit register */ - PARAM_REG32, /* 32-bit register */ - PARAM_REG3264, /* 32-bit or 64-bit register */ - PARAM_REG2_32, /* 32-bit register */ - PARAM_MMX, /* MMX register */ - PARAM_MMX2, /* MMX register in modrm */ - PARAM_XMM, /* XMM register */ - PARAM_RM, /* 16 or 32-bit memory or register */ - PARAM_RM8, /* 8-bit memory or register */ - PARAM_RM16, /* 16-bit memory or register */ - PARAM_RM32, /* 32-bit memory or register */ - PARAM_RMPTR, /* 16 or 32-bit memory or register */ - PARAM_RMPTR8, /* 8-bit memory or register */ - PARAM_RMPTR16, /* 16-bit memory or register */ - PARAM_RMPTR32, /* 32-bit memory or register */ - PARAM_RMXMM, /* 32 or 64-bit memory or register */ - PARAM_REGORXMM, /* 32 or 64-bit register or XMM register */ - PARAM_M64, /* 64-bit memory */ - PARAM_M64PTR, /* 64-bit memory */ - PARAM_MMXM, /* 64-bit memory or MMX register */ - PARAM_XMMM, /* 128-bit memory or XMM register */ - PARAM_I4, /* 4-bit signed immediate */ - PARAM_I8, /* 8-bit signed immediate */ - PARAM_I16, /* 16-bit signed immediate */ - PARAM_UI8, /* 8-bit unsigned immediate */ - PARAM_UI16, /* 16-bit unsigned immediate */ - PARAM_IMM, /* 16 or 32-bit immediate */ - PARAM_IMM64, /* 16, 32 or 64-bit immediate */ - PARAM_ADDR, /* 16:16 or 16:32 address */ - PARAM_REL, /* 16 or 32-bit PC-relative displacement */ - PARAM_REL8, /* 8-bit PC-relative displacement */ - PARAM_MEM_OFFS, /* 16 or 32-bit mem offset */ - PARAM_PREIMP, /* prefix with implicit register */ - PARAM_SREG, /* segment register */ - PARAM_CREG, /* control register */ - PARAM_DREG, /* debug register */ - PARAM_TREG, /* test register */ - PARAM_1, /* used by shift/rotate instructions */ - PARAM_AL, - PARAM_CL, - PARAM_DL, - PARAM_BL, - PARAM_AH, - PARAM_CH, - PARAM_DH, - PARAM_BH, - PARAM_DX, - PARAM_EAX, /* EAX or AX */ - PARAM_ECX, /* ECX or CX */ - PARAM_EDX, /* EDX or DX */ - PARAM_EBX, /* EBX or BX */ - PARAM_ESP, /* ESP or SP */ - PARAM_EBP, /* EBP or BP */ - PARAM_ESI, /* ESI or SI */ - PARAM_EDI, /* EDI or DI */ - PARAM_XMM0, - PARAM_XMM64, /* 64-bit memory or XMM register */ - PARAM_XMM32, /* 32-bit memory or XMM register */ - PARAM_XMM16 /* 16-bit memory or XMM register */ -}; - -enum -{ - MODRM = 1, - GROUP, - FPU, - OP_SIZE, - ADDR_SIZE, - TWO_BYTE, - PREFIX, - SEG_CS, - SEG_DS, - SEG_ES, - SEG_FS, - SEG_GS, - SEG_SS, - ISREX, - THREE_BYTE /* [prefix] 0f op1 op2 and then mod/rm */ -}; - -#define FLAGS_MASK 0x0ff -#define VAR_NAME 0x100 -#define VAR_NAME4 0x200 -#define ALWAYS64 0x400 -#define SPECIAL64 0x800 -#define SPECIAL64_ENT(x) (SPECIAL64 | ((x) << 24)) -#define GROUP_MOD 0x1000 - -struct I386_OPCODE { - const char *mnemonic; - uint32_t flags; - uint32_t param1; - uint32_t param2; - uint32_t param3; - offs_t dasm_flags; -}; - -struct GROUP_OP { - char mnemonic[32]; - const I386_OPCODE *opcode; -}; - -static const uint8_t *opcode_ptr; -static const uint8_t *opcode_ptr_base; - -static const I386_OPCODE i386_opcode_table1[256] = +const i386_disassembler::I386_OPCODE i386_disassembler::i386_opcode_table1[256] = { // 0x00 {"add", MODRM, PARAM_RM8, PARAM_REG8, 0 }, @@ -283,7 +175,7 @@ static const I386_OPCODE i386_opcode_table1[256] = {"xchg", 0, PARAM_EAX, PARAM_EDI, 0 }, {"cbw\0cwde\0cdqe", VAR_NAME, 0, 0, 0 }, {"cwd\0cdq\0cqo", VAR_NAME, 0, 0, 0 }, - {"call", ALWAYS64, PARAM_ADDR, 0, 0, DASMFLAG_STEP_OVER}, + {"call", ALWAYS64, PARAM_ADDR, 0, 0, STEP_OVER}, {"wait", 0, 0, 0, 0 }, {"pushf\0pushfd\0pushfq",VAR_NAME, 0, 0, 0 }, {"popf\0popfd\0popfq",VAR_NAME, 0, 0, 0 }, @@ -326,20 +218,20 @@ static const I386_OPCODE i386_opcode_table1[256] = // 0xc0 {"groupC0", GROUP, 0, 0, 0 }, {"groupC1", GROUP, 0, 0, 0 }, - {"ret", 0, PARAM_UI16, 0, 0, DASMFLAG_STEP_OUT}, - {"ret", 0, 0, 0, 0, DASMFLAG_STEP_OUT}, + {"ret", 0, PARAM_UI16, 0, 0, STEP_OUT}, + {"ret", 0, 0, 0, 0, STEP_OUT}, {"les", MODRM, PARAM_REG, PARAM_RM, 0 }, {"lds", MODRM, PARAM_REG, PARAM_RM, 0 }, {"mov", MODRM, PARAM_RMPTR8, PARAM_UI8, 0 }, {"mov", MODRM, PARAM_RMPTR, PARAM_IMM, 0 }, {"enter", 0, PARAM_UI16, PARAM_UI8, 0 }, {"leave", 0, 0, 0, 0 }, - {"retf", 0, PARAM_UI16, 0, 0, DASMFLAG_STEP_OUT}, - {"retf", 0, 0, 0, 0, DASMFLAG_STEP_OUT}, - {"int 3", 0, 0, 0, 0, DASMFLAG_STEP_OVER}, - {"int", 0, PARAM_UI8, 0, 0, DASMFLAG_STEP_OVER}, + {"retf", 0, PARAM_UI16, 0, 0, STEP_OUT}, + {"retf", 0, 0, 0, 0, STEP_OUT}, + {"int 3", 0, 0, 0, 0, STEP_OVER}, + {"int", 0, PARAM_UI8, 0, 0, STEP_OVER}, {"into", 0, 0, 0, 0 }, - {"iret", 0, 0, 0, 0, DASMFLAG_STEP_OUT}, + {"iret", 0, 0, 0, 0, STEP_OUT}, // 0xd0 {"groupD0", GROUP, 0, 0, 0 }, {"groupD1", GROUP, 0, 0, 0 }, @@ -358,15 +250,15 @@ static const I386_OPCODE i386_opcode_table1[256] = {"escape", FPU, 0, 0, 0 }, {"escape", FPU, 0, 0, 0 }, // 0xe0 - {"loopne", 0, PARAM_REL8, 0, 0, DASMFLAG_STEP_OVER}, - {"loopz", 0, PARAM_REL8, 0, 0, DASMFLAG_STEP_OVER}, - {"loop", 0, PARAM_REL8, 0, 0, DASMFLAG_STEP_OVER}, + {"loopne", 0, PARAM_REL8, 0, 0, STEP_OVER}, + {"loopz", 0, PARAM_REL8, 0, 0, STEP_OVER}, + {"loop", 0, PARAM_REL8, 0, 0, STEP_OVER}, {"jcxz\0jecxz\0jrcxz",VAR_NAME, PARAM_REL8, 0, 0 }, {"in", 0, PARAM_AL, PARAM_UI8, 0 }, {"in", 0, PARAM_EAX, PARAM_UI8, 0 }, {"out", 0, PARAM_UI8, PARAM_AL, 0 }, {"out", 0, PARAM_UI8, PARAM_EAX, 0 }, - {"call", 0, PARAM_REL, 0, 0, DASMFLAG_STEP_OVER}, + {"call", 0, PARAM_REL, 0, 0, STEP_OVER}, {"jmp", 0, PARAM_REL, 0, 0 }, {"jmp", 0, PARAM_ADDR, 0, 0 }, {"jmp", 0, PARAM_REL8, 0, 0 }, @@ -393,12 +285,12 @@ static const I386_OPCODE i386_opcode_table1[256] = {"groupFF", GROUP, 0, 0, 0 } }; -static const I386_OPCODE x64_opcode_alt[] = +const i386_disassembler::I386_OPCODE i386_disassembler::x64_opcode_alt[] = { {"movsxd", MODRM | ALWAYS64,PARAM_REG, PARAM_RMPTR32, 0 }, }; -static const I386_OPCODE i386_opcode_table2[256] = +const i386_disassembler::I386_OPCODE i386_disassembler::i386_opcode_table2[256] = { // 0x00 {"group0F00", GROUP, 0, 0, 0 }, @@ -724,7 +616,7 @@ static const I386_OPCODE i386_opcode_table2[256] = {"bsr\0" "???\0" "???\0" - "lzcnt", MODRM|VAR_NAME4, PARAM_REG, PARAM_RM, 0, DASMFLAG_STEP_OVER}, + "lzcnt", MODRM|VAR_NAME4, PARAM_REG, PARAM_RM, 0, STEP_OVER}, {"movsx", MODRM, PARAM_REG, PARAM_RMPTR8, 0 }, {"movsx", MODRM, PARAM_REG, PARAM_RMPTR16, 0 }, // 0xc0 @@ -821,7 +713,7 @@ static const I386_OPCODE i386_opcode_table2[256] = {"???", 0, 0, 0, 0 } }; -static const I386_OPCODE i386_opcode_table0F38[256] = +const i386_disassembler::I386_OPCODE i386_disassembler::i386_opcode_table0F38[256] = { // 0x00 {"pshufb\0" @@ -1265,7 +1157,7 @@ static const I386_OPCODE i386_opcode_table0F38[256] = {"???", 0, 0, 0, 0 }, }; -static const I386_OPCODE i386_opcode_table0F3A[256] = +const i386_disassembler::I386_OPCODE i386_disassembler::i386_opcode_table0F3A[256] = { // 0x00 {"???", 0, 0, 0, 0 }, @@ -1613,7 +1505,7 @@ static const I386_OPCODE i386_opcode_table0F3A[256] = {"???", 0, 0, 0, 0 }, }; -static const I386_OPCODE group80_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::group80_table[8] = { {"add", 0, PARAM_RMPTR8, PARAM_UI8, 0 }, {"or", 0, PARAM_RMPTR8, PARAM_UI8, 0 }, @@ -1625,7 +1517,7 @@ static const I386_OPCODE group80_table[8] = {"cmp", 0, PARAM_RMPTR8, PARAM_UI8, 0 } }; -static const I386_OPCODE group81_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::group81_table[8] = { {"add", 0, PARAM_RMPTR, PARAM_IMM, 0 }, {"or", 0, PARAM_RMPTR, PARAM_IMM, 0 }, @@ -1637,7 +1529,7 @@ static const I386_OPCODE group81_table[8] = {"cmp", 0, PARAM_RMPTR, PARAM_IMM, 0 } }; -static const I386_OPCODE group83_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::group83_table[8] = { {"add", 0, PARAM_RMPTR, PARAM_I8, 0 }, {"or", 0, PARAM_RMPTR, PARAM_I8, 0 }, @@ -1649,7 +1541,7 @@ static const I386_OPCODE group83_table[8] = {"cmp", 0, PARAM_RMPTR, PARAM_I8, 0 } }; -static const I386_OPCODE groupC0_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::groupC0_table[8] = { {"rol", 0, PARAM_RMPTR8, PARAM_UI8, 0 }, {"ror", 0, PARAM_RMPTR8, PARAM_UI8, 0 }, @@ -1661,7 +1553,7 @@ static const I386_OPCODE groupC0_table[8] = {"sar", 0, PARAM_RMPTR8, PARAM_UI8, 0 } }; -static const I386_OPCODE groupC1_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::groupC1_table[8] = { {"rol", 0, PARAM_RMPTR, PARAM_UI8, 0 }, {"ror", 0, PARAM_RMPTR, PARAM_UI8, 0 }, @@ -1673,7 +1565,7 @@ static const I386_OPCODE groupC1_table[8] = {"sar", 0, PARAM_RMPTR, PARAM_UI8, 0 } }; -static const I386_OPCODE groupD0_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::groupD0_table[8] = { {"rol", 0, PARAM_RMPTR8, PARAM_1, 0 }, {"ror", 0, PARAM_RMPTR8, PARAM_1, 0 }, @@ -1685,7 +1577,7 @@ static const I386_OPCODE groupD0_table[8] = {"sar", 0, PARAM_RMPTR8, PARAM_1, 0 } }; -static const I386_OPCODE groupD1_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::groupD1_table[8] = { {"rol", 0, PARAM_RMPTR, PARAM_1, 0 }, {"ror", 0, PARAM_RMPTR, PARAM_1, 0 }, @@ -1697,7 +1589,7 @@ static const I386_OPCODE groupD1_table[8] = {"sar", 0, PARAM_RMPTR, PARAM_1, 0 } }; -static const I386_OPCODE groupD2_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::groupD2_table[8] = { {"rol", 0, PARAM_RMPTR8, PARAM_CL, 0 }, {"ror", 0, PARAM_RMPTR8, PARAM_CL, 0 }, @@ -1709,7 +1601,7 @@ static const I386_OPCODE groupD2_table[8] = {"sar", 0, PARAM_RMPTR8, PARAM_CL, 0 } }; -static const I386_OPCODE groupD3_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::groupD3_table[8] = { {"rol", 0, PARAM_RMPTR, PARAM_CL, 0 }, {"ror", 0, PARAM_RMPTR, PARAM_CL, 0 }, @@ -1721,7 +1613,7 @@ static const I386_OPCODE groupD3_table[8] = {"sar", 0, PARAM_RMPTR, PARAM_CL, 0 } }; -static const I386_OPCODE groupF6_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::groupF6_table[8] = { {"test", 0, PARAM_RMPTR8, PARAM_UI8, 0 }, {"test", 0, PARAM_RMPTR8, PARAM_UI8, 0 }, @@ -1733,7 +1625,7 @@ static const I386_OPCODE groupF6_table[8] = {"idiv", 0, PARAM_RMPTR8, 0, 0 } }; -static const I386_OPCODE groupF7_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::groupF7_table[8] = { {"test", 0, PARAM_RMPTR, PARAM_IMM, 0 }, {"test", 0, PARAM_RMPTR, PARAM_IMM, 0 }, @@ -1745,7 +1637,7 @@ static const I386_OPCODE groupF7_table[8] = {"idiv", 0, PARAM_RMPTR, 0, 0 } }; -static const I386_OPCODE groupFE_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::groupFE_table[8] = { {"inc", 0, PARAM_RMPTR8, 0, 0 }, {"dec", 0, PARAM_RMPTR8, 0, 0 }, @@ -1757,19 +1649,19 @@ static const I386_OPCODE groupFE_table[8] = {"???", 0, 0, 0, 0 } }; -static const I386_OPCODE groupFF_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::groupFF_table[8] = { {"inc", 0, PARAM_RMPTR, 0, 0 }, {"dec", 0, PARAM_RMPTR, 0, 0 }, - {"call", ALWAYS64, PARAM_RMPTR, 0, 0, DASMFLAG_STEP_OVER}, - {"call far ptr ",0, PARAM_RM, 0, 0, DASMFLAG_STEP_OVER}, + {"call", ALWAYS64, PARAM_RMPTR, 0, 0, STEP_OVER}, + {"call far ptr ",0, PARAM_RM, 0, 0, STEP_OVER}, {"jmp", ALWAYS64, PARAM_RMPTR, 0, 0 }, {"jmp far ptr ",0, PARAM_RM, 0, 0 }, {"push", 0, PARAM_RMPTR, 0, 0 }, {"???", 0, 0, 0, 0 } }; -static const I386_OPCODE group0F00_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::group0F00_table[8] = { {"sldt", 0, PARAM_RM, 0, 0 }, {"str", 0, PARAM_RM, 0, 0 }, @@ -1781,7 +1673,7 @@ static const I386_OPCODE group0F00_table[8] = {"???", 0, 0, 0, 0 } }; -static const I386_OPCODE group0F01_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::group0F01_table[8] = { {"sgdt", 0, PARAM_RM, 0, 0 }, {"sidt", 0, PARAM_RM, 0, 0 }, @@ -1793,7 +1685,7 @@ static const I386_OPCODE group0F01_table[8] = {"invlpg", 0, PARAM_RM, 0, 0 } }; -static const I386_OPCODE group0F0D_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::group0F0D_table[8] = { {"prefetch", 0, PARAM_RM8, 0, 0 }, {"prefetchw", 0, PARAM_RM8, 0, 0 }, @@ -1805,7 +1697,7 @@ static const I386_OPCODE group0F0D_table[8] = {"???", 0, 0, 0, 0 } }; -static const I386_OPCODE group0F12_table[4] = +const i386_disassembler::I386_OPCODE i386_disassembler::group0F12_table[4] = { { "movlps\0" "movlpd\0" @@ -1825,7 +1717,7 @@ static const I386_OPCODE group0F12_table[4] = "movsldup", VAR_NAME4,PARAM_XMM, PARAM_XMMM, 0 } }; -static const I386_OPCODE group0F16_table[4] = +const i386_disassembler::I386_OPCODE i386_disassembler::group0F16_table[4] = { { "movhps\0" "movhpd\0" @@ -1845,7 +1737,7 @@ static const I386_OPCODE group0F16_table[4] = "movshdup", VAR_NAME4,PARAM_XMM, PARAM_XMMM, 0 } }; -static const I386_OPCODE group0F18_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::group0F18_table[8] = { {"prefetchnta", 0, PARAM_RM8, 0, 0 }, {"prefetch0", 0, PARAM_RM8, 0, 0 }, @@ -1857,7 +1749,7 @@ static const I386_OPCODE group0F18_table[8] = {"???", 0, 0, 0, 0 } }; -static const I386_OPCODE group0F71_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::group0F71_table[8] = { {"???", 0, 0, 0, 0 }, {"???", 0, 0, 0, 0 }, @@ -1869,7 +1761,7 @@ static const I386_OPCODE group0F71_table[8] = {"???", 0, 0, 0, 0 } }; -static const I386_OPCODE group0F72_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::group0F72_table[8] = { {"???", 0, 0, 0, 0 }, {"???", 0, 0, 0, 0 }, @@ -1881,7 +1773,7 @@ static const I386_OPCODE group0F72_table[8] = {"???", 0, 0, 0, 0 } }; -static const I386_OPCODE group0F73_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::group0F73_table[8] = { {"???", 0, 0, 0, 0 }, {"???", 0, 0, 0, 0 }, @@ -1893,7 +1785,7 @@ static const I386_OPCODE group0F73_table[8] = {"pslldq", 0, PARAM_MMX2, PARAM_UI8, 0 }, }; -static const I386_OPCODE group0FAE_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::group0FAE_table[8] = { {"fxsave", 0, PARAM_RM, 0, 0 }, {"fxrstor", 0, PARAM_RM, 0, 0 }, @@ -1906,7 +1798,7 @@ static const I386_OPCODE group0FAE_table[8] = }; -static const I386_OPCODE group0FBA_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::group0FBA_table[8] = { {"???", 0, 0, 0, 0 }, {"???", 0, 0, 0, 0 }, @@ -1918,7 +1810,7 @@ static const I386_OPCODE group0FBA_table[8] = {"btc", 0, PARAM_RM, PARAM_UI8, 0 } }; -static const I386_OPCODE group0FC7_table[8] = +const i386_disassembler::I386_OPCODE i386_disassembler::group0FC7_table[8] = { {"???", 0, 0, 0, 0 }, {"cmpxchg8b", MODRM, PARAM_M64PTR, 0, 0 }, @@ -1933,7 +1825,7 @@ static const I386_OPCODE group0FC7_table[8] = {"vmptrtst", MODRM, PARAM_M64PTR, 0, 0 } }; -static const GROUP_OP group_op_table[] = +const i386_disassembler::GROUP_OP i386_disassembler::group_op_table[] = { { "group80", group80_table }, { "group81", group81_table }, @@ -1964,98 +1856,60 @@ static const GROUP_OP group_op_table[] = -static const char *const i386_reg[3][16] = +const char *const i386_disassembler::i386_reg[3][16] = { {"ax", "cx", "dx", "bx", "sp", "bp", "si", "di", "r8w", "r9w", "r10w","r11w","r12w","r13w","r14w","r15w"}, {"eax", "ecx", "edx", "ebx", "esp", "ebp", "esi", "edi", "r8d", "r9d", "r10d","r11d","r12d","r13d","r14d","r15d"}, {"rax", "rcx", "rdx", "rbx", "rsp", "rbp", "rsi", "rdi", "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15"} }; -static const char *const i386_reg8[8] = {"al", "cl", "dl", "bl", "ah", "ch", "dh", "bh"}; -static const char *const i386_reg8rex[16] = {"al", "cl", "dl", "bl", "spl", "bpl", "sil", "dil", "r8l", "r9l", "r10l", "r11l", "r12l", "r13l", "r14l", "r15l"}; -static const char *const i386_sreg[8] = {"es", "cs", "ss", "ds", "fs", "gs", "???", "???"}; - -static int address_size; -static int operand_size; -static int address_prefix; -static int operand_prefix; -static int max_length; -static uint64_t pc; -static uint8_t modrm; -static uint32_t segment; -static offs_t dasm_flags; -static std::string modrm_string; -static uint8_t rex, regex, sibex, rmex; -static uint8_t pre0f; -static uint8_t curmode; - -#define MODRM_REG1 ((modrm >> 3) & 0x7) -#define MODRM_REG2 (modrm & 0x7) -#define MODRM_MOD ((modrm >> 6) & 0x3) - -static inline uint8_t FETCH(void) +const char *const i386_disassembler::i386_reg8[8] = {"al", "cl", "dl", "bl", "ah", "ch", "dh", "bh"}; +const char *const i386_disassembler::i386_reg8rex[16] = {"al", "cl", "dl", "bl", "spl", "bpl", "sil", "dil", "r8l", "r9l", "r10l", "r11l", "r12l", "r13l", "r14l", "r15l"}; +const char *const i386_disassembler::i386_sreg[8] = {"es", "cs", "ss", "ds", "fs", "gs", "???", "???"}; + +inline uint8_t i386_disassembler::FETCH(offs_t base_pc, offs_t &pc, const data_buffer &opcodes) { - if ((opcode_ptr - opcode_ptr_base) + 1 > max_length) + if ((pc - base_pc) + 1 > max_length) return 0xff; + uint8_t d = opcodes.r8(pc); pc++; - return *opcode_ptr++; + return d; } -#if 0 -static inline uint16_t FETCH16(void) +inline uint16_t i386_disassembler::FETCH16(offs_t base_pc, offs_t &pc, const data_buffer &opcodes) { - uint16_t d; - if ((opcode_ptr - opcode_ptr_base) + 2 > max_length) + if ((pc - base_pc) + 2 > max_length) return 0xffff; - d = opcode_ptr[0] | (opcode_ptr[1] << 8); - opcode_ptr += 2; + uint16_t d = opcodes.r16(pc); pc += 2; return d; } -#endif -static inline uint32_t FETCH32(void) +inline uint32_t i386_disassembler::FETCH32(offs_t base_pc, offs_t &pc, const data_buffer &opcodes) { - uint32_t d; - if ((opcode_ptr - opcode_ptr_base) + 4 > max_length) + if ((pc - base_pc) + 4 > max_length) return 0xffffffff; - d = opcode_ptr[0] | (opcode_ptr[1] << 8) | (opcode_ptr[2] << 16) | (opcode_ptr[3] << 24); - opcode_ptr += 4; + uint32_t d = opcodes.r32(pc); pc += 4; return d; } -static inline uint8_t FETCHD(void) +inline uint8_t i386_disassembler::FETCHD(offs_t base_pc, offs_t &pc, const data_buffer &opcodes) { - if ((opcode_ptr - opcode_ptr_base) + 1 > max_length) - return 0xff; - pc++; - return *opcode_ptr++; + return FETCH(base_pc, pc, opcodes); } -static inline uint16_t FETCHD16(void) +inline uint16_t i386_disassembler::FETCHD16(offs_t base_pc, offs_t &pc, const data_buffer &opcodes) { - uint16_t d; - if ((opcode_ptr - opcode_ptr_base) + 2 > max_length) - return 0xffff; - d = opcode_ptr[0] | (opcode_ptr[1] << 8); - opcode_ptr += 2; - pc += 2; - return d; + return FETCH16(base_pc, pc, opcodes); } -static inline uint32_t FETCHD32(void) +inline uint32_t i386_disassembler::FETCHD32(offs_t base_pc, offs_t &pc, const data_buffer &opcodes) { - uint32_t d; - if ((opcode_ptr - opcode_ptr_base) + 4 > max_length) - return 0xffffffff; - d = opcode_ptr[0] | (opcode_ptr[1] << 8) | (opcode_ptr[2] << 16) | (opcode_ptr[3] << 24); - opcode_ptr += 4; - pc += 4; - return d; + return FETCH32(base_pc, pc, opcodes); } -static char *hexstring(uint32_t value, int digits) +char *i386_disassembler::hexstring(uint32_t value, int digits) { static char buffer[20]; buffer[0] = '0'; @@ -2066,7 +1920,7 @@ static char *hexstring(uint32_t value, int digits) return (buffer[1] >= '0' && buffer[1] <= '9') ? &buffer[1] : &buffer[0]; } -static char *hexstring64(uint32_t lo, uint32_t hi) +char *i386_disassembler::hexstring64(uint32_t lo, uint32_t hi) { static char buffer[40]; buffer[0] = '0'; @@ -2077,15 +1931,15 @@ static char *hexstring64(uint32_t lo, uint32_t hi) return (buffer[1] >= '0' && buffer[1] <= '9') ? &buffer[1] : &buffer[0]; } -static char *hexstringpc(uint64_t pc) +char *i386_disassembler::hexstringpc(uint64_t pc) { - if (curmode == 64) + if (m_config->get_mode() == 64) return hexstring64((uint32_t)pc, (uint32_t)(pc >> 32)); else return hexstring((uint32_t)pc, 0); } -static char *shexstring(uint32_t value, int digits, bool always) +char *i386_disassembler::shexstring(uint32_t value, int digits, bool always) { static char buffer[20]; if (value >= 0x80000000) @@ -2097,18 +1951,18 @@ static char *shexstring(uint32_t value, int digits, bool always) return buffer; } -static void handle_sib_byte(std::ostream &stream, uint8_t mod) +void i386_disassembler::handle_sib_byte(std::ostream &stream, uint8_t mod, offs_t base_pc, offs_t &pc, const data_buffer &opcodes) { uint32_t i32; uint8_t scale, i, base; - uint8_t sib = FETCHD(); + uint8_t sib = FETCHD(base_pc, pc, opcodes); scale = (sib >> 6) & 0x3; i = ((sib >> 3) & 0x7) | sibex; base = (sib & 0x7) | rmex; if (base == 5 && mod == 0) { - i32 = FETCH32(); + i32 = FETCHD32(base_pc, pc, opcodes); util::stream_format(stream, "%s", hexstring(i32, 0)); } else if (base != 5 || mod != 3) util::stream_format(stream, "%s", i386_reg[address_size][base]); @@ -2120,14 +1974,14 @@ static void handle_sib_byte(std::ostream &stream, uint8_t mod) } } -static void handle_modrm(std::ostream &stream) +void i386_disassembler::handle_modrm(std::ostream &stream, offs_t base_pc, offs_t &pc, const data_buffer &opcodes) { int8_t disp8; int16_t disp16; int32_t disp32; uint8_t mod, rm; - modrm = FETCHD(); + modrm = FETCHD(base_pc, pc, opcodes); mod = (modrm >> 6) & 0x3; rm = (modrm & 0x7) | rmex; @@ -2147,38 +2001,38 @@ static void handle_modrm(std::ostream &stream) util::stream_format(stream, "[" ); if( address_size == 2 ) { if ((rm & 7) == 4) - handle_sib_byte(stream, mod ); + handle_sib_byte(stream, mod, base_pc, pc, opcodes); else if ((rm & 7) == 5 && mod == 0) { - disp32 = FETCHD32(); + disp32 = FETCHD32(base_pc, pc, opcodes); util::stream_format(stream, "rip%s", shexstring(disp32, 0, true)); } else util::stream_format(stream, "%s", i386_reg[2][rm]); if( mod == 1 ) { - disp8 = FETCHD(); + disp8 = FETCHD(base_pc, pc, opcodes); if (disp8 != 0) util::stream_format(stream, "%s", shexstring((int32_t)disp8, 0, true) ); } else if( mod == 2 ) { - disp32 = FETCHD32(); + disp32 = FETCHD32(base_pc, pc, opcodes); if (disp32 != 0) util::stream_format(stream, "%s", shexstring(disp32, 0, true) ); } } else if (address_size == 1) { if ((rm & 7) == 4) - handle_sib_byte(stream, mod ); + handle_sib_byte(stream, mod, base_pc, pc, opcodes); else if ((rm & 7) == 5 && mod == 0) { - disp32 = FETCHD32(); - if (curmode == 64) + disp32 = FETCHD32(base_pc, pc, opcodes); + if (m_config->get_mode() == 64) util::stream_format(stream, "eip%s", shexstring(disp32, 0, true) ); else util::stream_format(stream, "%s", hexstring(disp32, 0) ); } else util::stream_format(stream, "%s", i386_reg[1][rm]); if( mod == 1 ) { - disp8 = FETCHD(); + disp8 = FETCHD(base_pc, pc, opcodes); if (disp8 != 0) util::stream_format(stream, "%s", shexstring((int32_t)disp8, 0, true) ); } else if( mod == 2 ) { - disp32 = FETCHD32(); + disp32 = FETCHD32(base_pc, pc, opcodes); if (disp32 != 0) util::stream_format(stream, "%s", shexstring(disp32, 0, true) ); } @@ -2193,7 +2047,7 @@ static void handle_modrm(std::ostream &stream) case 5: util::stream_format(stream, "di" ); break; case 6: if( mod == 0 ) { - disp16 = FETCHD16(); + disp16 = FETCHD16(base_pc, pc, opcodes); util::stream_format(stream, "%s", hexstring((unsigned) (uint16_t) disp16, 0) ); } else { util::stream_format(stream, "bp" ); @@ -2202,11 +2056,11 @@ static void handle_modrm(std::ostream &stream) case 7: util::stream_format(stream, "bx" ); break; } if( mod == 1 ) { - disp8 = FETCHD(); + disp8 = FETCHD(base_pc, pc, opcodes); if (disp8 != 0) util::stream_format(stream, "%s", shexstring((int32_t)disp8, 0, true) ); } else if( mod == 2 ) { - disp16 = FETCHD16(); + disp16 = FETCHD16(base_pc, pc, opcodes); if (disp16 != 0) util::stream_format(stream, "%s", shexstring((int32_t)disp16, 0, true) ); } @@ -2214,14 +2068,14 @@ static void handle_modrm(std::ostream &stream) util::stream_format(stream, "]" ); } -static void handle_modrm(std::string &buffer) +void i386_disassembler::handle_modrm(std::string &buffer, offs_t base_pc, offs_t &pc, const data_buffer &opcodes) { std::stringstream stream; - handle_modrm(stream); + handle_modrm(stream, base_pc, pc, opcodes); buffer = stream.str(); } -static void handle_param(std::ostream &stream, uint32_t param) +void i386_disassembler::handle_param(std::ostream &stream, uint32_t param, offs_t base_pc, offs_t &pc, const data_buffer &opcodes) { uint8_t i8; uint16_t i16; @@ -2235,58 +2089,58 @@ static void handle_param(std::ostream &stream, uint32_t param) switch(param) { case PARAM_REG: - util::stream_format(stream, "%s", i386_reg[operand_size][MODRM_REG1 | regex] ); + util::stream_format(stream, "%s", i386_reg[operand_size][MODRM_REG1() | regex] ); break; case PARAM_REG8: - util::stream_format(stream, "%s", (rex ? i386_reg8rex : i386_reg8)[MODRM_REG1 | regex] ); + util::stream_format(stream, "%s", (rex ? i386_reg8rex : i386_reg8)[MODRM_REG1() | regex] ); break; case PARAM_REG16: - util::stream_format(stream, "%s", i386_reg[0][MODRM_REG1 | regex] ); + util::stream_format(stream, "%s", i386_reg[0][MODRM_REG1() | regex] ); break; case PARAM_REG32: - util::stream_format(stream, "%s", i386_reg[1][MODRM_REG1 | regex] ); + util::stream_format(stream, "%s", i386_reg[1][MODRM_REG1() | regex] ); break; case PARAM_REG3264: - util::stream_format(stream, "%s", i386_reg[(operand_size == 2) ? 2 : 1][MODRM_REG1 | regex] ); + util::stream_format(stream, "%s", i386_reg[(operand_size == 2) ? 2 : 1][MODRM_REG1() | regex] ); break; case PARAM_MMX: if (pre0f == 0x66 || pre0f == 0xf2 || pre0f == 0xf3) - util::stream_format(stream, "xmm%d", MODRM_REG1 | regex ); + util::stream_format(stream, "xmm%d", MODRM_REG1() | regex ); else - util::stream_format(stream, "mm%d", MODRM_REG1 | regex ); + util::stream_format(stream, "mm%d", MODRM_REG1() | regex ); break; case PARAM_MMX2: if (pre0f == 0x66 || pre0f == 0xf2 || pre0f == 0xf3) - util::stream_format(stream, "xmm%d", MODRM_REG2 | regex ); + util::stream_format(stream, "xmm%d", MODRM_REG2() | regex ); else - util::stream_format(stream, "mm%d", MODRM_REG2 | regex ); + util::stream_format(stream, "mm%d", MODRM_REG2() | regex ); break; case PARAM_XMM: - util::stream_format(stream, "xmm%d", MODRM_REG1 | regex ); + util::stream_format(stream, "xmm%d", MODRM_REG1() | regex ); break; case PARAM_REGORXMM: if (pre0f != 0xf2 && pre0f != 0xf3) - util::stream_format(stream, "xmm%d", MODRM_REG1 | regex ); + util::stream_format(stream, "xmm%d", MODRM_REG1() | regex ); else - util::stream_format(stream, "%s", i386_reg[(operand_size == 2) ? 2 : 1][MODRM_REG1 | regex] ); + util::stream_format(stream, "%s", i386_reg[(operand_size == 2) ? 2 : 1][MODRM_REG1() | regex] ); break; case PARAM_REG2_32: - util::stream_format(stream, "%s", i386_reg[1][MODRM_REG2 | rmex] ); + util::stream_format(stream, "%s", i386_reg[1][MODRM_REG2() | rmex] ); break; case PARAM_RM: case PARAM_RMPTR: if( modrm >= 0xc0 ) { - util::stream_format(stream, "%s", i386_reg[operand_size][MODRM_REG2 | rmex] ); + util::stream_format(stream, "%s", i386_reg[operand_size][MODRM_REG2() | rmex] ); } else { if (param == PARAM_RMPTR) { @@ -2304,7 +2158,7 @@ static void handle_param(std::ostream &stream, uint32_t param) case PARAM_RM8: case PARAM_RMPTR8: if( modrm >= 0xc0 ) { - util::stream_format(stream, "%s", (rex ? i386_reg8rex : i386_reg8)[MODRM_REG2 | rmex] ); + util::stream_format(stream, "%s", (rex ? i386_reg8rex : i386_reg8)[MODRM_REG2() | rmex] ); } else { if (param == PARAM_RMPTR8) util::stream_format(stream, "byte ptr " ); @@ -2315,7 +2169,7 @@ static void handle_param(std::ostream &stream, uint32_t param) case PARAM_RM16: case PARAM_RMPTR16: if( modrm >= 0xc0 ) { - util::stream_format(stream, "%s", i386_reg[0][MODRM_REG2 | rmex] ); + util::stream_format(stream, "%s", i386_reg[0][MODRM_REG2() | rmex] ); } else { if (param == PARAM_RMPTR16) util::stream_format(stream, "word ptr " ); @@ -2326,7 +2180,7 @@ static void handle_param(std::ostream &stream, uint32_t param) case PARAM_RM32: case PARAM_RMPTR32: if( modrm >= 0xc0 ) { - util::stream_format(stream, "%s", i386_reg[1][MODRM_REG2 | rmex] ); + util::stream_format(stream, "%s", i386_reg[1][MODRM_REG2() | rmex] ); } else { if (param == PARAM_RMPTR32) util::stream_format(stream, "dword ptr " ); @@ -2337,9 +2191,9 @@ static void handle_param(std::ostream &stream, uint32_t param) case PARAM_RMXMM: if( modrm >= 0xc0 ) { if (pre0f != 0xf2 && pre0f != 0xf3) - util::stream_format(stream, "xmm%d", MODRM_REG2 | rmex ); + util::stream_format(stream, "xmm%d", MODRM_REG2() | rmex ); else - util::stream_format(stream, "%s", i386_reg[(operand_size == 2) ? 2 : 1][MODRM_REG2 | rmex] ); + util::stream_format(stream, "%s", i386_reg[(operand_size == 2) ? 2 : 1][MODRM_REG2() | rmex] ); } else { if (param == PARAM_RMPTR32) util::stream_format(stream, "dword ptr " ); @@ -2361,9 +2215,9 @@ static void handle_param(std::ostream &stream, uint32_t param) case PARAM_MMXM: if( modrm >= 0xc0 ) { if (pre0f == 0x66 || pre0f == 0xf2 || pre0f == 0xf3) - util::stream_format(stream, "xmm%d", MODRM_REG2 | rmex ); + util::stream_format(stream, "xmm%d", MODRM_REG2() | rmex ); else - util::stream_format(stream, "mm%d", MODRM_REG2 | rmex ); + util::stream_format(stream, "mm%d", MODRM_REG2() | rmex ); } else { util::stream_format(stream, "%s", modrm_string ); } @@ -2371,70 +2225,70 @@ static void handle_param(std::ostream &stream, uint32_t param) case PARAM_XMMM: if( modrm >= 0xc0 ) { - util::stream_format(stream, "xmm%d", MODRM_REG2 | rmex ); + util::stream_format(stream, "xmm%d", MODRM_REG2() | rmex ); } else { util::stream_format(stream, "%s", modrm_string ); } break; case PARAM_I4: - i8 = FETCHD(); + i8 = FETCHD(base_pc, pc, opcodes); util::stream_format(stream, "%d", i8 & 0x0f ); break; case PARAM_I8: - i8 = FETCHD(); + i8 = FETCHD(base_pc, pc, opcodes); util::stream_format(stream, "%s", shexstring((int8_t)i8, 0, false) ); break; case PARAM_I16: - i16 = FETCHD16(); + i16 = FETCHD16(base_pc, pc, opcodes); util::stream_format(stream, "%s", shexstring((int16_t)i16, 0, false) ); break; case PARAM_UI8: - i8 = FETCHD(); + i8 = FETCHD(base_pc, pc, opcodes); util::stream_format(stream, "%s", shexstring((uint8_t)i8, 0, false) ); break; case PARAM_UI16: - i16 = FETCHD16(); + i16 = FETCHD16(base_pc, pc, opcodes); util::stream_format(stream, "%s", shexstring((uint16_t)i16, 0, false) ); break; case PARAM_IMM64: if (operand_size == 2) { - uint32_t lo32 = FETCHD32(); - i32 = FETCHD32(); + uint32_t lo32 = FETCHD32(base_pc, pc, opcodes); + i32 = FETCHD32(base_pc, pc, opcodes); util::stream_format(stream, "%s", hexstring64(lo32, i32) ); } else if( operand_size ) { - i32 = FETCHD32(); + i32 = FETCHD32(base_pc, pc, opcodes); util::stream_format(stream, "%s", hexstring(i32, 0) ); } else { - i16 = FETCHD16(); + i16 = FETCHD16(base_pc, pc, opcodes); util::stream_format(stream, "%s", hexstring(i16, 0) ); } break; case PARAM_IMM: if( operand_size ) { - i32 = FETCHD32(); + i32 = FETCHD32(base_pc, pc, opcodes); util::stream_format(stream, "%s", hexstring(i32, 0) ); } else { - i16 = FETCHD16(); + i16 = FETCHD16(base_pc, pc, opcodes); util::stream_format(stream, "%s", hexstring(i16, 0) ); } break; case PARAM_ADDR: if( operand_size ) { - addr = FETCHD32(); - ptr = FETCHD16(); + addr = FETCHD32(base_pc, pc, opcodes); + ptr = FETCHD16(base_pc, pc, opcodes); util::stream_format(stream, "%s:", hexstring(ptr, 4) ); util::stream_format(stream, "%s", hexstring(addr, 0) ); } else { - addr = FETCHD16(); - ptr = FETCHD16(); + addr = FETCHD16(base_pc, pc, opcodes); + ptr = FETCHD16(base_pc, pc, opcodes); util::stream_format(stream, "%s:", hexstring(ptr, 4) ); util::stream_format(stream, "%s", hexstring(addr, 0) ); } @@ -2442,17 +2296,17 @@ static void handle_param(std::ostream &stream, uint32_t param) case PARAM_REL: if( operand_size ) { - d32 = FETCHD32(); + d32 = FETCHD32(base_pc, pc, opcodes); util::stream_format(stream, "%s", hexstringpc(pc + d32) ); } else { /* make sure to keep the relative offset within the segment */ - d16 = FETCHD16(); + d16 = FETCHD16(base_pc, pc, opcodes); util::stream_format(stream, "%s", hexstringpc((pc & 0xFFFF0000) | ((pc + d16) & 0x0000FFFF)) ); } break; case PARAM_REL8: - d8 = FETCHD(); + d8 = FETCHD(base_pc, pc, opcodes); util::stream_format(stream, "%s", hexstringpc(pc + d8) ); break; @@ -2468,10 +2322,10 @@ static void handle_param(std::ostream &stream, uint32_t param) } if( address_size ) { - i32 = FETCHD32(); + i32 = FETCHD32(base_pc, pc, opcodes); util::stream_format(stream, "[%s]", hexstring(i32, 0) ); } else { - i16 = FETCHD16(); + i16 = FETCHD16(base_pc, pc, opcodes); util::stream_format(stream, "[%s]", hexstring(i16, 0) ); } break; @@ -2489,19 +2343,19 @@ static void handle_param(std::ostream &stream, uint32_t param) break; case PARAM_SREG: - util::stream_format(stream, "%s", i386_sreg[MODRM_REG1] ); + util::stream_format(stream, "%s", i386_sreg[MODRM_REG1()] ); break; case PARAM_CREG: - util::stream_format(stream, "cr%d", MODRM_REG1 | regex ); + util::stream_format(stream, "cr%d", MODRM_REG1() | regex ); break; case PARAM_TREG: - util::stream_format(stream, "tr%d", MODRM_REG1 | regex ); + util::stream_format(stream, "tr%d", MODRM_REG1() | regex ); break; case PARAM_DREG: - util::stream_format(stream, "dr%d", MODRM_REG1 | regex ); + util::stream_format(stream, "dr%d", MODRM_REG1() | regex ); break; case PARAM_1: @@ -2536,7 +2390,7 @@ static void handle_param(std::ostream &stream, uint32_t param) } } -static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) +void i386_disassembler::handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2, offs_t base_pc, offs_t &pc, const data_buffer &opcodes) { switch (op1 & 0x7) { @@ -2545,8 +2399,7 @@ static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) if (op2 < 0xc0) { pc--; // adjust fetch pointer, so modrm byte read again - opcode_ptr--; - handle_modrm( modrm_string ); + handle_modrm(modrm_string, base_pc, pc, opcodes); switch ((op2 >> 3) & 0x7) { case 0: util::stream_format(stream, "fadd dword ptr %s", modrm_string); break; @@ -2581,8 +2434,7 @@ static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) if (op2 < 0xc0) { pc--; // adjust fetch pointer, so modrm byte read again - opcode_ptr--; - handle_modrm( modrm_string ); + handle_modrm(modrm_string, base_pc, pc, opcodes); switch ((op2 >> 3) & 0x7) { case 0: util::stream_format(stream, "fld dword ptr %s", modrm_string); break; @@ -2645,8 +2497,7 @@ static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) if (op2 < 0xc0) { pc--; // adjust fetch pointer, so modrm byte read again - opcode_ptr--; - handle_modrm( modrm_string ); + handle_modrm(modrm_string, base_pc, pc, opcodes); switch ((op2 >> 3) & 0x7) { case 0: util::stream_format(stream, "fiadd dword ptr %s", modrm_string); break; @@ -2689,8 +2540,7 @@ static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) if (op2 < 0xc0) { pc--; // adjust fetch pointer, so modrm byte read again - opcode_ptr--; - handle_modrm( modrm_string ); + handle_modrm(modrm_string, base_pc, pc, opcodes); switch ((op2 >> 3) & 0x7) { case 0: util::stream_format(stream, "fild dword ptr %s", modrm_string); break; @@ -2739,8 +2589,7 @@ static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) if (op2 < 0xc0) { pc--; // adjust fetch pointer, so modrm byte read again - opcode_ptr--; - handle_modrm( modrm_string ); + handle_modrm(modrm_string, base_pc, pc, opcodes); switch ((op2 >> 3) & 0x7) { case 0: util::stream_format(stream, "fadd qword ptr %s", modrm_string); break; @@ -2786,8 +2635,7 @@ static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) if (op2 < 0xc0) { pc--; // adjust fetch pointer, so modrm byte read again - opcode_ptr--; - handle_modrm( modrm_string ); + handle_modrm(modrm_string, base_pc, pc, opcodes); switch ((op2 >> 3) & 0x7) { case 0: util::stream_format(stream, "fld qword ptr %s", modrm_string); break; @@ -2830,8 +2678,7 @@ static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) if (op2 < 0xc0) { pc--; // adjust fetch pointer, so modrm byte read again - opcode_ptr--; - handle_modrm( modrm_string ); + handle_modrm(modrm_string, base_pc, pc, opcodes); switch ((op2 >> 3) & 0x7) { case 0: util::stream_format(stream, "fiadd word ptr %s", modrm_string); break; @@ -2879,8 +2726,7 @@ static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) if (op2 < 0xc0) { pc--; // adjust fetch pointer, so modrm byte read again - opcode_ptr--; - handle_modrm( modrm_string ); + handle_modrm(modrm_string, base_pc, pc, opcodes); switch ((op2 >> 3) & 0x7) { case 0: util::stream_format(stream, "fild word ptr %s", modrm_string); break; @@ -2913,7 +2759,7 @@ static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) } } -static void decode_opcode(std::ostream &stream, const I386_OPCODE *op, uint8_t op1) +void i386_disassembler::decode_opcode(std::ostream &stream, const I386_OPCODE *op, uint8_t op1, offs_t base_pc, offs_t &pc, const data_buffer &opcodes) { int i; uint8_t op2; @@ -2924,15 +2770,15 @@ static void decode_opcode(std::ostream &stream, const I386_OPCODE *op, uint8_t o switch( op->flags & FLAGS_MASK ) { case ISREX: - if (curmode == 64) + if (m_config->get_mode() == 64) { rex = op1; operand_size = (op1 & 8) ? 2 : 1; regex = (op1 << 1) & 8; sibex = (op1 << 2) & 8; rmex = (op1 << 3) & 8; - op2 = FETCH(); - decode_opcode(stream, &i386_opcode_table1[op2], op1 ); + op2 = FETCH(base_pc, pc, opcodes); + decode_opcode(stream, &i386_opcode_table1[op2], op1, base_pc, pc, opcodes); return; } break; @@ -2944,37 +2790,37 @@ static void decode_opcode(std::ostream &stream, const I386_OPCODE *op, uint8_t o operand_size ^= 1; operand_prefix = 1; } - op2 = FETCH(); - decode_opcode(stream, &i386_opcode_table1[op2], op2 ); + op2 = FETCH(base_pc, pc, opcodes); + decode_opcode(stream, &i386_opcode_table1[op2], op2, base_pc, pc, opcodes); return; case ADDR_SIZE: rex = regex = sibex = rmex = 0; if(address_prefix == 0) { - if (curmode != 64) + if (m_config->get_mode() != 64) address_size ^= 1; else address_size ^= 3; address_prefix = 1; } - op2 = FETCH(); - decode_opcode(stream, &i386_opcode_table1[op2], op2 ); + op2 = FETCH(base_pc, pc, opcodes); + decode_opcode(stream, &i386_opcode_table1[op2], op2, base_pc, pc, opcodes); return; case TWO_BYTE: - if (&opcode_ptr[-2] >= opcode_ptr_base) - pre0f = opcode_ptr[-2]; - op2 = FETCHD(); - decode_opcode(stream, &i386_opcode_table2[op2], op1 ); + if (pc - 2 >= base_pc) + pre0f = opcodes.r8(pc-2); + op2 = FETCHD(base_pc, pc, opcodes); + decode_opcode(stream, &i386_opcode_table2[op2], op1, base_pc, pc, opcodes); return; case THREE_BYTE: - op2 = FETCHD(); - if (opcode_ptr[-2] == 0x38) - decode_opcode(stream, &i386_opcode_table0F38[op2], op1 ); + op2 = FETCHD(base_pc, pc, opcodes); + if (opcodes.r8(pc-2) == 0x38) + decode_opcode(stream, &i386_opcode_table0F38[op2], op1, base_pc, pc, opcodes); else - decode_opcode(stream, &i386_opcode_table0F3A[op2], op1 ); + decode_opcode(stream, &i386_opcode_table0F3A[op2], op1, base_pc, pc, opcodes); return; case SEG_CS: @@ -2985,43 +2831,43 @@ static void decode_opcode(std::ostream &stream, const I386_OPCODE *op, uint8_t o case SEG_SS: rex = regex = sibex = rmex = 0; segment = op->flags; - op2 = FETCH(); - decode_opcode(stream, &i386_opcode_table1[op2], op2 ); + op2 = FETCH(base_pc, pc, opcodes); + decode_opcode(stream, &i386_opcode_table1[op2], op2, base_pc, pc, opcodes); return; case PREFIX: - op2 = FETCH(); + op2 = FETCH(base_pc, pc, opcodes); if ((op2 != 0x0f) && (op2 != 0x90)) util::stream_format(stream, "%-7s ", op->mnemonic ); if ((op2 == 0x90) && !pre0f) pre0f = op1; - decode_opcode(stream, &i386_opcode_table1[op2], op2 ); + decode_opcode(stream, &i386_opcode_table1[op2], op2, base_pc, pc, opcodes); return; case GROUP: - handle_modrm( modrm_string ); + handle_modrm(modrm_string, base_pc, pc, opcodes); for( i=0; i < ARRAY_LENGTH(group_op_table); i++ ) { if( strcmp(op->mnemonic, group_op_table[i].mnemonic) == 0 ) { if (op->flags & GROUP_MOD) - decode_opcode(stream, &group_op_table[i].opcode[MODRM_MOD], op1 ); + decode_opcode(stream, &group_op_table[i].opcode[MODRM_MOD()], op1, base_pc, pc, opcodes); else - decode_opcode(stream, &group_op_table[i].opcode[MODRM_REG1], op1 ); + decode_opcode(stream, &group_op_table[i].opcode[MODRM_REG1()], op1, base_pc, pc, opcodes); return; } } goto handle_unknown; case FPU: - op2 = FETCHD(); - handle_fpu(stream, op1, op2); + op2 = FETCHD(base_pc, pc, opcodes); + handle_fpu(stream, op1, op2, base_pc, pc, opcodes); return; case MODRM: - handle_modrm( modrm_string ); + handle_modrm(modrm_string, base_pc, pc, opcodes); break; } - if ((op->flags & ALWAYS64) && curmode == 64) + if ((op->flags & ALWAYS64) && m_config->get_mode() == 64) operand_size = 2; if ((op->flags & VAR_NAME) && operand_size > 0) @@ -3044,17 +2890,17 @@ static void decode_opcode(std::ostream &stream, const I386_OPCODE *op, uint8_t o dasm_flags = op->dasm_flags; if( op->param1 != 0 ) { - handle_param(stream, op->param1 ); + handle_param(stream, op->param1, base_pc, pc, opcodes); } if( op->param2 != 0 ) { util::stream_format(stream, "," ); - handle_param(stream, op->param2 ); + handle_param(stream, op->param2, base_pc, pc, opcodes); } if( op->param3 != 0 ) { util::stream_format(stream, "," ); - handle_param(stream, op->param3 ); + handle_param(stream, op->param3, base_pc, pc, opcodes); } return; @@ -3062,12 +2908,12 @@ handle_unknown: util::stream_format(stream, "???"); } -int i386_dasm_one_ex(std::ostream &stream, uint64_t eip, const uint8_t *oprom, int mode) +offs_t i386_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { + offs_t base_pc = pc; uint8_t op; - opcode_ptr = opcode_ptr_base = oprom; - switch(mode) + switch(m_config->get_mode()) { case 1: /* 8086/8088/80186/80188 */ address_size = 0; @@ -3095,37 +2941,24 @@ int i386_dasm_one_ex(std::ostream &stream, uint64_t eip, const uint8_t *oprom, i max_length = 15; break; } - pc = eip; dasm_flags = 0; segment = 0; - curmode = mode; pre0f = 0; rex = regex = sibex = rmex = 0; address_prefix = 0; operand_prefix = 0; - op = FETCH(); + op = FETCH(base_pc, pc, opcodes); - decode_opcode( stream, &i386_opcode_table1[op], op ); - return (pc-eip) | dasm_flags | DASMFLAG_SUPPORTED; -} - -int i386_dasm_one(std::ostream &stream, offs_t eip, const uint8_t *oprom, int mode) -{ - return i386_dasm_one_ex(stream, eip, oprom, mode); -} - -CPU_DISASSEMBLE( x86_16 ) -{ - return i386_dasm_one_ex(stream, pc, oprom, 16); + decode_opcode( stream, &i386_opcode_table1[op], op, base_pc, pc, opcodes); + return (pc-base_pc) | dasm_flags | SUPPORTED; } -CPU_DISASSEMBLE( x86_32 ) +i386_disassembler::i386_disassembler(config *conf) : m_config(conf) { - return i386_dasm_one_ex(stream, pc, oprom, 32); } -CPU_DISASSEMBLE( x86_64 ) +u32 i386_disassembler::opcode_alignment() const { - return i386_dasm_one_ex(stream, pc, oprom, 64); + return 1; } diff --git a/src/devices/cpu/i386/i386dasm.h b/src/devices/cpu/i386/i386dasm.h index 42142bee675..25f5ec0d4d6 100644 --- a/src/devices/cpu/i386/i386dasm.h +++ b/src/devices/cpu/i386/i386dasm.h @@ -1,5 +1,216 @@ // license:BSD-3-Clause // copyright-holders:Ville Linde, Peter Ferrie -extern int i386_dasm_one(std::ostream &stream, uint32_t pc, const uint8_t *oprom, int mode); -extern int i386_dasm_one_ex(std::ostream &stream, uint64_t eip, const uint8_t *oprom, int mode); +#ifndef MAME_CPU_I386_I386DASM_H +#define MAME_CPU_I386_I386DASM_H + +#pragma once + +class i386_disassembler : public util::disasm_interface +{ +public: + class config { + public: + virtual ~config() = default; + virtual int get_mode() const = 0; + }; + + i386_disassembler(config *conf); + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum + { + PARAM_REG = 1, /* 16 or 32-bit register */ + PARAM_REG8, /* 8-bit register */ + PARAM_REG16, /* 16-bit register */ + PARAM_REG32, /* 32-bit register */ + PARAM_REG3264, /* 32-bit or 64-bit register */ + PARAM_REG2_32, /* 32-bit register */ + PARAM_MMX, /* MMX register */ + PARAM_MMX2, /* MMX register in modrm */ + PARAM_XMM, /* XMM register */ + PARAM_RM, /* 16 or 32-bit memory or register */ + PARAM_RM8, /* 8-bit memory or register */ + PARAM_RM16, /* 16-bit memory or register */ + PARAM_RM32, /* 32-bit memory or register */ + PARAM_RMPTR, /* 16 or 32-bit memory or register */ + PARAM_RMPTR8, /* 8-bit memory or register */ + PARAM_RMPTR16, /* 16-bit memory or register */ + PARAM_RMPTR32, /* 32-bit memory or register */ + PARAM_RMXMM, /* 32 or 64-bit memory or register */ + PARAM_REGORXMM, /* 32 or 64-bit register or XMM register */ + PARAM_M64, /* 64-bit memory */ + PARAM_M64PTR, /* 64-bit memory */ + PARAM_MMXM, /* 64-bit memory or MMX register */ + PARAM_XMMM, /* 128-bit memory or XMM register */ + PARAM_I4, /* 4-bit signed immediate */ + PARAM_I8, /* 8-bit signed immediate */ + PARAM_I16, /* 16-bit signed immediate */ + PARAM_UI8, /* 8-bit unsigned immediate */ + PARAM_UI16, /* 16-bit unsigned immediate */ + PARAM_IMM, /* 16 or 32-bit immediate */ + PARAM_IMM64, /* 16, 32 or 64-bit immediate */ + PARAM_ADDR, /* 16:16 or 16:32 address */ + PARAM_REL, /* 16 or 32-bit PC-relative displacement */ + PARAM_REL8, /* 8-bit PC-relative displacement */ + PARAM_MEM_OFFS, /* 16 or 32-bit mem offset */ + PARAM_PREIMP, /* prefix with implicit register */ + PARAM_SREG, /* segment register */ + PARAM_CREG, /* control register */ + PARAM_DREG, /* debug register */ + PARAM_TREG, /* test register */ + PARAM_1, /* used by shift/rotate instructions */ + PARAM_AL, + PARAM_CL, + PARAM_DL, + PARAM_BL, + PARAM_AH, + PARAM_CH, + PARAM_DH, + PARAM_BH, + PARAM_DX, + PARAM_EAX, /* EAX or AX */ + PARAM_ECX, /* ECX or CX */ + PARAM_EDX, /* EDX or DX */ + PARAM_EBX, /* EBX or BX */ + PARAM_ESP, /* ESP or SP */ + PARAM_EBP, /* EBP or BP */ + PARAM_ESI, /* ESI or SI */ + PARAM_EDI, /* EDI or DI */ + PARAM_XMM0, + PARAM_XMM64, /* 64-bit memory or XMM register */ + PARAM_XMM32, /* 32-bit memory or XMM register */ + PARAM_XMM16 /* 16-bit memory or XMM register */ + }; + + enum + { + MODRM = 1, + GROUP, + FPU, + OP_SIZE, + ADDR_SIZE, + TWO_BYTE, + PREFIX, + SEG_CS, + SEG_DS, + SEG_ES, + SEG_FS, + SEG_GS, + SEG_SS, + ISREX, + THREE_BYTE /* [prefix] 0f op1 op2 and then mod/rm */ + }; + + enum { + FLAGS_MASK = 0x0ff, + VAR_NAME = 0x100, + VAR_NAME4 = 0x200, + ALWAYS64 = 0x400, + SPECIAL64 = 0x800, + GROUP_MOD = 0x1000 + }; + + struct I386_OPCODE { + const char *mnemonic; + u32 flags; + u32 param1; + u32 param2; + u32 param3; + offs_t dasm_flags; + }; + + struct GROUP_OP { + char mnemonic[32]; + const I386_OPCODE *opcode; + }; + + static constexpr u32 SPECIAL64_ENT(u32 x) { + return SPECIAL64 | (x << 24); + } + + static const I386_OPCODE i386_opcode_table1[256]; + static const I386_OPCODE x64_opcode_alt[]; + static const I386_OPCODE i386_opcode_table2[256]; + static const I386_OPCODE i386_opcode_table0F38[256]; + static const I386_OPCODE i386_opcode_table0F3A[256]; + static const I386_OPCODE group80_table[8]; + static const I386_OPCODE group81_table[8]; + static const I386_OPCODE group83_table[8]; + static const I386_OPCODE groupC0_table[8]; + static const I386_OPCODE groupC1_table[8]; + static const I386_OPCODE groupD0_table[8]; + static const I386_OPCODE groupD1_table[8]; + static const I386_OPCODE groupD2_table[8]; + static const I386_OPCODE groupD3_table[8]; + static const I386_OPCODE groupF6_table[8]; + static const I386_OPCODE groupF7_table[8]; + static const I386_OPCODE groupFE_table[8]; + static const I386_OPCODE groupFF_table[8]; + static const I386_OPCODE group0F00_table[8]; + static const I386_OPCODE group0F01_table[8]; + static const I386_OPCODE group0F0D_table[8]; + static const I386_OPCODE group0F12_table[4]; + static const I386_OPCODE group0F16_table[4]; + static const I386_OPCODE group0F18_table[8]; + static const I386_OPCODE group0F71_table[8]; + static const I386_OPCODE group0F72_table[8]; + static const I386_OPCODE group0F73_table[8]; + static const I386_OPCODE group0FAE_table[8]; + static const I386_OPCODE group0FBA_table[8]; + static const I386_OPCODE group0FC7_table[8]; + static const GROUP_OP group_op_table[]; + static const char *const i386_reg[3][16]; + static const char *const i386_reg8[8]; + static const char *const i386_reg8rex[16]; + static const char *const i386_sreg[8]; + + config *m_config; + + int address_size; + int operand_size; + int address_prefix; + int operand_prefix; + int max_length; + uint8_t modrm; + uint32_t segment; + offs_t dasm_flags; + std::string modrm_string; + uint8_t rex, regex, sibex, rmex; + uint8_t pre0f; + + inline u8 MODRM_REG1() const { + return (modrm >> 3) & 0x7; + } + + inline u8 MODRM_REG2() const { + return modrm & 0x7; + } + + inline u8 MODRM_MOD() const { + return (modrm >> 6) & 0x7; + } + + inline uint8_t FETCH(offs_t base_pc, offs_t &pc, const data_buffer &opcodes); + inline uint16_t FETCH16(offs_t base_pc, offs_t &pc, const data_buffer &opcodes); + inline uint32_t FETCH32(offs_t base_pc, offs_t &pc, const data_buffer &opcodes); + inline uint8_t FETCHD(offs_t base_pc, offs_t &pc, const data_buffer &opcodes); + inline uint16_t FETCHD16(offs_t base_pc, offs_t &pc, const data_buffer &opcodes); + inline uint32_t FETCHD32(offs_t base_pc, offs_t &pc, const data_buffer &opcodes); + + char *hexstring(uint32_t value, int digits); + char *hexstring64(uint32_t lo, uint32_t hi); + char *hexstringpc(uint64_t pc); + char *shexstring(uint32_t value, int digits, bool always); + void handle_sib_byte(std::ostream &stream, uint8_t mod, offs_t base_pc, offs_t &pc, const data_buffer &opcodes); + void handle_modrm(std::ostream &stream, offs_t base_pc, offs_t &pc, const data_buffer &opcodes); + void handle_modrm(std::string &buffer, offs_t base_pc, offs_t &pc, const data_buffer &opcodes); + void handle_param(std::ostream &stream, uint32_t param, offs_t base_pc, offs_t &pc, const data_buffer &opcodes); + void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2, offs_t base_pc, offs_t &pc, const data_buffer &opcodes); + void decode_opcode(std::ostream &stream, const I386_OPCODE *op, uint8_t op1, offs_t base_pc, offs_t &pc, const data_buffer &opcodes); +}; + +#endif diff --git a/src/devices/cpu/i8008/8008dasm.cpp b/src/devices/cpu/i8008/8008dasm.cpp index 66be08a40b7..88d2cacf88b 100644 --- a/src/devices/cpu/i8008/8008dasm.cpp +++ b/src/devices/cpu/i8008/8008dasm.cpp @@ -9,18 +9,21 @@ *****************************************************************************/ #include "emu.h" +#include "8008dasm.h" -#define OP(A) oprom[(A) - PC] -#define ARG(A) opram[(A) - PC] +const char i8008_disassembler::reg[] = { 'a', 'b', 'c', 'd', 'e', 'h', 'l', 'm' }; +const char i8008_disassembler::flag_names[] = { 'c', 'z', 's', 'p' }; -static const char reg[] = { 'a', 'b', 'c', 'd', 'e', 'h', 'l', 'm' }; -static const char flag_names[] = { 'c', 'z', 's', 'p' }; +u32 i8008_disassembler::opcode_alignment() const +{ + return 1; +} -CPU_DISASSEMBLE(i8008) +offs_t i8008_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { uint32_t flags = 0; unsigned PC = pc; - uint8_t op = OP(pc++); + uint8_t op = opcodes.r8(pc++); switch (op >> 6) { case 0x03: // starting with 11 @@ -65,28 +68,28 @@ CPU_DISASSEMBLE(i8008) case 3 : util::stream_format(stream, "r%c%c",(BIT(op,5) ? 't' : 'f'),flag_names[(op>>3)&3]); break; case 4 : { switch((op >> 3) & 7) { - case 0 : util::stream_format(stream, "adi %02x",ARG(pc)); pc++; break; - case 1 : util::stream_format(stream, "aci %02x",ARG(pc)); pc++; break; - case 2 : util::stream_format(stream, "sui %02x",ARG(pc)); pc++; break; - case 3 : util::stream_format(stream, "sbi %02x",ARG(pc)); pc++; break; - case 4 : util::stream_format(stream, "ndi %02x",ARG(pc)); pc++; break; - case 5 : util::stream_format(stream, "xri %02x",ARG(pc)); pc++; break; - case 6 : util::stream_format(stream, "ori %02x",ARG(pc)); pc++; break; - case 7 : util::stream_format(stream, "cpi %02x",ARG(pc)); pc++; break; + case 0 : util::stream_format(stream, "adi %02x",params.r8(pc)); pc++; break; + case 1 : util::stream_format(stream, "aci %02x",params.r8(pc)); pc++; break; + case 2 : util::stream_format(stream, "sui %02x",params.r8(pc)); pc++; break; + case 3 : util::stream_format(stream, "sbi %02x",params.r8(pc)); pc++; break; + case 4 : util::stream_format(stream, "ndi %02x",params.r8(pc)); pc++; break; + case 5 : util::stream_format(stream, "xri %02x",params.r8(pc)); pc++; break; + case 6 : util::stream_format(stream, "ori %02x",params.r8(pc)); pc++; break; + case 7 : util::stream_format(stream, "cpi %02x",params.r8(pc)); pc++; break; } } break; case 5 : util::stream_format(stream, "rst %02x",(op>>3) & 7); break; - case 6 : util::stream_format(stream, "l%ci %02x",reg[(op >> 3) & 7],ARG(pc)); pc++; break; + case 6 : util::stream_format(stream, "l%ci %02x",reg[(op >> 3) & 7],params.r8(pc)); pc++; break; case 7 : util::stream_format(stream, "ret"); break; } break; case 0x01: // starting with 01 switch(op & 7) { - case 0 : util::stream_format(stream, "j%c%c %02x%02x",(BIT(op,5)? 't' : 'f'),flag_names[(op>>3)&3], ARG(pc+1) & 0x3f,ARG(pc)); pc+=2; break; - case 2 : util::stream_format(stream, "c%c%c %02x%02x",(BIT(op,5)? 't' : 'f'),flag_names[(op>>3)&3], ARG(pc+1) & 0x3f,ARG(pc)); pc+=2; break; - case 4 : util::stream_format(stream, "jmp %02x%02x",ARG(pc+1) & 0x3f,ARG(pc)); pc+=2; break; - case 6 : util::stream_format(stream, "cal %02x%02x",ARG(pc+1) & 0x3f,ARG(pc)); pc+=2; break; + case 0 : util::stream_format(stream, "j%c%c %02x%02x",(BIT(op,5)? 't' : 'f'),flag_names[(op>>3)&3], params.r8(pc+1) & 0x3f,params.r8(pc)); pc+=2; break; + case 2 : util::stream_format(stream, "c%c%c %02x%02x",(BIT(op,5)? 't' : 'f'),flag_names[(op>>3)&3], params.r8(pc+1) & 0x3f,params.r8(pc)); pc+=2; break; + case 4 : util::stream_format(stream, "jmp %02x%02x",params.r8(pc+1) & 0x3f,params.r8(pc)); pc+=2; break; + case 6 : util::stream_format(stream, "cal %02x%02x",params.r8(pc+1) & 0x3f,params.r8(pc)); pc+=2; break; case 1 : case 3 : case 5 : @@ -111,5 +114,5 @@ CPU_DISASSEMBLE(i8008) } break; } - return (pc - PC) | flags | DASMFLAG_SUPPORTED; + return (pc - PC) | flags | SUPPORTED; } diff --git a/src/devices/cpu/i8008/8008dasm.h b/src/devices/cpu/i8008/8008dasm.h new file mode 100644 index 00000000000..a5cb209dda6 --- /dev/null +++ b/src/devices/cpu/i8008/8008dasm.h @@ -0,0 +1,31 @@ +// license:BSD-3-Clause +// copyright-holders:Miodrag Milanovic +/***************************************************************************** + * + * 8008dasm.c + * + * Intel 8008 CPU Disassembly + * + *****************************************************************************/ + +#ifndef MAME_CPU_I8008_8008DASM_H +#define MAME_CPU_I8008_8008DASM_H + +#pragma once + +class i8008_disassembler : public util::disasm_interface +{ +public: + i8008_disassembler() = default; + virtual ~i8008_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char reg[]; + static const char flag_names[]; + +}; + +#endif diff --git a/src/devices/cpu/i8008/i8008.cpp b/src/devices/cpu/i8008/i8008.cpp index 6baa28a766b..b2de40a7109 100644 --- a/src/devices/cpu/i8008/i8008.cpp +++ b/src/devices/cpu/i8008/i8008.cpp @@ -9,6 +9,7 @@ *****************************************************************************/ #include "emu.h" #include "i8008.h" +#include "8008dasm.h" #include "debugger.h" //************************************************************************** @@ -203,34 +204,13 @@ void i8008_device::state_string_export(const device_state_entry &entry, std::str } //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t i8008_device::disasm_min_opcode_bytes() const -{ - return 1; -} - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t i8008_device::disasm_max_opcode_bytes() const -{ - return 3; -} - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t i8008_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *i8008_device::create_disassembler() { - extern CPU_DISASSEMBLE( i8008 ); - return CPU_DISASSEMBLE_NAME(i8008)(this, stream, pc, oprom, opram, options); + return new i8008_disassembler; } //************************************************************************** diff --git a/src/devices/cpu/i8008/i8008.h b/src/devices/cpu/i8008/i8008.h index b6450fcf5e5..f808cc3790b 100644 --- a/src/devices/cpu/i8008/i8008.h +++ b/src/devices/cpu/i8008/i8008.h @@ -42,11 +42,8 @@ protected: virtual void state_export(const device_state_entry &entry) override; virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; - // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void execute_one(int opcode); diff --git a/src/devices/cpu/i8085/8085dasm.cpp b/src/devices/cpu/i8085/8085dasm.cpp index 5f898c86464..73f7b0bea57 100644 --- a/src/devices/cpu/i8085/8085dasm.cpp +++ b/src/devices/cpu/i8085/8085dasm.cpp @@ -8,288 +8,27 @@ *****************************************************************************/ #include "emu.h" +#include "8085dasm.h" -/* 8080/8085A mnemonics were more irritation than information - What would you guess "CP $3456" to mean? It's not compare, - but call if plus ... therefore: */ -//#define Z80_MNEMONICS - -#define OP(A) oprom[(A) - PC] -#define ARG(A) opram[(A) - PC] -#define ARGW(A) (opram[(A) - PC] | (opram[(A) + 1 - PC] << 8)) +u32 i8085_disassembler::opcode_alignment() const +{ + return 1; +} -CPU_DISASSEMBLE(i8085) +offs_t i8085_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - uint32_t flags = 0; + offs_t flags = 0; uint8_t op; - unsigned PC = pc; - switch (op = OP(pc++)) + unsigned prevpc = pc; + switch (op = opcodes.r8(pc++)) { -#ifdef Z80_MNEMONICS - case 0x00: util::stream_format(stream, "nop"); break; - case 0x01: util::stream_format(stream, "ld bc,$%04x", ARGW(pc)); pc+=2; break; - case 0x02: util::stream_format(stream, "ld (bc),a"); break; - case 0x03: util::stream_format(stream, "inc bc"); break; - case 0x04: util::stream_format(stream, "inc b"); break; - case 0x05: util::stream_format(stream, "dec b"); break; - case 0x06: util::stream_format(stream, "ld b,$%02x", ARG(pc)); pc++; break; - case 0x07: util::stream_format(stream, "rlca"); break; - case 0x08: util::stream_format(stream, "sub hl,bc (*)"); break; - case 0x09: util::stream_format(stream, "add hl,bc"); break; - case 0x0a: util::stream_format(stream, "ld a,(bc)"); break; - case 0x0b: util::stream_format(stream, "dec bc"); break; - case 0x0c: util::stream_format(stream, "inc c"); break; - case 0x0d: util::stream_format(stream, "dec c"); break; - case 0x0e: util::stream_format(stream, "ld c,$%02x", ARG(pc)); pc++; break; - case 0x0f: util::stream_format(stream, "rrca"); break; - case 0x10: util::stream_format(stream, "sra hl (*)"); break; - case 0x11: util::stream_format(stream, "ld de,$%04x", ARGW(pc)); pc+=2; break; - case 0x12: util::stream_format(stream, "ld (de),a"); break; - case 0x13: util::stream_format(stream, "inc de"); break; - case 0x14: util::stream_format(stream, "inc d"); break; - case 0x15: util::stream_format(stream, "dec d"); break; - case 0x16: util::stream_format(stream, "ld d,$%02x", ARG(pc)); pc++; break; - case 0x17: util::stream_format(stream, "rla"); break; - case 0x18: util::stream_format(stream, "rl de (*)"); break; - case 0x19: util::stream_format(stream, "add hl,de"); break; - case 0x1a: util::stream_format(stream, "ld a,(de)"); break; - case 0x1b: util::stream_format(stream, "dec de"); break; - case 0x1c: util::stream_format(stream, "inc e"); break; - case 0x1d: util::stream_format(stream, "dec e"); break; - case 0x1e: util::stream_format(stream, "ld e,$%02x", ARG(pc)); pc++; break; - case 0x1f: util::stream_format(stream, "rra"); break; - case 0x20: util::stream_format(stream, "rim"); break; - case 0x21: util::stream_format(stream, "ld hl,$%04x", ARGW(pc)); pc+=2; break; - case 0x22: util::stream_format(stream, "ld ($%04x),hl", ARGW(pc)); pc+=2;break; - case 0x23: util::stream_format(stream, "inc hl"); break; - case 0x24: util::stream_format(stream, "inc h"); break; - case 0x25: util::stream_format(stream, "dec h"); break; - case 0x26: util::stream_format(stream, "ld h,$%02x", ARG(pc)); pc++; break; - case 0x27: util::stream_format(stream, "daa"); break; - case 0x28: util::stream_format(stream, "ld de,hl+$%02x (*)",ARG(pc));pc++;break; - case 0x29: util::stream_format(stream, "add hl,hl"); break; - case 0x2a: util::stream_format(stream, "ld hl,($%04x)", ARGW(pc)); pc+=2;break; - case 0x2b: util::stream_format(stream, "dec hl"); break; - case 0x2c: util::stream_format(stream, "inc l"); break; - case 0x2d: util::stream_format(stream, "dec l"); break; - case 0x2e: util::stream_format(stream, "ld l,$%02x", ARG(pc)); pc++; break; - case 0x2f: util::stream_format(stream, "cpl"); break; - case 0x30: util::stream_format(stream, "sim"); break; - case 0x31: util::stream_format(stream, "ld sp,$%04x", ARGW(pc)); pc+=2; break; - case 0x32: util::stream_format(stream, "ld ($%04x),a", ARGW(pc)); pc+=2; break; - case 0x33: util::stream_format(stream, "inc sp"); break; - case 0x34: util::stream_format(stream, "inc (hl)"); break; - case 0x35: util::stream_format(stream, "dec (hl)"); break; - case 0x36: util::stream_format(stream, "ld (hl),$%02x", ARG(pc)); pc++; break; - case 0x37: util::stream_format(stream, "scf"); break; - case 0x38: util::stream_format(stream, "ld de,sp+$%02x (*)",ARG(pc));pc++;break; - case 0x39: util::stream_format(stream, "add hl,sp"); break; - case 0x3a: util::stream_format(stream, "ld a,($%04x)", ARGW(pc)); pc+=2; break; - case 0x3b: util::stream_format(stream, "dec sp"); break; - case 0x3c: util::stream_format(stream, "inc a"); break; - case 0x3d: util::stream_format(stream, "dec a"); break; - case 0x3e: util::stream_format(stream, "ld a,$%02x", ARG(pc)); pc++; break; - case 0x3f: util::stream_format(stream, "ccf"); break; - case 0x40: util::stream_format(stream, "ld b,b"); break; - case 0x41: util::stream_format(stream, "ld b,c"); break; - case 0x42: util::stream_format(stream, "ld b,d"); break; - case 0x43: util::stream_format(stream, "ld b,e"); break; - case 0x44: util::stream_format(stream, "ld b,h"); break; - case 0x45: util::stream_format(stream, "ld b,l"); break; - case 0x46: util::stream_format(stream, "ld b,(hl)"); break; - case 0x47: util::stream_format(stream, "ld b,a"); break; - case 0x48: util::stream_format(stream, "ld c,b"); break; - case 0x49: util::stream_format(stream, "ld c,c"); break; - case 0x4a: util::stream_format(stream, "ld c,d"); break; - case 0x4b: util::stream_format(stream, "ld c,e"); break; - case 0x4c: util::stream_format(stream, "ld c,h"); break; - case 0x4d: util::stream_format(stream, "ld c,l"); break; - case 0x4e: util::stream_format(stream, "ld c,(hl)"); break; - case 0x4f: util::stream_format(stream, "ld c,a"); break; - case 0x50: util::stream_format(stream, "ld d,b"); break; - case 0x51: util::stream_format(stream, "ld d,c"); break; - case 0x52: util::stream_format(stream, "ld d,d"); break; - case 0x53: util::stream_format(stream, "ld d,e"); break; - case 0x54: util::stream_format(stream, "ld d,h"); break; - case 0x55: util::stream_format(stream, "ld d,l"); break; - case 0x56: util::stream_format(stream, "ld d,(hl)"); break; - case 0x57: util::stream_format(stream, "ld d,a"); break; - case 0x58: util::stream_format(stream, "ld e,b"); break; - case 0x59: util::stream_format(stream, "ld e,c"); break; - case 0x5a: util::stream_format(stream, "ld e,d"); break; - case 0x5b: util::stream_format(stream, "ld e,e"); break; - case 0x5c: util::stream_format(stream, "ld e,h"); break; - case 0x5d: util::stream_format(stream, "ld e,l"); break; - case 0x5e: util::stream_format(stream, "ld e,(hl)"); break; - case 0x5f: util::stream_format(stream, "ld e,a"); break; - case 0x60: util::stream_format(stream, "ld h,b"); break; - case 0x61: util::stream_format(stream, "ld h,c"); break; - case 0x62: util::stream_format(stream, "ld h,d"); break; - case 0x63: util::stream_format(stream, "ld h,e"); break; - case 0x64: util::stream_format(stream, "ld h,h"); break; - case 0x65: util::stream_format(stream, "ld h,l"); break; - case 0x66: util::stream_format(stream, "ld h,(hl)"); break; - case 0x67: util::stream_format(stream, "ld h,a"); break; - case 0x68: util::stream_format(stream, "ld l,b"); break; - case 0x69: util::stream_format(stream, "ld l,c"); break; - case 0x6a: util::stream_format(stream, "ld l,d"); break; - case 0x6b: util::stream_format(stream, "ld l,e"); break; - case 0x6c: util::stream_format(stream, "ld l,h"); break; - case 0x6d: util::stream_format(stream, "ld l,l"); break; - case 0x6e: util::stream_format(stream, "ld l,(hl)"); break; - case 0x6f: util::stream_format(stream, "ld l,a"); break; - case 0x70: util::stream_format(stream, "ld (hl),b"); break; - case 0x71: util::stream_format(stream, "ld (hl),c"); break; - case 0x72: util::stream_format(stream, "ld (hl),d"); break; - case 0x73: util::stream_format(stream, "ld (hl),e"); break; - case 0x74: util::stream_format(stream, "ld (hl),h"); break; - case 0x75: util::stream_format(stream, "ld (hl),l"); break; - case 0x76: util::stream_format(stream, "halt"); break; - case 0x77: util::stream_format(stream, "ld (hl),a"); break; - case 0x78: util::stream_format(stream, "ld a,b"); break; - case 0x79: util::stream_format(stream, "ld a,c"); break; - case 0x7a: util::stream_format(stream, "ld a,d"); break; - case 0x7b: util::stream_format(stream, "ld a,e"); break; - case 0x7c: util::stream_format(stream, "ld a,h"); break; - case 0x7d: util::stream_format(stream, "ld a,l"); break; - case 0x7e: util::stream_format(stream, "ld a,(hl)"); break; - case 0x7f: util::stream_format(stream, "ld a,a"); break; - case 0x80: util::stream_format(stream, "add a,b"); break; - case 0x81: util::stream_format(stream, "add a,c"); break; - case 0x82: util::stream_format(stream, "add a,d"); break; - case 0x83: util::stream_format(stream, "add a,e"); break; - case 0x84: util::stream_format(stream, "add a,h"); break; - case 0x85: util::stream_format(stream, "add a,l"); break; - case 0x86: util::stream_format(stream, "add a,(hl)"); break; - case 0x87: util::stream_format(stream, "add a,a"); break; - case 0x88: util::stream_format(stream, "adc a,b"); break; - case 0x89: util::stream_format(stream, "adc a,c"); break; - case 0x8a: util::stream_format(stream, "adc a,d"); break; - case 0x8b: util::stream_format(stream, "adc a,e"); break; - case 0x8c: util::stream_format(stream, "adc a,h"); break; - case 0x8d: util::stream_format(stream, "adc a,l"); break; - case 0x8e: util::stream_format(stream, "adc a,(hl)"); break; - case 0x8f: util::stream_format(stream, "adc a,a"); break; - case 0x90: util::stream_format(stream, "sub b"); break; - case 0x91: util::stream_format(stream, "sub c"); break; - case 0x92: util::stream_format(stream, "sub d"); break; - case 0x93: util::stream_format(stream, "sub e"); break; - case 0x94: util::stream_format(stream, "sub h"); break; - case 0x95: util::stream_format(stream, "sub l"); break; - case 0x96: util::stream_format(stream, "sub (hl)"); break; - case 0x97: util::stream_format(stream, "sub a"); break; - case 0x98: util::stream_format(stream, "sbc a,b"); break; - case 0x99: util::stream_format(stream, "sbc a,c"); break; - case 0x9a: util::stream_format(stream, "sbc a,d"); break; - case 0x9b: util::stream_format(stream, "sbc a,e"); break; - case 0x9c: util::stream_format(stream, "sbc a,h"); break; - case 0x9d: util::stream_format(stream, "sbc a,l"); break; - case 0x9e: util::stream_format(stream, "sbc a,(hl)"); break; - case 0x9f: util::stream_format(stream, "sbc a,a"); break; - case 0xa0: util::stream_format(stream, "and b"); break; - case 0xa1: util::stream_format(stream, "and c"); break; - case 0xa2: util::stream_format(stream, "and d"); break; - case 0xa3: util::stream_format(stream, "and e"); break; - case 0xa4: util::stream_format(stream, "and h"); break; - case 0xa5: util::stream_format(stream, "and l"); break; - case 0xa6: util::stream_format(stream, "and (hl)"); break; - case 0xa7: util::stream_format(stream, "and a"); break; - case 0xa8: util::stream_format(stream, "xor b"); break; - case 0xa9: util::stream_format(stream, "xor c"); break; - case 0xaa: util::stream_format(stream, "xor d"); break; - case 0xab: util::stream_format(stream, "xor e"); break; - case 0xac: util::stream_format(stream, "xor h"); break; - case 0xad: util::stream_format(stream, "xor l"); break; - case 0xae: util::stream_format(stream, "xor (hl)"); break; - case 0xaf: util::stream_format(stream, "xor a"); break; - case 0xb0: util::stream_format(stream, "or b"); break; - case 0xb1: util::stream_format(stream, "or c"); break; - case 0xb2: util::stream_format(stream, "or d"); break; - case 0xb3: util::stream_format(stream, "or e"); break; - case 0xb4: util::stream_format(stream, "or h"); break; - case 0xb5: util::stream_format(stream, "or l"); break; - case 0xb6: util::stream_format(stream, "or (hl)"); break; - case 0xb7: util::stream_format(stream, "or a"); break; - case 0xb8: util::stream_format(stream, "cp b"); break; - case 0xb9: util::stream_format(stream, "cp c"); break; - case 0xba: util::stream_format(stream, "cp d"); break; - case 0xbb: util::stream_format(stream, "cp e"); break; - case 0xbc: util::stream_format(stream, "cp h"); break; - case 0xbd: util::stream_format(stream, "cp l"); break; - case 0xbe: util::stream_format(stream, "cp (hl)"); break; - case 0xbf: util::stream_format(stream, "cp a"); break; - case 0xc0: util::stream_format(stream, "ret nz"); flags = DASMFLAG_STEP_OUT; break; - case 0xc1: util::stream_format(stream, "pop bc"); break; - case 0xc2: util::stream_format(stream, "jp nz,$%04x", ARGW(pc)); pc+=2; break; - case 0xc3: util::stream_format(stream, "jp $%04x", ARGW(pc)); pc+=2; break; - case 0xc4: util::stream_format(stream, "call nz,$%04x", ARGW(pc)); pc+=2; flags = DASMFLAG_STEP_OVER; break; - case 0xc5: util::stream_format(stream, "push bc"); break; - case 0xc6: util::stream_format(stream, "add a,$%02x", ARG(pc)); pc++; break; - case 0xc7: util::stream_format(stream, "rst $00"); flags = DASMFLAG_STEP_OVER; break; - case 0xc8: util::stream_format(stream, "ret z"); flags = DASMFLAG_STEP_OUT; break; - case 0xc9: util::stream_format(stream, "ret"); flags = DASMFLAG_STEP_OUT; break; - case 0xca: util::stream_format(stream, "jp z,$%04x", ARGW(pc)); pc+=2; break; - case 0xcb: util::stream_format(stream, "rst v,$40 (*)"); flags = DASMFLAG_STEP_OVER; break; - case 0xcc: util::stream_format(stream, "call z,$%04x", ARGW(pc)); pc+=2; flags = DASMFLAG_STEP_OVER; break; - case 0xcd: util::stream_format(stream, "call $%04x", ARGW(pc)); pc+=2; flags = DASMFLAG_STEP_OVER; break; - case 0xce: util::stream_format(stream, "adc a,$%02x", ARG(pc)); pc++; break; - case 0xcf: util::stream_format(stream, "rst $08"); flags = DASMFLAG_STEP_OVER; break; - case 0xd0: util::stream_format(stream, "ret nc"); flags = DASMFLAG_STEP_OUT; break; - case 0xd1: util::stream_format(stream, "pop de"); break; - case 0xd2: util::stream_format(stream, "jp nc,$%04x", ARGW(pc)); pc+=2; break; - case 0xd3: util::stream_format(stream, "out ($%02x),a", ARG(pc)); pc++; break; - case 0xd4: util::stream_format(stream, "call nc,$%04x", ARGW(pc)); pc+=2; flags = DASMFLAG_STEP_OVER; break; - case 0xd5: util::stream_format(stream, "push de"); break; - case 0xd6: util::stream_format(stream, "sub $%02x", ARG(pc)); pc++; break; - case 0xd7: util::stream_format(stream, "rst $10"); flags = DASMFLAG_STEP_OVER; break; - case 0xd8: util::stream_format(stream, "ret c"); break; - case 0xd9: util::stream_format(stream, "ld (de),hl (*)"); break; - case 0xda: util::stream_format(stream, "jp c,$%04x", ARGW(pc)); pc+=2; break; - case 0xdb: util::stream_format(stream, "in a,($%02x)", ARG(pc)); pc++; break; - case 0xdc: util::stream_format(stream, "call c,$%04x", ARGW(pc)); pc+=2; flags = DASMFLAG_STEP_OVER; break; - case 0xdd: util::stream_format(stream, "jp nx,$%04x (*)",ARGW(pc));pc+=2;break; - case 0xde: util::stream_format(stream, "sub $%02x", ARG(pc)); pc++; break; - case 0xdf: util::stream_format(stream, "rst $18"); flags = DASMFLAG_STEP_OVER; break; - case 0xe0: util::stream_format(stream, "ret pe"); break; - case 0xe1: util::stream_format(stream, "pop hl"); break; - case 0xe2: util::stream_format(stream, "jp pe,$%04x", ARGW(pc)); pc+=2; break; - case 0xe3: util::stream_format(stream, "ex (sp),hl"); break; - case 0xe4: util::stream_format(stream, "call pe,$%04x", ARGW(pc)); pc+=2; flags = DASMFLAG_STEP_OVER; break; - case 0xe5: util::stream_format(stream, "push hl"); break; - case 0xe6: util::stream_format(stream, "and $%02x", ARG(pc)); pc++; break; - case 0xe7: util::stream_format(stream, "rst $20"); flags = DASMFLAG_STEP_OVER; break; - case 0xe8: util::stream_format(stream, "ret po"); break; - case 0xe9: util::stream_format(stream, "jp (hl)"); break; - case 0xea: util::stream_format(stream, "jp po,$%04x", ARGW(pc)); pc+=2; break; - case 0xeb: util::stream_format(stream, "ex de,hl"); break; - case 0xec: util::stream_format(stream, "call po,$%04x", ARGW(pc)); pc+=2; flags = DASMFLAG_STEP_OVER; break; - case 0xed: util::stream_format(stream, "ld hl,(de) (*)"); break; - case 0xee: util::stream_format(stream, "xor $%02x", ARG(pc)); pc++; break; - case 0xef: util::stream_format(stream, "rst $28"); flags = DASMFLAG_STEP_OVER; break; - case 0xf0: util::stream_format(stream, "ret p"); break; - case 0xf1: util::stream_format(stream, "pop af"); break; - case 0xf2: util::stream_format(stream, "jp p,$%04x", ARGW(pc)); pc+=2; break; - case 0xf3: util::stream_format(stream, "di"); break; - case 0xf4: util::stream_format(stream, "cp $%04x", ARGW(pc)); pc+=2; break; - case 0xf5: util::stream_format(stream, "push af"); break; - case 0xf6: util::stream_format(stream, "or $%02x", ARG(pc)); pc++; break; - case 0xf7: util::stream_format(stream, "rst $30"); flags = DASMFLAG_STEP_OVER; break; - case 0xf8: util::stream_format(stream, "ret m"); break; - case 0xf9: util::stream_format(stream, "ld sp,hl"); break; - case 0xfa: util::stream_format(stream, "jp m,$%04x", ARGW(pc)); pc+=2; break; - case 0xfb: util::stream_format(stream, "ei"); break; - case 0xfc: util::stream_format(stream, "call m,$%04x", ARGW(pc)); pc+=2; flags = DASMFLAG_STEP_OVER; break; - case 0xfd: util::stream_format(stream, "jp x,$%04x (*)",ARGW(pc));pc+=2; break; - case 0xfe: util::stream_format(stream, "cp $%02x", ARG(pc)); pc++; break; - case 0xff: util::stream_format(stream, "rst $38"); flags = DASMFLAG_STEP_OVER; break; -#else case 0x00: util::stream_format(stream, "nop"); break; - case 0x01: util::stream_format(stream, "lxi b,$%04x", ARGW(pc)); pc+=2; break; + case 0x01: util::stream_format(stream, "lxi b,$%04x", params.r16(pc)); pc+=2; break; case 0x02: util::stream_format(stream, "stax b"); break; case 0x03: util::stream_format(stream, "inx b"); break; case 0x04: util::stream_format(stream, "inr b"); break; case 0x05: util::stream_format(stream, "dcr b"); break; - case 0x06: util::stream_format(stream, "mvi b,$%02x", ARG(pc)); pc++; break; + case 0x06: util::stream_format(stream, "mvi b,$%02x", params.r8(pc)); pc++; break; case 0x07: util::stream_format(stream, "rlc"); break; case 0x08: util::stream_format(stream, "dsub (*)"); break; case 0x09: util::stream_format(stream, "dad b"); break; @@ -297,15 +36,15 @@ CPU_DISASSEMBLE(i8085) case 0x0b: util::stream_format(stream, "dcx b"); break; case 0x0c: util::stream_format(stream, "inr c"); break; case 0x0d: util::stream_format(stream, "dcr c"); break; - case 0x0e: util::stream_format(stream, "mvi c,$%02x", ARG(pc)); pc++; break; + case 0x0e: util::stream_format(stream, "mvi c,$%02x", params.r8(pc)); pc++; break; case 0x0f: util::stream_format(stream, "rrc"); break; case 0x10: util::stream_format(stream, "asrh (*)"); break; - case 0x11: util::stream_format(stream, "lxi d,$%04x", ARGW(pc)); pc+=2; break; + case 0x11: util::stream_format(stream, "lxi d,$%04x", params.r16(pc)); pc+=2; break; case 0x12: util::stream_format(stream, "stax d"); break; case 0x13: util::stream_format(stream, "inx d"); break; case 0x14: util::stream_format(stream, "inr d"); break; case 0x15: util::stream_format(stream, "dcr d"); break; - case 0x16: util::stream_format(stream, "mvi d,$%02x", ARG(pc)); pc++; break; + case 0x16: util::stream_format(stream, "mvi d,$%02x", params.r8(pc)); pc++; break; case 0x17: util::stream_format(stream, "ral"); break; case 0x18: util::stream_format(stream, "rlde (*)"); break; case 0x19: util::stream_format(stream, "dad d"); break; @@ -313,39 +52,39 @@ CPU_DISASSEMBLE(i8085) case 0x1b: util::stream_format(stream, "dcx d"); break; case 0x1c: util::stream_format(stream, "inr e"); break; case 0x1d: util::stream_format(stream, "dcr e"); break; - case 0x1e: util::stream_format(stream, "mvi e,$%02x", ARG(pc)); pc++; break; + case 0x1e: util::stream_format(stream, "mvi e,$%02x", params.r8(pc)); pc++; break; case 0x1f: util::stream_format(stream, "rar"); break; case 0x20: util::stream_format(stream, "rim"); break; - case 0x21: util::stream_format(stream, "lxi h,$%04x", ARGW(pc)); pc+=2; break; - case 0x22: util::stream_format(stream, "shld $%04x", ARGW(pc)); pc+=2; break; + case 0x21: util::stream_format(stream, "lxi h,$%04x", params.r16(pc)); pc+=2; break; + case 0x22: util::stream_format(stream, "shld $%04x", params.r16(pc)); pc+=2; break; case 0x23: util::stream_format(stream, "inx h"); break; case 0x24: util::stream_format(stream, "inr h"); break; case 0x25: util::stream_format(stream, "dcr h"); break; - case 0x26: util::stream_format(stream, "mvi h,$%02x", ARG(pc)); pc++; break; + case 0x26: util::stream_format(stream, "mvi h,$%02x", params.r8(pc)); pc++; break; case 0x27: util::stream_format(stream, "daa"); break; - case 0x28: util::stream_format(stream, "ldeh $%02x (*)", ARG(pc)); pc++; break; + case 0x28: util::stream_format(stream, "ldeh $%02x (*)", params.r8(pc)); pc++; break; case 0x29: util::stream_format(stream, "dad h"); break; - case 0x2a: util::stream_format(stream, "lhld $%04x", ARGW(pc)); pc+=2; break; + case 0x2a: util::stream_format(stream, "lhld $%04x", params.r16(pc)); pc+=2; break; case 0x2b: util::stream_format(stream, "dcx h"); break; case 0x2c: util::stream_format(stream, "inr l"); break; case 0x2d: util::stream_format(stream, "dcr l"); break; - case 0x2e: util::stream_format(stream, "mvi l,$%02x", ARG(pc)); pc++; break; + case 0x2e: util::stream_format(stream, "mvi l,$%02x", params.r8(pc)); pc++; break; case 0x2f: util::stream_format(stream, "cma"); break; case 0x30: util::stream_format(stream, "sim"); break; - case 0x31: util::stream_format(stream, "lxi sp,$%04x", ARGW(pc)); pc+=2; break; - case 0x32: util::stream_format(stream, "stax $%04x", ARGW(pc)); pc+=2; break; + case 0x31: util::stream_format(stream, "lxi sp,$%04x", params.r16(pc)); pc+=2; break; + case 0x32: util::stream_format(stream, "stax $%04x", params.r16(pc)); pc+=2; break; case 0x33: util::stream_format(stream, "inx sp"); break; case 0x34: util::stream_format(stream, "inr m"); break; case 0x35: util::stream_format(stream, "dcr m"); break; - case 0x36: util::stream_format(stream, "mvi m,$%02x", ARG(pc)); pc++; break; + case 0x36: util::stream_format(stream, "mvi m,$%02x", params.r8(pc)); pc++; break; case 0x37: util::stream_format(stream, "stc"); break; - case 0x38: util::stream_format(stream, "ldes $%02x (*)", ARG(pc)); pc++; break; - case 0x39: util::stream_format(stream, "dad sp"); break; - case 0x3a: util::stream_format(stream, "ldax $%04x", ARGW(pc)); pc+=2; break; + case 0x38: util::stream_format(stream, "ldes $%02x (*)", params.r8(pc)); pc++; break; + case 0x39: util::stream_format(stream, "dad sp"); break; + case 0x3a: util::stream_format(stream, "ldax $%04x", params.r16(pc)); pc+=2; break; case 0x3b: util::stream_format(stream, "dcx sp"); break; case 0x3c: util::stream_format(stream, "inr a"); break; case 0x3d: util::stream_format(stream, "dcr a"); break; - case 0x3e: util::stream_format(stream, "mvi a,$%02x", ARG(pc)); pc++; break; + case 0x3e: util::stream_format(stream, "mvi a,$%02x", params.r8(pc)); pc++; break; case 0x3f: util::stream_format(stream, "cmc"); break; case 0x40: util::stream_format(stream, "mov b,b"); break; case 0x41: util::stream_format(stream, "mov b,c"); break; @@ -475,71 +214,70 @@ CPU_DISASSEMBLE(i8085) case 0xbd: util::stream_format(stream, "cmp l"); break; case 0xbe: util::stream_format(stream, "cmp m"); break; case 0xbf: util::stream_format(stream, "cmp a"); break; - case 0xc0: util::stream_format(stream, "rnz"); flags = DASMFLAG_STEP_OUT; break; + case 0xc0: util::stream_format(stream, "rnz"); flags = STEP_OUT; break; case 0xc1: util::stream_format(stream, "pop b"); break; - case 0xc2: util::stream_format(stream, "jnz $%04x", ARGW(pc)); pc+=2; break; - case 0xc3: util::stream_format(stream, "jmp $%04x", ARGW(pc)); pc+=2; break; - case 0xc4: util::stream_format(stream, "cnz $%04x", ARGW(pc)); pc+=2; flags = DASMFLAG_STEP_OVER; break; + case 0xc2: util::stream_format(stream, "jnz $%04x", params.r16(pc)); pc+=2; break; + case 0xc3: util::stream_format(stream, "jmp $%04x", params.r16(pc)); pc+=2; break; + case 0xc4: util::stream_format(stream, "cnz $%04x", params.r16(pc)); pc+=2; flags = STEP_OVER; break; case 0xc5: util::stream_format(stream, "push b"); break; - case 0xc6: util::stream_format(stream, "adi $%02x", ARG(pc)); pc++; break; - case 0xc7: util::stream_format(stream, "rst 0"); flags = DASMFLAG_STEP_OVER; break; - case 0xc8: util::stream_format(stream, "rz"); flags = DASMFLAG_STEP_OUT; break; - case 0xc9: util::stream_format(stream, "ret"); flags = DASMFLAG_STEP_OUT; break; - case 0xca: util::stream_format(stream, "jz $%04x", ARGW(pc)); pc+=2; break; - case 0xcb: util::stream_format(stream, "rstv 8 (*)"); flags = DASMFLAG_STEP_OVER; break; - case 0xcc: util::stream_format(stream, "cz $%04x", ARGW(pc)); pc+=2; flags = DASMFLAG_STEP_OVER; break; - case 0xcd: util::stream_format(stream, "call $%04x", ARGW(pc)); pc+=2; flags = DASMFLAG_STEP_OVER; break; - case 0xce: util::stream_format(stream, "aci $%02x", ARG(pc)); pc++; break; - case 0xcf: util::stream_format(stream, "rst 1"); flags = DASMFLAG_STEP_OVER; break; - case 0xd0: util::stream_format(stream, "rnc"); flags = DASMFLAG_STEP_OUT; break; + case 0xc6: util::stream_format(stream, "adi $%02x", params.r8(pc)); pc++; break; + case 0xc7: util::stream_format(stream, "rst 0"); flags = STEP_OVER; break; + case 0xc8: util::stream_format(stream, "rz"); flags = STEP_OUT; break; + case 0xc9: util::stream_format(stream, "ret"); flags = STEP_OUT; break; + case 0xca: util::stream_format(stream, "jz $%04x", params.r16(pc)); pc+=2; break; + case 0xcb: util::stream_format(stream, "rstv 8 (*)"); flags = STEP_OVER; break; + case 0xcc: util::stream_format(stream, "cz $%04x", params.r16(pc)); pc+=2; flags = STEP_OVER; break; + case 0xcd: util::stream_format(stream, "call $%04x", params.r16(pc)); pc+=2; flags = STEP_OVER; break; + case 0xce: util::stream_format(stream, "aci $%02x", params.r8(pc)); pc++; break; + case 0xcf: util::stream_format(stream, "rst 1"); flags = STEP_OVER; break; + case 0xd0: util::stream_format(stream, "rnc"); flags = STEP_OUT; break; case 0xd1: util::stream_format(stream, "pop d"); break; - case 0xd2: util::stream_format(stream, "jnc $%04x", ARGW(pc)); pc+=2; break; - case 0xd3: util::stream_format(stream, "out $%02x", ARG(pc)); pc++; break; - case 0xd4: util::stream_format(stream, "cnc $%04x", ARGW(pc)); pc+=2; flags = DASMFLAG_STEP_OVER; break; + case 0xd2: util::stream_format(stream, "jnc $%04x", params.r16(pc)); pc+=2; break; + case 0xd3: util::stream_format(stream, "out $%02x", params.r8(pc)); pc++; break; + case 0xd4: util::stream_format(stream, "cnc $%04x", params.r16(pc)); pc+=2; flags = STEP_OVER; break; case 0xd5: util::stream_format(stream, "push d"); break; - case 0xd6: util::stream_format(stream, "sui $%02x", ARG(pc)); pc++; break; - case 0xd7: util::stream_format(stream, "rst 2"); flags = DASMFLAG_STEP_OVER; break; - case 0xd8: util::stream_format(stream, "rc"); flags = DASMFLAG_STEP_OUT; break; + case 0xd6: util::stream_format(stream, "sui $%02x", params.r8(pc)); pc++; break; + case 0xd7: util::stream_format(stream, "rst 2"); flags = STEP_OVER; break; + case 0xd8: util::stream_format(stream, "rc"); flags = STEP_OUT; break; case 0xd9: util::stream_format(stream, "shlx d (*)"); break; - case 0xda: util::stream_format(stream, "jc $%04x", ARGW(pc)); pc+=2; break; - case 0xdb: util::stream_format(stream, "in $%02x", ARG(pc)); pc++; break; - case 0xdc: util::stream_format(stream, "cc $%04x", ARGW(pc)); pc+=2; flags = DASMFLAG_STEP_OVER; break; - case 0xdd: util::stream_format(stream, "jnx $%04x (*)", ARGW(pc)); pc+=2; break; - case 0xde: util::stream_format(stream, "sbi $%02x", ARG(pc)); pc++; break; - case 0xdf: util::stream_format(stream, "rst 3"); flags = DASMFLAG_STEP_OVER; break; - case 0xe0: util::stream_format(stream, "rpo"); flags = DASMFLAG_STEP_OUT; break; + case 0xda: util::stream_format(stream, "jc $%04x", params.r16(pc)); pc+=2; break; + case 0xdb: util::stream_format(stream, "in $%02x", params.r8(pc)); pc++; break; + case 0xdc: util::stream_format(stream, "cc $%04x", params.r16(pc)); pc+=2; flags = STEP_OVER; break; + case 0xdd: util::stream_format(stream, "jnx $%04x (*)", params.r16(pc)); pc+=2; break; + case 0xde: util::stream_format(stream, "sbi $%02x", params.r8(pc)); pc++; break; + case 0xdf: util::stream_format(stream, "rst 3"); flags = STEP_OVER; break; + case 0xe0: util::stream_format(stream, "rpo"); flags = STEP_OUT; break; case 0xe1: util::stream_format(stream, "pop h"); break; - case 0xe2: util::stream_format(stream, "jpo $%04x", ARGW(pc)); pc+=2; break; + case 0xe2: util::stream_format(stream, "jpo $%04x", params.r16(pc)); pc+=2; break; case 0xe3: util::stream_format(stream, "xthl"); break; - case 0xe4: util::stream_format(stream, "cpo $%04x", ARGW(pc)); pc+=2; flags = DASMFLAG_STEP_OVER; break; + case 0xe4: util::stream_format(stream, "cpo $%04x", params.r16(pc)); pc+=2; flags = STEP_OVER; break; case 0xe5: util::stream_format(stream, "push h"); break; - case 0xe6: util::stream_format(stream, "ani $%02x", ARG(pc)); pc++; break; - case 0xe7: util::stream_format(stream, "rst 4"); flags = DASMFLAG_STEP_OVER; break; - case 0xe8: util::stream_format(stream, "rpe"); flags = DASMFLAG_STEP_OUT; break; + case 0xe6: util::stream_format(stream, "ani $%02x", params.r8(pc)); pc++; break; + case 0xe7: util::stream_format(stream, "rst 4"); flags = STEP_OVER; break; + case 0xe8: util::stream_format(stream, "rpe"); flags = STEP_OUT; break; case 0xe9: util::stream_format(stream, "pchl"); break; - case 0xea: util::stream_format(stream, "jpe $%04x", ARGW(pc)); pc+=2; break; + case 0xea: util::stream_format(stream, "jpe $%04x", params.r16(pc)); pc+=2; break; case 0xeb: util::stream_format(stream, "xchg"); break; - case 0xec: util::stream_format(stream, "cpe $%04x", ARGW(pc)); pc+=2; flags = DASMFLAG_STEP_OVER; break; + case 0xec: util::stream_format(stream, "cpe $%04x", params.r16(pc)); pc+=2; flags = STEP_OVER; break; case 0xed: util::stream_format(stream, "lhlx d (*)"); break; - case 0xee: util::stream_format(stream, "xri $%02x", ARG(pc)); pc++; break; - case 0xef: util::stream_format(stream, "rst 5"); flags = DASMFLAG_STEP_OVER; break; - case 0xf0: util::stream_format(stream, "rp"); flags = DASMFLAG_STEP_OUT; break; - case 0xf1: util::stream_format(stream, "pop psw"); break; - case 0xf2: util::stream_format(stream, "jp $%04x", ARGW(pc)); pc+=2; break; + case 0xee: util::stream_format(stream, "xri $%02x", params.r8(pc)); pc++; break; + case 0xef: util::stream_format(stream, "rst 5"); flags = STEP_OVER; break; + case 0xf0: util::stream_format(stream, "rp"); flags = STEP_OUT; break; + case 0xf1: util::stream_format(stream, "pop psw"); break; + case 0xf2: util::stream_format(stream, "jp $%04x", params.r16(pc)); pc+=2; break; case 0xf3: util::stream_format(stream, "di"); break; - case 0xf4: util::stream_format(stream, "cp $%04x", ARGW(pc)); pc+=2; break; - case 0xf5: util::stream_format(stream, "push psw"); break; - case 0xf6: util::stream_format(stream, "ori $%02x", ARG(pc)); pc++; break; - case 0xf7: util::stream_format(stream, "rst 6"); flags = DASMFLAG_STEP_OVER; break; - case 0xf8: util::stream_format(stream, "rm"); flags = DASMFLAG_STEP_OUT; break; + case 0xf4: util::stream_format(stream, "cp $%04x", params.r16(pc)); pc+=2; break; + case 0xf5: util::stream_format(stream, "push psw"); break; + case 0xf6: util::stream_format(stream, "ori $%02x", params.r8(pc)); pc++; break; + case 0xf7: util::stream_format(stream, "rst 6"); flags = STEP_OVER; break; + case 0xf8: util::stream_format(stream, "rm"); flags = STEP_OUT; break; case 0xf9: util::stream_format(stream, "sphl"); break; - case 0xfa: util::stream_format(stream, "jm $%04x", ARGW(pc)); pc+=2; break; + case 0xfa: util::stream_format(stream, "jm $%04x", params.r16(pc)); pc+=2; break; case 0xfb: util::stream_format(stream, "ei"); break; - case 0xfc: util::stream_format(stream, "cm $%04x", ARGW(pc)); pc+=2; flags = DASMFLAG_STEP_OVER; break; - case 0xfd: util::stream_format(stream, "jx $%04x (*)", ARGW(pc)); pc+=2; break; - case 0xfe: util::stream_format(stream, "cpi $%02x", ARG(pc)); pc++; break; - case 0xff: util::stream_format(stream, "rst 7"); flags = DASMFLAG_STEP_OVER; break; -#endif + case 0xfc: util::stream_format(stream, "cm $%04x", params.r16(pc)); pc+=2; flags = STEP_OVER; break; + case 0xfd: util::stream_format(stream, "jx $%04x (*)", params.r16(pc)); pc+=2; break; + case 0xfe: util::stream_format(stream, "cpi $%02x", params.r8(pc)); pc++; break; + case 0xff: util::stream_format(stream, "rst 7"); flags = STEP_OVER; break; } - return (pc - PC) | flags | DASMFLAG_SUPPORTED; + return (pc - prevpc) | flags | SUPPORTED; } diff --git a/src/devices/cpu/i8085/8085dasm.h b/src/devices/cpu/i8085/8085dasm.h new file mode 100644 index 00000000000..b2466ec2d05 --- /dev/null +++ b/src/devices/cpu/i8085/8085dasm.h @@ -0,0 +1,25 @@ +// license:BSD-3-Clause +// copyright-holders:Juergen Buchmueller +/***************************************************************************** + * + * 8085dasm.c + * Portable I8085A disassembler + * + *****************************************************************************/ + +#ifndef MAME_CPU_I8085_8085DASM_H +#define MAME_CPU_I8085_8085DASM_H + +#pragma once + +class i8085_disassembler : public util::disasm_interface +{ +public: + i8085_disassembler() = default; + virtual ~i8085_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/i8085/i8085.cpp b/src/devices/cpu/i8085/i8085.cpp index 9b89bd0af8d..9a3e7df76c4 100644 --- a/src/devices/cpu/i8085/i8085.cpp +++ b/src/devices/cpu/i8085/i8085.cpp @@ -109,6 +109,7 @@ #include "emu.h" #include "debugger.h" #include "i8085.h" +#include "8085dasm.h" #define VERBOSE 0 #include "logmacro.h" @@ -456,10 +457,9 @@ void i8085a_cpu_device::state_string_export(const device_state_entry &entry, std } } -offs_t i8085a_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +util::disasm_interface *i8085a_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( i8085 ); - return CPU_DISASSEMBLE_NAME(i8085)(this, stream, pc, oprom, opram, options); + return new i8085_disassembler; } diff --git a/src/devices/cpu/i8085/i8085.h b/src/devices/cpu/i8085/i8085.h index 1e60c9f8447..d144283f934 100644 --- a/src/devices/cpu/i8085/i8085.h +++ b/src/devices/cpu/i8085/i8085.h @@ -100,9 +100,7 @@ protected: virtual void state_import(const device_state_entry &entry) override; // device_disasm_interface overrides - virtual u32 disasm_min_opcode_bytes() const override { return 1; } - virtual u32 disasm_max_opcode_bytes() const override { return 3; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; enum { diff --git a/src/devices/cpu/i8089/i8089.cpp b/src/devices/cpu/i8089/i8089.cpp index 93a38ceea04..075cc92fb18 100644 --- a/src/devices/cpu/i8089/i8089.cpp +++ b/src/devices/cpu/i8089/i8089.cpp @@ -8,6 +8,7 @@ #include "emu.h" #include "i8089.h" +#include "i8089_dasm.h" #include "i8089_channel.h" @@ -144,13 +145,12 @@ device_memory_interface::space_config_vector i8089_device::memory_space_config() } //------------------------------------------------- -// disasm_disassemble - disassembler +// disassemble - disassembler //------------------------------------------------- -offs_t i8089_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *i8089_device::create_disassembler() { - extern CPU_DISASSEMBLE(i8089); - return CPU_DISASSEMBLE_NAME(i8089)(this, stream, pc, oprom, opram, options); + return new i8089_disassembler(); } //------------------------------------------------- diff --git a/src/devices/cpu/i8089/i8089.h b/src/devices/cpu/i8089/i8089.h index 3465c444e2a..812ae99a733 100644 --- a/src/devices/cpu/i8089/i8089.h +++ b/src/devices/cpu/i8089/i8089.h @@ -82,9 +82,7 @@ protected: address_space_config m_io_config; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 7; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // device_state_interface overrides virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; diff --git a/src/devices/cpu/i8089/i8089_dasm.cpp b/src/devices/cpu/i8089/i8089_dasm.cpp index 1159602289b..8e45053b1ba 100644 --- a/src/devices/cpu/i8089/i8089_dasm.cpp +++ b/src/devices/cpu/i8089/i8089_dasm.cpp @@ -9,439 +9,385 @@ ***************************************************************************/ #include "emu.h" +#include "i8089_dasm.h" -class i8089_instruction +const char *const i8089_disassembler::m_reg[] = { -public: - i8089_instruction(offs_t pc, const uint8_t *oprom) : - m_oprom(oprom), m_ppc(pc), m_pc(0), m_flags(DASMFLAG_SUPPORTED) - { - // instruction - m_brp = (oprom[0] >> 5) & 0x07; - m_wb = (oprom[0] >> 3) & 0x03; - m_aa = (oprom[0] >> 1) & 0x03; - m_w = (oprom[0] >> 0) & 0x01; - m_opc = (oprom[1] >> 2) & 0x3f; - m_mm = (oprom[1] >> 0) & 0x03; - - // clear buffers - memset(m_buffer, 0, sizeof(m_buffer)); - memset(m_offset, 0, sizeof(m_offset)); - - // start working - disassemble(); - } - - char *buffer() { return m_buffer; } - int length() const { return m_pc; } - int flags() const { return m_flags; } - -private: - const uint8_t *m_oprom; + "ga", "gb", "gc", "bc", "tp", "ix", "cc", "mc" +}; - char m_buffer[256]; - char m_offset[100]; - offs_t m_ppc; - int m_pc; +// fetch 1-byte value +uint8_t i8089_disassembler::fetch_value8() +{ + uint8_t i = m_opcodes->r8(m_pc); + m_pc += 1; + return i; +} - // decoded instruction - int m_brp; - int m_wb; - int m_aa; - int m_w; - int m_opc; - int m_mm; +// fetch 2-byte value +uint16_t i8089_disassembler::fetch_value16() +{ + uint16_t i = m_opcodes->r16(m_pc); + m_pc += 2; + return i; +} - // dasm flags - int m_flags; +// fetch a 1 or 2 byte immediate value +uint16_t i8089_disassembler::fetch_immediate() +{ + return (m_wb & 1) ? fetch_value8() : fetch_value16(); +} - // register names - static const char *m_reg[]; +// print memory offset +std::string i8089_disassembler::offset() +{ + const char *mm_name[] = { "ga", "gb", "gc", "pp" }; - // register index - enum + switch (m_aa) { - GA, // 20-bit general purpose address a - GB, // 20-bit general purpose address b - GC, // 20-bit general purpose address c - BC, // byte count - TP, // 20-bit task pointer - IX, // index - CC, // mask compare - MC // channel control - }; - - // fetch 1-byte value - uint8_t fetch_value8() - { - uint8_t i = m_oprom[m_pc]; - m_pc += 1; - return i; + case 0: return util::string_format("[%s]", mm_name[m_mm]); + case 1: return util::string_format("[%s].%02x", mm_name[m_mm], m_opcodes->r8(m_pc++)); + case 2: return util::string_format("[%s+ix]", mm_name[m_mm]); + case 3: return util::string_format("[%s+ix+]", mm_name[m_mm]); } + return ""; +} - // fetch 2-byte value - uint16_t fetch_value16() - { - uint16_t i = m_oprom[m_pc] | m_oprom[m_pc + 1] << 8; - m_pc += 2; - return i; - } +// invalid instruction +std::string i8089_disassembler::invalid() +{ + return "???"; +} - // fetch a 1 or 2 byte immediate value - uint16_t fetch_immediate() - { - return (m_wb & 1) ? fetch_value8() : fetch_value16(); - } +// to register or memory from immediate +std::string i8089_disassembler::from_i(std::string instr8, std::string instr16, std::string target) +{ + if (m_w == 0 && m_wb == 1) + return util::string_format("%s %s, %02x", instr8, target, fetch_immediate()); + else if (m_w == 1 && m_wb == 2) + return util::string_format("%s %s, %04x", instr16, target, fetch_immediate()); + else + return invalid(); +} - // print memory offset - void offset() - { - const char *mm_name[] = { "ga", "gb", "gc", "pp" }; +// register, immediate +std::string i8089_disassembler::inst_ri(std::string instr8, std::string instr16) +{ + if (m_mm == 0) + return from_i(instr8, instr16, m_reg[m_brp]); + else + return invalid(); +} - switch (m_aa) - { - case 0: sprintf(m_offset, "[%s]", mm_name[m_mm]); break; - case 1: sprintf(m_offset, "[%s].%02x", mm_name[m_mm], m_oprom[m_pc]); m_pc++; break; - case 2: sprintf(m_offset, "[%s+ix]", mm_name[m_mm]); break; - case 3: sprintf(m_offset, "[%s+ix+]", mm_name[m_mm]); break; - } - } +// register +std::string i8089_disassembler::inst_r(std::string instr) +{ + if (m_mm == 0 && m_w == 0 && m_aa == 0 && m_wb == 0) + return util::string_format("%s %s", instr, m_reg[m_brp]); + else + return invalid(); +} - // to register or memory from immediate - void from_i(const char *instr8, const char *instr16, const char *target) - { - if (m_w == 0 && m_wb == 1) - sprintf(m_buffer, "%s %s, %02x", instr8, target, fetch_immediate()); - else if (m_w == 1 && m_wb == 2) - sprintf(m_buffer, "%s %s, %04x", instr16, target, fetch_immediate()); - else - invalid(); - } +// jump register +std::string i8089_disassembler::inst_jr(std::string instr8, std::string instr16) +{ + uint16_t i = fetch_immediate(); + if (m_mm == 0 && m_w == 0 && m_wb == 1) + return util::string_format("%s %s, %05x", instr8, m_reg[m_brp], m_pc + (int8_t) i); + else if (m_mm == 0 && m_w == 0 && m_wb == 2) + return util::string_format("%s %s, %05x", instr16, m_reg[m_brp], m_pc + (int16_t) i); + else + return invalid(); +} - // register, immediate - void inst_ri(const char *instr8, const char *instr16) - { - if (m_mm == 0) - from_i(instr8, instr16, m_reg[m_brp]); - else - invalid(); - } +// memory immediate +std::string i8089_disassembler::inst_mi(std::string instr8, std::string instr16) +{ + std::string off = offset(); + return from_i(instr8, instr16, off); +} - // register - void inst_r(const char *instr) - { - if (m_mm == 0 && m_w == 0 && m_aa == 0 && m_wb == 0) - sprintf(m_buffer, "%s %s", instr, m_reg[m_brp]); - else - invalid(); - } +// register memory +std::string i8089_disassembler::inst_rm(std::string instr8, std::string instr16) +{ + std::string off = offset(); + if (m_w == 0 && m_wb == 0) + return util::string_format("%s %s, %s", instr8, m_reg[m_brp], off); + else if (m_w == 1 && m_wb == 0) + return util::string_format("%s %s, %s", instr16, m_reg[m_brp], off); + else + return invalid(); +} - // jump register - void inst_jr(const char *instr8, const char *instr16) - { - uint16_t i = fetch_immediate(); - if (m_mm == 0 && m_w == 0 && m_wb == 1) - sprintf(m_buffer, "%s %s, %05x", instr8, m_reg[m_brp], m_ppc + m_pc + (int8_t) i); - else if (m_mm == 0 && m_w == 0 && m_wb == 2) - sprintf(m_buffer, "%s %s, %05x", instr16, m_reg[m_brp], m_ppc + m_pc + (int16_t) i); - else - invalid(); - } +// jump memory +std::string i8089_disassembler::inst_jm(std::string jump8short, std::string jump8long) +{ + std::string off = offset(); + uint16_t i = fetch_immediate(); + if (m_w == 0 && m_wb == 1 && m_brp == 0) + return util::string_format("%s %s, %05x", jump8short, off, m_pc + (int8_t) i); + else if (m_w == 0 && m_wb == 2 && m_brp == 0) + return util::string_format("%s %s, %05x", jump8long, off, m_pc + (int16_t) i); + else + return invalid(); +} - // memory immediate - void inst_mi(const char *instr8, const char *instr16) - { - offset(); - from_i(instr8, instr16, m_offset); - } +// jump memory bit +std::string i8089_disassembler::inst_jmb(std::string jump8short, std::string jump8long) +{ + std::string off = offset(); + uint16_t i = fetch_immediate(); + if (m_w == 0 && m_wb == 1) + return util::string_format("%s %s, %d, %05x", jump8short, off, m_brp, m_pc + (int8_t) i); + else if (m_w == 0 && m_wb == 2) + return util::string_format("%s %s, %d, %05x", jump8long, off, m_brp, m_pc + (int16_t) i); + else + return invalid(); +} - // register memory - void inst_rm(const char *instr8, const char *instr16) - { - offset(); - if (m_w == 0 && m_wb == 0) - sprintf(m_buffer, "%s %s, %s", instr8, m_reg[m_brp], m_offset); - else if (m_w == 1 && m_wb == 0) - sprintf(m_buffer, "%s %s, %s", instr16, m_reg[m_brp], m_offset); - else - invalid(); - } +// memory register +std::string i8089_disassembler::inst_mr(std::string instr8, std::string instr16) +{ + std::string off = offset(); + if (m_w == 0 && m_wb == 0) + return util::string_format("%s %s, %s", instr8, off, m_reg[m_brp]); + else if (m_w == 1 && m_wb == 0) + return util::string_format("%s %s, %s", instr16, off, m_reg[m_brp]); + else + return invalid(); +} - // jump memory - void inst_jm(const char *jump8short, const char *jump8long) - { - offset(); - uint16_t i = fetch_immediate(); - if (m_w == 0 && m_wb == 1 && m_brp == 0) - sprintf(m_buffer, "%s %s, %05x", jump8short, m_offset, m_ppc + m_pc + (int8_t) i); - else if (m_w == 0 && m_wb == 2 && m_brp == 0) - sprintf(m_buffer, "%s %s, %05x", jump8long, m_offset, m_ppc + m_pc + (int16_t) i); - else - invalid(); - } +// pointer memory +std::string i8089_disassembler::inst_pm(std::string instr16) +{ + std::string off = offset(); + if (m_w == 1 && m_wb == 0) + return util::string_format("%s %s, %s", instr16, m_reg[m_brp], off); + else + return invalid(); +} - // jump memory bit - void inst_jmb(const char *jump8short, const char *jump8long) - { - offset(); - uint16_t i = fetch_immediate(); - if (m_w == 0 && m_wb == 1) - sprintf(m_buffer, "%s %s, %d, %05x", jump8short, m_offset, m_brp, m_ppc + m_pc + (int8_t) i); - else if (m_w == 0 && m_wb == 2) - sprintf(m_buffer, "%s %s, %d, %05x", jump8long, m_offset, m_brp, m_ppc + m_pc + (int16_t) i); - else - invalid(); - } +// memory pointer +std::string i8089_disassembler::inst_mp(std::string instr16) +{ + std::string off = offset(); + if (m_w == 1 && m_wb == 0) + return util::string_format("%s %s, %s", instr16, off, m_reg[m_brp]); + else + return invalid(); +} - // memory register - void inst_mr(const char *instr8, const char *instr16) - { - offset(); - if (m_w == 0 && m_wb == 0) - sprintf(m_buffer, "%s %s, %s", instr8, m_offset, m_reg[m_brp]); - else if (m_w == 1 && m_wb == 0) - sprintf(m_buffer, "%s %s, %s", instr16, m_offset, m_reg[m_brp]); - else - invalid(); - } +// jump memory +std::string i8089_disassembler::inst_j16(std::string jump8short, std::string jump16short, std::string jump8long, std::string jump16long) +{ + std::string off = offset(); + uint16_t i = fetch_immediate(); + if (m_w == 0 && m_wb == 1) + return util::string_format("%s %s, %05x", jump8short, off, m_pc + (int8_t) i); + else if (m_w == 1 && m_wb == 1) + return util::string_format("%s %s, %05x", jump16short, off, m_pc + (int8_t) i); + else if (m_w == 0 && m_wb == 2) + return util::string_format("%s %s, %05x", jump8long, off, m_pc + (int16_t) i); + else if (m_w == 1 && m_wb == 2) + return util::string_format("%s %s, %05x", jump16long, off, m_pc + (int16_t) i); + else + return invalid(); +} - // pointer memory - void inst_pm(const char *instr16) - { - offset(); - if (m_w == 1 && m_wb == 0) - sprintf(m_buffer, "%s %s, %s", instr16, m_reg[m_brp], m_offset); - else - invalid(); - } +// memory +std::string i8089_disassembler::inst_m(std::string instr8, std::string instr16) +{ + std::string off = offset(); + if (m_w == 0 && m_wb == 0) + return util::string_format("%s %s", instr8, off); + else if (m_w == 1 && m_wb == 0) + return util::string_format("%s %s", instr16, off); + else + return invalid(); +} - // memory pointer - void inst_mp(const char *instr16) - { - offset(); - if (m_w == 1 && m_wb == 0) - sprintf(m_buffer, "%s %s, %s", instr16, m_offset, m_reg[m_brp]); - else - invalid(); - } +// memory bit +std::string i8089_disassembler::inst_b(std::string instr) +{ + std::string off = offset(); + if (m_w == 0 && m_wb == 0) + return util::string_format("%s %s, %d", instr, off, m_brp); + else + return invalid(); +} - // jump memory - void inst_j16(const char *jump8short, const char *jump16short, const char *jump8long, const char *jump16long) - { - offset(); - uint16_t i = fetch_immediate(); - if (m_w == 0 && m_wb == 1) - sprintf(m_buffer, "%s %s, %05x", jump8short, m_offset, m_ppc + m_pc + (int8_t) i); - else if (m_w == 1 && m_wb == 1) - sprintf(m_buffer, "%s %s, %05x", jump16short, m_offset, m_ppc + m_pc + (int8_t) i); - else if (m_w == 0 && m_wb == 2) - sprintf(m_buffer, "%s %s, %05x", jump8long, m_offset, m_ppc + m_pc + (int16_t) i); - else if (m_w == 1 && m_wb == 2) - sprintf(m_buffer, "%s %s, %05x", jump16long, m_offset, m_ppc + m_pc + (int16_t) i); - else - invalid(); - } +u32 i8089_disassembler::opcode_alignment() const +{ + return 1; +} - // memory - void inst_m(const char *instr8, const char *instr16) - { - offset(); - if (m_w == 0 && m_wb == 0) - sprintf(m_buffer, "%s %s", instr8, m_offset); - else if (m_w == 1 && m_wb == 0) - sprintf(m_buffer, "%s %s", instr16, m_offset); - else - invalid(); - } +void i8089_disassembler::load_instruction() +{ + // instruction + m_brp = (m_opcodes->r8(m_pc) >> 5) & 0x07; + m_wb = (m_opcodes->r8(m_pc) >> 3) & 0x03; + m_aa = (m_opcodes->r8(m_pc) >> 1) & 0x03; + m_w = (m_opcodes->r8(m_pc) >> 0) & 0x01; + m_opc = (m_opcodes->r8(m_pc+1) >> 2) & 0x3f; + m_mm = (m_opcodes->r8(m_pc+1) >> 0) & 0x03; + m_pc += 2; +} - // memory bit - void inst_b(const char *instr) - { - offset(); - if (m_w == 0 && m_wb == 0) - sprintf(m_buffer, "%s %s, %d", instr, m_offset, m_brp); - else - invalid(); - } +offs_t i8089_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + m_opcodes = &opcodes; + m_pc = pc; + m_flags = SUPPORTED; - // invalid instruction - void invalid() - { - sprintf(m_buffer, "???"); - } + load_instruction(); + stream << do_disassemble(); + return (m_pc - pc) | m_flags; +} - void disassemble() +std::string i8089_disassembler::do_disassemble() +{ + switch (m_opc) { - m_pc += 2; - - switch (m_opc) + case 0x00: + if (m_mm == 0 && m_w == 0 && m_aa == 0 && m_wb == 0) { - case 0x00: - if (m_mm == 0 && m_w == 0 && m_aa == 0 && m_wb == 0) + switch (m_brp) { - switch (m_brp) - { - case 0: sprintf(m_buffer, "nop"); break; - case 1: invalid(); break; - case 2: sprintf(m_buffer, "sintr"); break; - case 3: sprintf(m_buffer, "xfer"); break; - case 4: sprintf(m_buffer, "wid 8, 8"); break; - case 5: sprintf(m_buffer, "wid 8, 16"); break; - case 6: sprintf(m_buffer, "wid 16, 8"); break; - case 7: sprintf(m_buffer, "wid 16, 16"); break; - } + case 0: return util::string_format("nop"); + case 1: return invalid(); break; + case 2: return util::string_format("sintr"); + case 3: return util::string_format("xfer"); + case 4: return util::string_format("wid 8, 8"); + case 5: return util::string_format("wid 8, 16"); + case 6: return util::string_format("wid 16, 8"); + case 7: return util::string_format("wid 16, 16"); } - else - invalid(); - break; + } + else + return invalid(); + break; - case 0x02: - if (m_w == 1 && m_aa == 0 && m_wb == 2) - { - uint16_t offs = fetch_immediate(); - uint16_t segm = fetch_immediate(); - sprintf(m_buffer, "lpdi %s, %05x", m_reg[m_brp], ((segm << 4) + offs) & 0xfffff); - } - else - invalid(); - break; + case 0x02: + if (m_w == 1 && m_aa == 0 && m_wb == 2) + { + uint16_t offs = fetch_immediate(); + uint16_t segm = fetch_immediate(); + return util::string_format("lpdi %s, %05x", m_reg[m_brp], ((segm << 4) + offs) & 0xfffff); + } + else + return invalid(); - case 0x08: - if (m_mm == 0) - { - uint16_t i = fetch_immediate(); - - if (m_w == 0 && m_aa == 0 && m_wb == 1 && m_brp == TP) - sprintf(m_buffer, "jmp %05x", m_ppc + m_pc + (int8_t) i); - else if (m_w == 1 && m_aa == 0 && m_wb == 2 && m_brp == TP) - sprintf(m_buffer, "ljmp %05x", m_ppc + m_pc + (int16_t) i); - else if (m_w == 0 && m_wb == 1) - sprintf(m_buffer, "addbi %s, %02x", m_reg[m_brp], i); - else if (m_w == 1 && m_wb == 2) - sprintf(m_buffer, "addi %s, %04x", m_reg[m_brp], i); - else - invalid(); - } - else - invalid(); - break; - - case 0x09: inst_ri("orbi", "ori"); break; - case 0x0a: inst_ri("andbi", "andi"); break; - case 0x0b: inst_r("not"); break; - case 0x0c: inst_ri("movbi", "movi"); break; - case 0x0e: inst_r("inc"); break; - case 0x0f: inst_r("dec"); break; - case 0x10: inst_jr("jnz", "ljnz"); break; - case 0x11: inst_jr("jz", "ljz"); break; - - case 0x12: - if (m_mm == 0 && m_w == 0 && m_aa == 0 && m_wb == 0 && m_brp == 1) - sprintf(m_buffer, "hlt"); + case 0x08: + if (m_mm == 0) + { + uint16_t i = fetch_immediate(); + + if (m_w == 0 && m_aa == 0 && m_wb == 1 && m_brp == TP) + return util::string_format("jmp %05x", m_pc + (int8_t) i); + else if (m_w == 1 && m_aa == 0 && m_wb == 2 && m_brp == TP) + return util::string_format("ljmp %05x", m_pc + (int16_t) i); + else if (m_w == 0 && m_wb == 1) + return util::string_format("addbi %s, %02x", m_reg[m_brp], i); + else if (m_w == 1 && m_wb == 2) + return util::string_format("addi %s, %04x", m_reg[m_brp], i); else - invalid(); - break; + return invalid(); + } + else + return invalid(); + + case 0x09: return inst_ri("orbi", "ori"); + case 0x0a: return inst_ri("andbi", "andi"); + case 0x0b: return inst_r("not"); + case 0x0c: return inst_ri("movbi", "movi"); + case 0x0e: return inst_r("inc"); + case 0x0f: return inst_r("dec"); + case 0x10: return inst_jr("jnz", "ljnz"); + case 0x11: return inst_jr("jz", "ljz"); + + case 0x12: + if (m_mm == 0 && m_w == 0 && m_aa == 0 && m_wb == 0 && m_brp == 1) + return util::string_format("hlt"); + else + return invalid(); - case 0x13: inst_mi("movbi", "movi"); break; - case 0x20: inst_rm("movb", "mov"); break; - case 0x21: inst_mr("movb", "mov"); break; - case 0x22: inst_pm("lpd"); break; - case 0x23: inst_pm("movp"); break; + case 0x13: return inst_mi("movbi", "movi"); + case 0x20: return inst_rm("movb", "mov"); + case 0x21: return inst_mr("movb", "mov"); + case 0x22: return inst_pm("lpd"); + case 0x23: return inst_pm("movp"); - case 0x24: - if (m_wb == 0) - { - offset(); + case 0x24: + if (m_wb == 0) + { + std::string off = offset(); - auto tmp = new i8089_instruction(m_pc, m_oprom + m_pc); - m_pc += tmp->length(); - std::string sub = tmp->buffer(); + load_instruction(); - if (m_w == 0) - sprintf(m_buffer, "movb %s, %s", sub.c_str(), m_offset); - else - sprintf(m_buffer, "mov %s, %s", sub.c_str(), m_offset); + if (m_opc != 0x33) + return invalid(); + std::string off2 = offset(); - delete(tmp); - } + if (m_w == 0) + return util::string_format("movb %s, %s", off2, off); else - invalid(); - break; + return util::string_format("mov %s, %s", off2, off); + } + else + return invalid(); - case 0x25: - if (m_w == 0 && m_wb == 3 && m_brp == 0) - { - offset(); - uint16_t i = fetch_immediate(); - int displacement = (int8_t) fetch_immediate(); - sprintf(m_buffer, "tsl %s, %02x, %05x", m_offset, i, m_ppc + m_pc + displacement); - } - else - invalid(); - break; + case 0x25: + if (m_w == 0 && m_wb == 3 && m_brp == 0) + { + std::string off = offset(); + uint16_t i = fetch_immediate(); + int displacement = (int8_t) fetch_immediate(); + return util::string_format("tsl %s, %02x, %05x", off, i, m_pc + displacement); + } + else + return invalid(); - case 0x26: inst_mp("movp"); break; + case 0x26: return inst_mp("movp"); - case 0x27: - if (m_w == 1 && m_brp == TP && (m_wb == 1 || m_wb == 2)) - { - offset(); - uint16_t i = fetch_immediate(); + case 0x27: + if (m_w == 1 && m_brp == TP && (m_wb == 1 || m_wb == 2)) + { + std::string off = offset(); + uint16_t i = fetch_immediate(); - if (m_wb == 1) - sprintf(m_buffer, "call %s, %05x", m_offset, m_ppc + m_pc + (int8_t) i); - else if (m_wb == 2) - sprintf(m_buffer, "lcall %s, %05x", m_offset, m_ppc + m_pc + (int16_t) i); + m_flags |= STEP_OVER; - m_flags |= DASMFLAG_STEP_OVER; - } - else - invalid(); - break; - - case 0x28: inst_rm("addb", "add"); break; - case 0x29: inst_rm("orb", "or"); break; - case 0x2a: inst_rm("andb", "and"); break; - case 0x2b: inst_rm("notb", "not"); break; - case 0x2c: inst_jm("jmce", "ljmce"); break; - case 0x2d: inst_jm("jmcne", "ljmcne"); break; - case 0x2e: inst_jmb("jnbt", "ljnbt"); break; - case 0x2f: inst_jmb("jbt", "ljbt"); break; - case 0x30: inst_mi("addbi", "addi"); break; - case 0x31: inst_mi("orbi", "ori"); break; - case 0x32: inst_mi("andbi", "andi"); break; - - case 0x33: - offset(); - sprintf(m_buffer, "%s", m_offset); - break; - - case 0x34: inst_mr("addb", "add"); break; - case 0x35: inst_mr("orb", "or"); break; - case 0x36: inst_mr("andb", "and"); break; - case 0x37: inst_mr("notb", "not"); break; - case 0x38: inst_j16("jnzb", "jnz", "ljnzb", "ljnz"); break; - case 0x39: inst_j16("jzb", "jz", "ljzb", "ljz"); break; - case 0x3a: inst_m("incb", "inc"); break; - case 0x3b: inst_m("decb", "dec"); break; - case 0x3d: inst_b("setb"); break; - case 0x3e: inst_b("clr"); break; - - default: - invalid(); + if (m_wb == 1) + return util::string_format("call %s, %05x", off, m_pc + (int8_t) i); + else if (m_wb == 2) + return util::string_format("lcall %s, %05x", off, m_pc + (int16_t) i); } + else + return invalid(); + + case 0x28: return inst_rm("addb", "add"); + case 0x29: return inst_rm("orb", "or"); + case 0x2a: return inst_rm("andb", "and"); + case 0x2b: return inst_rm("notb", "not"); + case 0x2c: return inst_jm("jmce", "ljmce"); + case 0x2d: return inst_jm("jmcne", "ljmcne"); + case 0x2e: return inst_jmb("jnbt", "ljnbt"); + case 0x2f: return inst_jmb("jbt", "ljbt"); + case 0x30: return inst_mi("addbi", "addi"); + case 0x31: return inst_mi("orbi", "ori"); + case 0x32: return inst_mi("andbi", "andi"); + + case 0x34: return inst_mr("addb", "add"); + case 0x35: return inst_mr("orb", "or"); + case 0x36: return inst_mr("andb", "and"); + case 0x37: return inst_mr("notb", "not"); + case 0x38: return inst_j16("jnzb", "jnz", "ljnzb", "ljnz"); + case 0x39: return inst_j16("jzb", "jz", "ljzb", "ljz"); + case 0x3a: return inst_m("incb", "inc"); + case 0x3b: return inst_m("decb", "dec"); + case 0x3d: return inst_b("setb"); + case 0x3e: return inst_b("clr"); } -}; -const char *i8089_instruction::m_reg[] = -{ - "ga", "gb", "gc", "bc", "tp", "ix", "cc", "mc" -}; - -CPU_DISASSEMBLE(i8089) -{ - std::unique_ptr i = std::make_unique(pc, oprom); - stream << i->buffer(); - offs_t result = i->length() | i->flags(); - return result; + return invalid(); } diff --git a/src/devices/cpu/i8089/i8089_dasm.h b/src/devices/cpu/i8089/i8089_dasm.h new file mode 100644 index 00000000000..cf59d4b483c --- /dev/null +++ b/src/devices/cpu/i8089/i8089_dasm.h @@ -0,0 +1,71 @@ +// license:GPL-2.0+ +// copyright-holders:Dirk Best +/*************************************************************************** + + Intel 8089 I/O Processor + + Disassembler + +***************************************************************************/ + +#ifndef MAME_CPU_I8089_I8089DASM_H +#define MAME_CPU_I8089_I8089DASM_H + +#pragma once + +class i8089_disassembler : public util::disasm_interface +{ +public: + i8089_disassembler() = default; + virtual ~i8089_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + // register index + enum + { + GA, // 20-bit general purpose address a + GB, // 20-bit general purpose address b + GC, // 20-bit general purpose address c + BC, // byte count + TP, // 20-bit task pointer + IX, // index + CC, // mask compare + MC // channel control + }; + + static const char *const m_reg[]; + + uint8_t m_brp, m_wb, m_aa, m_w, m_opc, m_mm; + offs_t m_pc, m_flags; + + const data_buffer *m_opcodes; + + uint8_t fetch_value8(); + uint16_t fetch_value16(); + uint16_t fetch_immediate(); + std::string offset(); + std::string invalid(); + + std::string from_i(std::string instr8, std::string instr16, std::string target); + std::string inst_ri(std::string instr8, std::string instr16); + std::string inst_r(std::string instr); + std::string inst_jr(std::string instr8, std::string instr16); + std::string inst_mi(std::string instr8, std::string instr16); + std::string inst_rm(std::string instr8, std::string instr16); + std::string inst_jm(std::string jump8short, std::string jump8long); + std::string inst_jmb(std::string jump8short, std::string jump8long); + std::string inst_mr(std::string instr8, std::string instr16); + std::string inst_pm(std::string instr16); + std::string inst_mp(std::string instr16); + std::string inst_j16(std::string jump8short, std::string jump16short, std::string jump8long, std::string jump16long); + std::string inst_m(std::string instr8, std::string instr16); + std::string inst_b(std::string instr); + + std::string do_disassemble(); + void load_instruction(); +}; + +#endif diff --git a/src/devices/cpu/i86/i86.cpp b/src/devices/cpu/i86/i86.cpp index 4c4cd49d6ae..19b5317b54a 100644 --- a/src/devices/cpu/i86/i86.cpp +++ b/src/devices/cpu/i86/i86.cpp @@ -570,9 +570,14 @@ void i8086_common_cpu_device::execute_set_input( int inptnum, int state ) } } -offs_t i8086_common_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *i8086_common_cpu_device::create_disassembler() { - return i386_dasm_one(stream, pc, oprom, 1); + return new i386_disassembler(this); +} + +int i8086_common_cpu_device::get_mode() const +{ + return 1; } uint8_t i8086_common_cpu_device::read_port_byte(uint16_t port) diff --git a/src/devices/cpu/i86/i86.h b/src/devices/cpu/i86/i86.h index f6e177c25d9..99ffb6a9f6f 100644 --- a/src/devices/cpu/i86/i86.h +++ b/src/devices/cpu/i86/i86.h @@ -5,6 +5,7 @@ #pragma once +#include ///////////////////////////////////////////////////////////////// @@ -39,7 +40,7 @@ enum }; -class i8086_common_cpu_device : public cpu_device +class i8086_common_cpu_device : public cpu_device, public i386_disassembler::config { public: template static devcb_base &set_lock_handler(device_t &device, Object &&cb) @@ -134,9 +135,8 @@ protected: virtual void execute_set_input(int inputnum, int state) override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 8; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; + virtual int get_mode() const override; // device_state_interface overrides virtual void state_import(const device_state_entry &entry) override; diff --git a/src/devices/cpu/i860/i860.cpp b/src/devices/cpu/i860/i860.cpp index eb22a347f2a..a9d8a3c78b9 100644 --- a/src/devices/cpu/i860/i860.cpp +++ b/src/devices/cpu/i860/i860.cpp @@ -18,6 +18,7 @@ TODO: Separate out i860XR and i860XP (make different types, etc). #include "emu.h" #include "debugger.h" #include "i860.h" +#include "i860dis.h" /* Control register numbers. */ @@ -231,11 +232,9 @@ void i860_cpu_device::device_reset() reset_i860(); } - -offs_t i860_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *i860_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( i860 ); - return CPU_DISASSEMBLE_NAME(i860)(this, stream, pc, oprom, opram, options); + return new i860_disassembler; } diff --git a/src/devices/cpu/i860/i860.h b/src/devices/cpu/i860/i860.h index 3387244858e..05e81407e7c 100644 --- a/src/devices/cpu/i860/i860.h +++ b/src/devices/cpu/i860/i860.h @@ -80,9 +80,7 @@ protected: virtual void state_import(const device_state_entry &entry) override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 4; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/i860/i860dasm.cpp b/src/devices/cpu/i860/i860dasm.cpp deleted file mode 100644 index 03d24e2d2a8..00000000000 --- a/src/devices/cpu/i860/i860dasm.cpp +++ /dev/null @@ -1,378 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:Jason Eckhardt -#include "i860.h" - -/* Sub-group decoders */ -static void i860_dasm_core_dasm(const uint32_t op, char* buffer); -static void i860_dasm_floating_point_dasm(const uint32_t op, char* buffer); -static void i860_dasm_CTRL_dasm(const uint32_t op, char* buffer); - -/* REG-Format Opcodes*/ -static void i860_dasm_ldx(const uint32_t op, char* buffer); -static void i860_dasm_stx(const uint32_t op, char* buffer); -static void i860_dasm_ixfr(const uint32_t op, char* buffer); -static void i860_dasm_fid_fst(const uint32_t op, char* buffer); -static void i860_dasm_flush(const uint32_t op, char* buffer); -static void i860_dasm_pstd(const uint32_t op, char* buffer); -static void i860_dasm_ldc_sdc(const uint32_t op, char* buffer); -static void i860_dasm_bri(const uint32_t op, char* buffer); -static void i860_dasm_trap(const uint32_t op, char* buffer); -static void i860_dasm_bte_btne(const uint32_t op, char* buffer); -static void i860_dasm_pfidy(const uint32_t op, char* buffer); -static void i860_dasm_addu_subu(const uint32_t op, char* buffer); -static void i860_dasm_shl_shr(const uint32_t op, char* buffer); -static void i860_dasm_shrd(const uint32_t op, char* buffer); -static void i860_dasm_bla(const uint32_t op, char* buffer); -static void i860_dasm_shra(const uint32_t op, char* buffer); -static void i860_dasm_and_andh(const uint32_t op, char* buffer); -static void i860_dasm_andnot_andnoth(const uint32_t op, char* buffer); -static void i860_dasm_or_orh(const uint32_t op, char* buffer); -static void i860_dasm_xor_xorh(const uint32_t op, char* buffer); - -/* CORE Escape Opcodes */ -static void i860_dasm_CORE_lock(const uint32_t op, char* buffer); -static void i860_dasm_CORE_calli(const uint32_t op, char* buffer); -static void i860_dasm_CORE_intovr(const uint32_t op, char* buffer); -static void i860_dasm_CORE_unlock(const uint32_t op, char* buffer); - -/* CTRL-Format Opcodes */ -static void i860_dasm_CTRL_br(const uint32_t op, char* buffer); -static void i860_dasm_CTRL_call(const uint32_t op, char* buffer); -static void i860_dasm_CTRL_bc_bct(const uint32_t op, char* buffer); -static void i860_dasm_CTRL_bnc_bnct(const uint32_t op, char* buffer); - -/* Floating-Point Instructions */ - - -CPU_DISASSEMBLE( i860 ) -{ - char tempB[1024] = ""; - - /* Little Endian */ - const uint32_t op = (oprom[3] << 24) | (oprom[2] << 16) | (oprom[1] << 8) | (oprom[0] << 0); - //const uint32_t op = (oprom[2] << 24) | (oprom[3] << 16) | (oprom[0] << 8) | (oprom[1] << 0); /* Mixed Endian */ - //const uint32_t op = (oprom[0] << 24) | (oprom[1] << 16) | (oprom[2] << 8) | (oprom[3] << 0); /* Big Endian */ - //const uint32_t op = (oprom[1] << 24) | (oprom[0] << 16) | (oprom[3] << 8) | (oprom[2] << 0); /* Mixed Endian */ - - /* The opcode is the top 6 bits */ - uint8_t opcode = (op >> 26) & 0x3f; - - /* DEBUG - print this out if you feel things are going a bit wonky */ - // sprintf(buffer, "%08x : oo %02x", op, opcode); - - /* Main decode */ - switch (opcode) - { - case 0x00: - case 0x01: - case 0x04: - case 0x05: i860_dasm_ldx(op, tempB); break; - - case 0x03: - case 0x07: i860_dasm_stx(op, tempB); break; - - case 0x02: i860_dasm_ixfr(op, tempB); break; - - case 0x06: sprintf(tempB, "(reserved)"); break; - - case 0x08: - case 0x09: - case 0x0a: - case 0x0b: i860_dasm_fid_fst(op, tempB); break; - - case 0x0d: i860_dasm_flush(op, tempB); break; - - case 0x0f: i860_dasm_pstd(op, tempB); break; - - case 0x0c: - case 0x0e: i860_dasm_ldc_sdc(op, tempB); break; - - case 0x10: i860_dasm_bri(op, tempB); break; - - case 0x11: i860_dasm_trap(op, tempB); break; - - case 0x12: i860_dasm_floating_point_dasm(op, tempB); break; /* Floating point operation sub-group */ - - case 0x13: i860_dasm_core_dasm(op, tempB); break; /* Core operation sub-group */ - - case 0x14: - case 0x15: - case 0x16: - case 0x17: i860_dasm_bte_btne(op, tempB); break; - - case 0x18: - case 0x19: i860_dasm_pfidy(op, tempB); break; - - case 0x1a: - case 0x1b: - case 0x1c: - case 0x1d: - case 0x1e: - case 0x1f: i860_dasm_CTRL_dasm(op, tempB); break; /* CTRL operation sub-group */ - - case 0x20: - case 0x21: - case 0x22: - case 0x23: - case 0x24: - case 0x25: - case 0x26: - case 0x27: i860_dasm_addu_subu(op, tempB); break; - - case 0x28: - case 0x29: - case 0x2a: - case 0x2b: i860_dasm_shl_shr(op, tempB); break; - - case 0x2c: i860_dasm_shrd(op, tempB); break; - - case 0x2d: i860_dasm_bla(op, tempB); break; - - case 0x2e: - case 0x2f: i860_dasm_shra(op, tempB); break; - - case 0x30: - case 0x31: - case 0x32: - case 0x33: i860_dasm_and_andh(op, tempB); break; - - case 0x34: - case 0x35: - case 0x36: - case 0x37: i860_dasm_andnot_andnoth(op, tempB); break; - - case 0x38: - case 0x39: - case 0x3a: - case 0x3b: i860_dasm_or_orh(op, tempB); break; - - case 0x3c: - case 0x3d: - case 0x3e: - case 0x3f: i860_dasm_xor_xorh(op, tempB); break; - - default: sprintf(tempB, "(reserved)"); break; - } - - /* More Debug */ - //strcat(buffer, " : "); - //strcat(buffer, tempB); - sprintf(buffer, "%s", tempB); - - /* All opcodes are 32 bits */ - return (4 | DASMFLAG_SUPPORTED); -} - - -// BIT HELPER -// 31 27 23 19 15 11 7 3 -// 0000 0011 1111 1111 0000 0111 1110 0000 - - -/**********************/ -/* Sub-group decoders */ -/**********************/ -static void i860_dasm_core_dasm(const uint32_t op, char* buffer) -{ - //uint8_t src1 = (op >> 11) & 0x0000001f; - - /* Reserved bits must be set to 0 */ - if ( (op & 0x000007e0) || (op & 0x03ff0000) ) - { - //logerror("[i860] Reserved CORE bits must be set to 0."); - printf("CORE baddie\n"); - } - - switch(op & 0x0000001f) - { - case 0x01: i860_dasm_CORE_lock(op, buffer); break; - case 0x02: i860_dasm_CORE_calli(op, buffer); break; - case 0x04: i860_dasm_CORE_intovr(op, buffer); break; - case 0x07: i860_dasm_CORE_unlock(op, buffer); break; - - default: sprintf(buffer, "(reserved)"); break; - } -} - -static void i860_dasm_floating_point_dasm(const uint32_t op, char* buffer) -{ - sprintf(buffer, "[[F-P unit]]"); -} - -static void i860_dasm_CTRL_dasm(const uint32_t op, char* buffer) -{ - uint8_t opc = (op >> 26) & 0x07; - - switch(opc) - { - case 0x02: i860_dasm_CTRL_br(op, buffer); break; - case 0x03: i860_dasm_CTRL_call(op, buffer); break; - case 0x04: case 0x05: i860_dasm_CTRL_bc_bct(op, buffer); break; - case 0x06: case 0x07: i860_dasm_CTRL_bnc_bnct(op, buffer); break; - - default: sprintf(buffer, "(reserved)"); break; - } -} - - -/*********************/ -/* REG-Format Opcodes*/ -/*********************/ -static void i860_dasm_ldx(const uint32_t op, char* buffer) -{ - sprintf(buffer, "ldx"); -} - -static void i860_dasm_stx(const uint32_t op, char* buffer) -{ - sprintf(buffer, "stx"); -} - -static void i860_dasm_ixfr(const uint32_t op, char* buffer) -{ -// uint16_t val = op & 0x7ff; -// uint8_t opc = (op >> 26) & 0x3f; -// uint8_t src2 = (op >> 21) & 0x1f; -// uint8_t dest = (op >> 16) & 0x1f; -// uint8_t src1 = (op >> 11) & 0x1f; - - sprintf(buffer, "ixfr"); -} - -static void i860_dasm_fid_fst(const uint32_t op, char* buffer) -{ - sprintf(buffer, "fst"); -} - -static void i860_dasm_flush(const uint32_t op, char* buffer) -{ - sprintf(buffer, "flush"); -} - -static void i860_dasm_pstd(const uint32_t op, char* buffer) -{ - sprintf(buffer, "pstd"); -} - -static void i860_dasm_ldc_sdc(const uint32_t op, char* buffer) -{ - sprintf(buffer, "ldc, sdc"); -} - -static void i860_dasm_bri(const uint32_t op, char* buffer) -{ - sprintf(buffer, "bri"); -} - -static void i860_dasm_trap(const uint32_t op, char* buffer) -{ - sprintf(buffer, "trap"); -} - -static void i860_dasm_bte_btne(const uint32_t op, char* buffer) -{ - sprintf(buffer, "bte, btne"); -} - -static void i860_dasm_pfidy(const uint32_t op, char* buffer) -{ - sprintf(buffer, "pfidy"); -} - -static void i860_dasm_addu_subu(const uint32_t op, char* buffer) -{ - sprintf(buffer, "addu, subu"); -} - -static void i860_dasm_shl_shr(const uint32_t op, char* buffer) -{ - sprintf(buffer, "shl, shr"); -} - -static void i860_dasm_shrd(const uint32_t op, char* buffer) -{ - sprintf(buffer, "shrd"); -} - -static void i860_dasm_bla(const uint32_t op, char* buffer) -{ - sprintf(buffer, "bla"); -} - -static void i860_dasm_shra(const uint32_t op, char* buffer) -{ - sprintf(buffer, "shra"); -} - -static void i860_dasm_and_andh(const uint32_t op, char* buffer) -{ - sprintf(buffer, "and, andh"); -} - -static void i860_dasm_andnot_andnoth(const uint32_t op, char* buffer) -{ - sprintf(buffer, "andnot, andnoth"); -} - -static void i860_dasm_or_orh(const uint32_t op, char* buffer) -{ - sprintf(buffer, "or, orh"); -} - -static void i860_dasm_xor_xorh(const uint32_t op, char* buffer) -{ - sprintf(buffer, "xor, xorh"); -} - - -/***********************/ -/* CORE Escape Opcodes */ -/***********************/ -static void i860_dasm_CORE_lock(const uint32_t op, char* buffer) -{ - sprintf(buffer, "lock"); -} - -static void i860_dasm_CORE_calli(const uint32_t op, char* buffer) -{ - sprintf(buffer, "calli"); -} - -static void i860_dasm_CORE_intovr(const uint32_t op, char* buffer) -{ - sprintf(buffer, "intovr"); -} - -static void i860_dasm_CORE_unlock(const uint32_t op, char* buffer) -{ - sprintf(buffer, "unlock"); -} - - -/***********************/ -/* CTRL-Format Opcodes */ -/***********************/ -static void i860_dasm_CTRL_br(const uint32_t op, char* buffer) -{ - sprintf(buffer, "br"); -} - -static void i860_dasm_CTRL_call(const uint32_t op, char* buffer) -{ - sprintf(buffer, "call"); -} - -static void i860_dasm_CTRL_bc_bct(const uint32_t op, char* buffer) -{ - sprintf(buffer, "bct"); -} - -static void i860_dasm_CTRL_bnc_bnct(const uint32_t op, char* buffer) -{ - sprintf(buffer, "bnct"); -} - - -/*******************************/ -/* Floating-Point Instructions */ -/*******************************/ diff --git a/src/devices/cpu/i860/i860dis.cpp b/src/devices/cpu/i860/i860dis.cpp index a1230d570cc..5f9d08da411 100644 --- a/src/devices/cpu/i860/i860dis.cpp +++ b/src/devices/cpu/i860/i860dis.cpp @@ -11,7 +11,7 @@ ***************************************************************************/ #include "emu.h" -#include "i860.h" +#include "i860dis.h" /* Macros for accessing register fields in instruction word. */ #define get_isrc1(bits) (((bits) >> 11) & 0x1f) @@ -28,12 +28,12 @@ /* Control register names. */ -static const char *const cr2str[] = +const char *const i860_disassembler::cr2str[] = {"fir", "psr", "dirbase", "db", "fsr", "epsr", "!", "!"}; /* Sign extend N-bit number. */ -static int32_t sign_ext(uint32_t x, int n) +int32_t i860_disassembler::sign_ext(uint32_t x, int n) { int32_t t; t = x >> (n - 1); @@ -44,7 +44,7 @@ static int32_t sign_ext(uint32_t x, int n) /* Basic integer 3-address register format: * mnemonic %rs1,%rs2,%rd */ -static void int_12d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) +void i860_disassembler::int_12d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) { /* Possibly prefix shrd with 'd.' */ if (((insn & 0xfc000000) == 0xb0000000) && (insn & 0x200)) @@ -58,7 +58,7 @@ static void int_12d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t /* Basic integer 3-address imm16 format: * mnemonic #imm16,%rs2,%rd */ -static void int_i2d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) +void i860_disassembler::int_i2d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) { /* Sign extend the 16-bit immediate. Print as hex for the bitwise operations. */ @@ -73,21 +73,21 @@ static void int_i2d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t /* Integer (mixed) 2-address isrc1ni,fdest. */ -static void int_1d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) +void i860_disassembler::int_1d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) { util::stream_format(stream, "%s\t%%r%d,%%f%d", mnemonic, get_isrc1 (insn), get_fdest (insn)); } /* Integer (mixed) 2-address csrc2,idest. */ -static void int_cd(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) +void i860_disassembler::int_cd(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) { util::stream_format(stream, "%s\t%%%s,%%r%d", mnemonic, cr2str[get_creg (insn)], get_idest (insn)); } /* Integer (mixed) 2-address isrc1,csrc2. */ -static void int_1c(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) +void i860_disassembler::int_1c(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) { util::stream_format(stream, "%s\t%%r%d,%%%s", mnemonic, get_isrc1(insn), cr2str[get_creg (insn)]); } @@ -95,7 +95,7 @@ static void int_1c(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t i /* Integer 1-address register format: * mnemonic %rs1 */ -static void int_1(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) +void i860_disassembler::int_1(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) { util::stream_format(stream, "%s\t%%r%d", mnemonic, get_isrc1 (insn)); } @@ -103,7 +103,7 @@ static void int_1(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t in /* Integer no-address register format: * mnemonic */ -static void int_0(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) +void i860_disassembler::int_0(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) { util::stream_format(stream, "%s", mnemonic); } @@ -111,7 +111,7 @@ static void int_0(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t in /* Basic floating-point 3-address register format: * mnemonic %fs1,%fs2,%fd */ -static void flop_12d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) +void i860_disassembler::flop_12d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) { char newname[256]; const char *const suffix[4] = { "ss", "sd", "ds", "dd" }; @@ -165,7 +165,7 @@ static void flop_12d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t /* Floating-point 2-address register format: * mnemonic %fs1,%fd */ -static void flop_1d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) +void i860_disassembler::flop_1d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) { const char *const suffix[4] = { "ss", "sd", "ds", "dd" }; const char *prefix_d, *prefix_p; @@ -179,7 +179,7 @@ static void flop_1d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t /* Floating-point 2-address register format: * mnemonic %fs2,%fd */ -static void flop_2d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) +void i860_disassembler::flop_2d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) { const char *const suffix[4] = { "ss", "sd", "ds", "dd" }; const char *prefix_d; @@ -192,7 +192,7 @@ static void flop_2d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t /* Floating-point (mixed) 2-address register format: * fxfr fsrc1,idest. */ -static void flop_fxfr(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) +void i860_disassembler::flop_fxfr(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) { const char *prefix_d = (insn & 0x200) ? "d." : ""; util::stream_format(stream, "%s%s\t%%f%d,%%r%d", prefix_d, mnemonic, get_fsrc1 (insn), @@ -202,7 +202,7 @@ static void flop_fxfr(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_ /* Branch with reg,reg,sbroff format: * mnemonic %rs1,%rs2,sbroff */ -static void int_12S(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) +void i860_disassembler::int_12S(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) { int32_t sbroff = sign_ext ((((insn >> 5) & 0xf800) | (insn & 0x07ff)), 16); int32_t rel = (int32_t)pc + (sbroff << 2) + 4; @@ -214,7 +214,7 @@ static void int_12S(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t /* Branch with #const5,reg,sbroff format: * mnemonic #const5,%rs2,sbroff */ -static void int_i2S(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) +void i860_disassembler::int_i2S(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) { int32_t sbroff = sign_ext ((((insn >> 5) & 0xf800) | (insn & 0x07ff)), 16); int32_t rel = (int32_t)pc + (sbroff << 2) + 4; @@ -226,7 +226,7 @@ static void int_i2S(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t /* Branch with lbroff format: * mnemonic lbroff */ -static void int_L(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) +void i860_disassembler::int_L(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) { int32_t lbroff = sign_ext ((insn & 0x03ffffff), 26); int32_t rel = (int32_t)pc + (lbroff << 2) + 4; @@ -238,7 +238,7 @@ static void int_L(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t in /* Integer load. * ld.{b,s,l} isrc1(isrc2),idest * ld.{b,s,l} #const(isrc2),idest */ -static void int_ldx(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) +void i860_disassembler::int_ldx(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) { /* Operand size, in bytes. */ int sizes[4] = { 1, 1, 2, 4 }; @@ -265,7 +265,7 @@ static void int_ldx(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t /* Integer store: st.b isrc1ni,#const(isrc2) */ -static void int_stx(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) +void i860_disassembler::int_stx(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) { /* Operand size, in bytes. */ int sizes[4] = { 1, 1, 2, 4 }; @@ -291,7 +291,7 @@ static void int_stx(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t * "fst.y fdest,isrc1(isrc2)", "fst.y fdest,isrc1(isrc2)++", * "fst.y fdest,#const(isrc2)" or "fst.y fdest,#const(isrc2)++" * Where y = {l,d,q}. Note, there is no pfld.q, though. */ -static void int_fldst(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) +void i860_disassembler::int_fldst(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) { int32_t immsrc1 = sign_ext (get_imm16 (insn), 16); /* Operand size, in bytes. */ @@ -353,7 +353,7 @@ static void int_fldst(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_ /* flush #const(isrc2)[++]. */ -static void int_flush(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) +void i860_disassembler::int_flush(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn) { const char *const auto_suff[2] = { "", "++" }; int32_t immsrc = sign_ext (get_imm16 (insn), 16); @@ -363,257 +363,234 @@ static void int_flush(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_ } -/* Flags for the decode table. */ -enum -{ - DEC_MORE = 1, /* More decoding necessary. */ - DEC_DECODED = 2 /* Fully decoded, go. */ -}; - - -struct decode_tbl_t -{ - /* Disassembly function for this opcode. - Call with buffer, mnemonic, pc, insn. */ - void (*insn_dis)(std::ostream &, char *, uint32_t, uint32_t); - - /* Flags for this opcode. */ - char flags; - - /* Mnemonic of this opcode (sometimes partial when more decode is - done in disassembly routines-- e.g., loads and stores). */ - const char *mnemonic; -}; - - /* First-level decode table (i.e., for the 6 primary opcode bits). */ -static const decode_tbl_t decode_tbl[64] = +const i860_disassembler::decode_tbl_t i860_disassembler::decode_tbl[64] = { /* A slight bit of decoding for loads and stores is done in the execution routines (operand size and addressing mode), which is why their respective entries are identical. */ - { int_ldx, DEC_DECODED, "ld." }, /* ld.b isrc1(isrc2),idest. */ - { int_ldx, DEC_DECODED, "ld." }, /* ld.b #const(isrc2),idest. */ - { int_1d, DEC_DECODED, "ixfr" }, /* ixfr isrc1ni,fdest. */ - { int_stx, DEC_DECODED, "st." }, /* st.b isrc1ni,#const(isrc2). */ - { int_ldx, DEC_DECODED, "ld." }, /* ld.{s,l} isrc1(isrc2),idest. */ - { int_ldx, DEC_DECODED, "ld." }, /* ld.{s,l} #const(isrc2),idest. */ - { nullptr, 0 , nullptr }, - { int_stx, DEC_DECODED, "st." }, /* st.{s,l} isrc1ni,#const(isrc2),idest.*/ - { int_fldst, DEC_DECODED, "fld." }, /* fld.{l,d,q} isrc1(isrc2)[++],fdest. */ - { int_fldst, DEC_DECODED, "fld." }, /* fld.{l,d,q} #const(isrc2)[++],fdest. */ - { int_fldst, DEC_DECODED, "fst." }, /* fst.{l,d,q} fdest,isrc1(isrc2)[++] */ - { int_fldst, DEC_DECODED, "fst." }, /* fst.{l,d,q} fdest,#const(isrc2)[++] */ - { int_cd, DEC_DECODED, "ld.c" }, /* ld.c csrc2,idest. */ - { int_flush, DEC_DECODED, "flush" }, /* flush #const(isrc2) (or autoinc). */ - { int_1c, DEC_DECODED, "st.c" }, /* st.c isrc1,csrc2. */ - { int_fldst, DEC_DECODED, "pstd." }, /* pst.d fdest,#const(isrc2)[++]. */ - { int_1, DEC_DECODED, "bri" }, /* bri isrc1ni. */ - { int_12d, DEC_DECODED, "trap" }, /* trap isrc1ni,isrc2,idest. */ - { nullptr, DEC_MORE, nullptr }, /* FP ESCAPE FORMAT, more decode. */ - { nullptr, DEC_MORE, nullptr }, /* CORE ESCAPE FORMAT, more decode. */ - { int_12S, DEC_DECODED, "btne" }, /* btne isrc1,isrc2,sbroff. */ - { int_i2S, DEC_DECODED, "btne" }, /* btne #const,isrc2,sbroff. */ - { int_12S, DEC_DECODED, "bte" }, /* bte isrc1,isrc2,sbroff. */ - { int_i2S, DEC_DECODED, "bte" }, /* bte #const5,isrc2,idest. */ - { int_fldst, DEC_DECODED, "pfld." }, /* pfld.{l,d,q} isrc1(isrc2)[++],fdest. */ - { int_fldst, DEC_DECODED, "pfld." }, /* pfld.{l,d,q} #const(isrc2)[++],fdest.*/ - { int_L, DEC_DECODED, "br" }, /* br lbroff. */ - { int_L, DEC_DECODED, "call" }, /* call lbroff . */ - { int_L, DEC_DECODED, "bc" }, /* bc lbroff. */ - { int_L, DEC_DECODED, "bc.t" }, /* bc.t lbroff. */ - { int_L, DEC_DECODED, "bnc" }, /* bnc lbroff. */ - { int_L, DEC_DECODED, "bnc.t" }, /* bnc.t lbroff. */ - { int_12d, DEC_DECODED, "addu" }, /* addu isrc1,isrc2,idest. */ - { int_i2d, DEC_DECODED, "addu" }, /* addu #const,isrc2,idest. */ - { int_12d, DEC_DECODED, "subu" }, /* subu isrc1,isrc2,idest. */ - { int_i2d, DEC_DECODED, "subu" }, /* subu #const,isrc2,idest. */ - { int_12d, DEC_DECODED, "adds" }, /* adds isrc1,isrc2,idest. */ - { int_i2d, DEC_DECODED, "adds" }, /* adds #const,isrc2,idest. */ - { int_12d, DEC_DECODED, "subs" }, /* subs isrc1,isrc2,idest. */ - { int_i2d, DEC_DECODED, "subs" }, /* subs #const,isrc2,idest. */ - { int_12d, DEC_DECODED, "shl" }, /* shl isrc1,isrc2,idest. */ - { int_i2d, DEC_DECODED, "shl" }, /* shl #const,isrc2,idest. */ - { int_12d, DEC_DECODED, "shr" }, /* shr isrc1,isrc2,idest. */ - { int_i2d, DEC_DECODED, "shr" }, /* shr #const,isrc2,idest. */ - { int_12d, DEC_DECODED, "shrd" }, /* shrd isrc1ni,isrc2,idest. */ - { int_12S, DEC_DECODED, "bla" }, /* bla isrc1ni,isrc2,sbroff. */ - { int_12d, DEC_DECODED, "shra" }, /* shra isrc1,isrc2,idest. */ - { int_i2d, DEC_DECODED, "shra" }, /* shra #const,isrc2,idest. */ - { int_12d, DEC_DECODED, "and" }, /* and isrc1,isrc2,idest. */ - { int_i2d, DEC_DECODED, "and" }, /* and #const,isrc2,idest. */ - { nullptr, 0 , nullptr }, - { int_i2d, DEC_DECODED, "andh" }, /* andh #const,isrc2,idest. */ - { int_12d, DEC_DECODED, "andnot" }, /* andnot isrc1,isrc2,idest. */ - { int_i2d, DEC_DECODED, "andnot" }, /* andnot #const,isrc2,idest. */ - { nullptr, 0 , nullptr }, - { int_i2d, DEC_DECODED, "andnoth" }, /* andnoth #const,isrc2,idest.*/ - { int_12d, DEC_DECODED, "or" }, /* or isrc1,isrc2,idest. */ - { int_i2d, DEC_DECODED, "or" }, /* or #const,isrc2,idest. */ - { nullptr, 0 , nullptr }, - { int_i2d, DEC_DECODED, "orh" }, /* orh #const,isrc2,idest. */ - { int_12d, DEC_DECODED, "xor" }, /* xor isrc1,isrc2,idest. */ - { int_i2d, DEC_DECODED, "xor" }, /* xor #const,isrc2,idest. */ - { nullptr, 0 , nullptr }, - { int_i2d, DEC_DECODED, "xorh" }, /* xorh #const,isrc2,idest. */ + { &i860_disassembler::int_ldx, DEC_DECODED, "ld." }, /* ld.b isrc1(isrc2),idest. */ + { &i860_disassembler::int_ldx, DEC_DECODED, "ld." }, /* ld.b #const(isrc2),idest. */ + { &i860_disassembler::int_1d, DEC_DECODED, "ixfr" }, /* ixfr isrc1ni,fdest. */ + { &i860_disassembler::int_stx, DEC_DECODED, "st." }, /* st.b isrc1ni,#const(isrc2). */ + { &i860_disassembler::int_ldx, DEC_DECODED, "ld." }, /* ld.{s,l} isrc1(isrc2),idest. */ + { &i860_disassembler::int_ldx, DEC_DECODED, "ld." }, /* ld.{s,l} #const(isrc2),idest. */ + { nullptr, 0 , nullptr }, + { &i860_disassembler::int_stx, DEC_DECODED, "st." }, /* st.{s,l} isrc1ni,#const(isrc2),idest.*/ + { &i860_disassembler::int_fldst, DEC_DECODED, "fld." }, /* fld.{l,d,q} isrc1(isrc2)[++],fdest. */ + { &i860_disassembler::int_fldst, DEC_DECODED, "fld." }, /* fld.{l,d,q} #const(isrc2)[++],fdest. */ + { &i860_disassembler::int_fldst, DEC_DECODED, "fst." }, /* fst.{l,d,q} fdest,isrc1(isrc2)[++] */ + { &i860_disassembler::int_fldst, DEC_DECODED, "fst." }, /* fst.{l,d,q} fdest,#const(isrc2)[++] */ + { &i860_disassembler::int_cd, DEC_DECODED, "ld.c" }, /* ld.c csrc2,idest. */ + { &i860_disassembler::int_flush, DEC_DECODED, "flush" }, /* flush #const(isrc2) (or autoinc). */ + { &i860_disassembler::int_1c, DEC_DECODED, "st.c" }, /* st.c isrc1,csrc2. */ + { &i860_disassembler::int_fldst, DEC_DECODED, "pstd." }, /* pst.d fdest,#const(isrc2)[++]. */ + { &i860_disassembler::int_1, DEC_DECODED, "bri" }, /* bri isrc1ni. */ + { &i860_disassembler::int_12d, DEC_DECODED, "trap" }, /* trap isrc1ni,isrc2,idest. */ + { nullptr, DEC_MORE, nullptr }, /* FP ESCAPE FORMAT, more decode. */ + { nullptr, DEC_MORE, nullptr }, /* CORE ESCAPE FORMAT, more decode. */ + { &i860_disassembler::int_12S, DEC_DECODED, "btne" }, /* btne isrc1,isrc2,sbroff. */ + { &i860_disassembler::int_i2S, DEC_DECODED, "btne" }, /* btne #const,isrc2,sbroff. */ + { &i860_disassembler::int_12S, DEC_DECODED, "bte" }, /* bte isrc1,isrc2,sbroff. */ + { &i860_disassembler::int_i2S, DEC_DECODED, "bte" }, /* bte #const5,isrc2,idest. */ + { &i860_disassembler::int_fldst, DEC_DECODED, "pfld." }, /* pfld.{l,d,q} isrc1(isrc2)[++],fdest. */ + { &i860_disassembler::int_fldst, DEC_DECODED, "pfld." }, /* pfld.{l,d,q} #const(isrc2)[++],fdest.*/ + { &i860_disassembler::int_L, DEC_DECODED, "br" }, /* br lbroff. */ + { &i860_disassembler::int_L, DEC_DECODED, "call" }, /* call lbroff . */ + { &i860_disassembler::int_L, DEC_DECODED, "bc" }, /* bc lbroff. */ + { &i860_disassembler::int_L, DEC_DECODED, "bc.t" }, /* bc.t lbroff. */ + { &i860_disassembler::int_L, DEC_DECODED, "bnc" }, /* bnc lbroff. */ + { &i860_disassembler::int_L, DEC_DECODED, "bnc.t" }, /* bnc.t lbroff. */ + { &i860_disassembler::int_12d, DEC_DECODED, "addu" }, /* addu isrc1,isrc2,idest. */ + { &i860_disassembler::int_i2d, DEC_DECODED, "addu" }, /* addu #const,isrc2,idest. */ + { &i860_disassembler::int_12d, DEC_DECODED, "subu" }, /* subu isrc1,isrc2,idest. */ + { &i860_disassembler::int_i2d, DEC_DECODED, "subu" }, /* subu #const,isrc2,idest. */ + { &i860_disassembler::int_12d, DEC_DECODED, "adds" }, /* adds isrc1,isrc2,idest. */ + { &i860_disassembler::int_i2d, DEC_DECODED, "adds" }, /* adds #const,isrc2,idest. */ + { &i860_disassembler::int_12d, DEC_DECODED, "subs" }, /* subs isrc1,isrc2,idest. */ + { &i860_disassembler::int_i2d, DEC_DECODED, "subs" }, /* subs #const,isrc2,idest. */ + { &i860_disassembler::int_12d, DEC_DECODED, "shl" }, /* shl isrc1,isrc2,idest. */ + { &i860_disassembler::int_i2d, DEC_DECODED, "shl" }, /* shl #const,isrc2,idest. */ + { &i860_disassembler::int_12d, DEC_DECODED, "shr" }, /* shr isrc1,isrc2,idest. */ + { &i860_disassembler::int_i2d, DEC_DECODED, "shr" }, /* shr #const,isrc2,idest. */ + { &i860_disassembler::int_12d, DEC_DECODED, "shrd" }, /* shrd isrc1ni,isrc2,idest. */ + { &i860_disassembler::int_12S, DEC_DECODED, "bla" }, /* bla isrc1ni,isrc2,sbroff. */ + { &i860_disassembler::int_12d, DEC_DECODED, "shra" }, /* shra isrc1,isrc2,idest. */ + { &i860_disassembler::int_i2d, DEC_DECODED, "shra" }, /* shra #const,isrc2,idest. */ + { &i860_disassembler::int_12d, DEC_DECODED, "and" }, /* and isrc1,isrc2,idest. */ + { &i860_disassembler::int_i2d, DEC_DECODED, "and" }, /* and #const,isrc2,idest. */ + { nullptr, 0 , nullptr }, + { &i860_disassembler::int_i2d, DEC_DECODED, "andh" }, /* andh #const,isrc2,idest. */ + { &i860_disassembler::int_12d, DEC_DECODED, "andnot" }, /* andnot isrc1,isrc2,idest. */ + { &i860_disassembler::int_i2d, DEC_DECODED, "andnot" }, /* andnot #const,isrc2,idest. */ + { nullptr, 0 , nullptr }, + { &i860_disassembler::int_i2d, DEC_DECODED, "andnoth" }, /* andnoth #const,isrc2,idest.*/ + { &i860_disassembler::int_12d, DEC_DECODED, "or" }, /* or isrc1,isrc2,idest. */ + { &i860_disassembler::int_i2d, DEC_DECODED, "or" }, /* or #const,isrc2,idest. */ + { nullptr, 0 , nullptr }, + { &i860_disassembler::int_i2d, DEC_DECODED, "orh" }, /* orh #const,isrc2,idest. */ + { &i860_disassembler::int_12d, DEC_DECODED, "xor" }, /* xor isrc1,isrc2,idest. */ + { &i860_disassembler::int_i2d, DEC_DECODED, "xor" }, /* xor #const,isrc2,idest. */ + { nullptr, 0 , nullptr }, + { &i860_disassembler::int_i2d, DEC_DECODED, "xorh" }, /* xorh #const,isrc2,idest. */ }; /* Second-level decode table (i.e., for the 3 core escape opcode bits). */ -static const decode_tbl_t core_esc_decode_tbl[8] = +const i860_disassembler::decode_tbl_t i860_disassembler::core_esc_decode_tbl[8] = { - { nullptr, 0 , nullptr }, - { int_0, DEC_DECODED, "lock" }, /* lock. */ - { int_1, DEC_DECODED, "calli" }, /* calli isrc1ni. */ - { nullptr, 0 , nullptr }, - { int_0, DEC_DECODED, "intovr" }, /* intovr. */ - { nullptr, 0 , nullptr }, - { nullptr, 0 , nullptr }, - { int_0, DEC_DECODED, "unlock" }, /* unlock. */ + { nullptr, 0 , nullptr }, + { &i860_disassembler::int_0, DEC_DECODED, "lock" }, /* lock. */ + { &i860_disassembler::int_1, DEC_DECODED, "calli" }, /* calli isrc1ni. */ + { nullptr, 0 , nullptr }, + { &i860_disassembler::int_0, DEC_DECODED, "intovr" }, /* intovr. */ + { nullptr, 0 , nullptr }, + { nullptr, 0 , nullptr }, + { &i860_disassembler::int_0, DEC_DECODED, "unlock" }, /* unlock. */ }; /* Second-level decode table (i.e., for the 7 FP extended opcode bits). */ -static const decode_tbl_t fp_decode_tbl[128] = +const i860_disassembler::decode_tbl_t i860_disassembler::fp_decode_tbl[128] = { /* Floating point instructions. The least significant 7 bits are the (extended) opcode and bits 10:7 are P,D,S,R respectively ([p]ipelined, [d]ual, [s]ource prec., [r]esult prec.). For some operations, I defer decoding the P,S,R bits to the emulation routine for them. */ - { flop_12d, DEC_DECODED, "r2p1." }, /* 0x00 pf[m]am */ - { flop_12d, DEC_DECODED, "r2pt." }, /* 0x01 pf[m]am */ - { flop_12d, DEC_DECODED, "r2ap1." }, /* 0x02 pf[m]am */ - { flop_12d, DEC_DECODED, "r2apt." }, /* 0x03 pf[m]am */ - { flop_12d, DEC_DECODED, "i2p1." }, /* 0x04 pf[m]am */ - { flop_12d, DEC_DECODED, "i2pt." }, /* 0x05 pf[m]am */ - { flop_12d, DEC_DECODED, "i2ap1." }, /* 0x06 pf[m]am */ - { flop_12d, DEC_DECODED, "i2apt." }, /* 0x07 pf[m]am */ - { flop_12d, DEC_DECODED, "rat1p2." }, /* 0x08 pf[m]am */ - { flop_12d, DEC_DECODED, "m12apm." }, /* 0x09 pf[m]am */ - { flop_12d, DEC_DECODED, "ra1p2." }, /* 0x0A pf[m]am */ - { flop_12d, DEC_DECODED, "m12ttpa." }, /* 0x0B pf[m]am */ - { flop_12d, DEC_DECODED, "iat1p2." }, /* 0x0C pf[m]am */ - { flop_12d, DEC_DECODED, "m12tpm." }, /* 0x0D pf[m]am */ - { flop_12d, DEC_DECODED, "ia1p2." }, /* 0x0E pf[m]am */ - { flop_12d, DEC_DECODED, "m12tpa." }, /* 0x0F pf[m]am */ - { flop_12d, DEC_DECODED, "r2s1." }, /* 0x10 pf[m]sm */ - { flop_12d, DEC_DECODED, "r2st." }, /* 0x11 pf[m]sm */ - { flop_12d, DEC_DECODED, "r2as1." }, /* 0x12 pf[m]sm */ - { flop_12d, DEC_DECODED, "r2ast." }, /* 0x13 pf[m]sm */ - { flop_12d, DEC_DECODED, "i2s1." }, /* 0x14 pf[m]sm */ - { flop_12d, DEC_DECODED, "i2st." }, /* 0x15 pf[m]sm */ - { flop_12d, DEC_DECODED, "i2as1." }, /* 0x16 pf[m]sm */ - { flop_12d, DEC_DECODED, "i2ast." }, /* 0x17 pf[m]sm */ - { flop_12d, DEC_DECODED, "rat1s2." }, /* 0x18 pf[m]sm */ - { flop_12d, DEC_DECODED, "m12asm." }, /* 0x19 pf[m]sm */ - { flop_12d, DEC_DECODED, "ra1s2." }, /* 0x1A pf[m]sm */ - { flop_12d, DEC_DECODED, "m12ttsa." }, /* 0x1B pf[m]sm */ - { flop_12d, DEC_DECODED, "iat1s2." }, /* 0x1C pf[m]sm */ - { flop_12d, DEC_DECODED, "m12tsm." }, /* 0x1D pf[m]sm */ - { flop_12d, DEC_DECODED, "ia1s2." }, /* 0x1E pf[m]sm */ - { flop_12d, DEC_DECODED, "m12tsa." }, /* 0x1F pf[m]sm */ - { flop_12d, DEC_DECODED, "fmul." }, /* 0x20 [p]fmul */ - { flop_12d, DEC_DECODED, "fmlow." }, /* 0x21 fmlow.dd */ - { flop_2d, DEC_DECODED, "frcp." }, /* 0x22 frcp.{ss,sd,dd} */ - { flop_2d, DEC_DECODED, "frsqr." }, /* 0x23 frsqr.{ss,sd,dd} */ - { flop_12d, DEC_DECODED, "pfmul3.dd" }, /* 0x24 pfmul3.dd */ - { nullptr, 0 , nullptr }, /* 0x25 */ - { nullptr, 0 , nullptr }, /* 0x26 */ - { nullptr, 0 , nullptr }, /* 0x27 */ - { nullptr, 0 , nullptr }, /* 0x28 */ - { nullptr, 0 , nullptr }, /* 0x29 */ - { nullptr, 0 , nullptr }, /* 0x2A */ - { nullptr, 0 , nullptr }, /* 0x2B */ - { nullptr, 0 , nullptr }, /* 0x2C */ - { nullptr, 0 , nullptr }, /* 0x2D */ - { nullptr, 0 , nullptr }, /* 0x2E */ - { nullptr, 0 , nullptr }, /* 0x2F */ - { flop_12d, DEC_DECODED, "fadd." }, /* 0x30, [p]fadd.{ss,sd,dd} */ - { flop_12d, DEC_DECODED, "fsub." }, /* 0x31, [p]fsub.{ss,sd,dd} */ - { flop_1d, DEC_DECODED, "fix." }, /* 0x32, [p]fix.{ss,sd,dd} */ - { flop_1d, DEC_DECODED, "famov." }, /* 0x33, [p]famov.{ss,sd,ds,dd} */ - { flop_12d, DEC_DECODED, "f{gt,le}" }, /* 0x34, pf{gt,le}.{ss,dd} */ - { flop_12d, DEC_DECODED, "feq." }, /* 0x35, pfeq.{ss,dd} */ - { nullptr, 0 , nullptr }, /* 0x36 */ - { nullptr, 0 , nullptr }, /* 0x37 */ - { nullptr, 0 , nullptr }, /* 0x38 */ - { nullptr, 0 , nullptr }, /* 0x39 */ - { flop_1d, DEC_DECODED, "ftrunc." }, /* 0x3A, [p]ftrunc.{ss,sd,dd} */ - { nullptr, 0 , nullptr }, /* 0x3B */ - { nullptr, 0 , nullptr }, /* 0x3C */ - { nullptr, 0 , nullptr }, /* 0x3D */ - { nullptr, 0 , nullptr }, /* 0x3E */ - { nullptr, 0 , nullptr }, /* 0x3F */ - { flop_fxfr, DEC_DECODED, "fxfr" }, /* 0x40, fxfr fsrc1,idest. */ - { nullptr, 0 , nullptr }, /* 0x41 */ - { nullptr, 0 , nullptr }, /* 0x42 */ - { nullptr, 0 , nullptr }, /* 0x43 */ - { nullptr, 0 , nullptr }, /* 0x44 */ - { nullptr, 0 , nullptr }, /* 0x45 */ - { nullptr, 0 , nullptr }, /* 0x46 */ - { nullptr, 0 , nullptr }, /* 0x47 */ - { nullptr, 0 , nullptr }, /* 0x48 */ - { flop_12d, DEC_DECODED, "fiadd." }, /* 0x49, [p]fiadd.{ss,dd} */ - { nullptr, 0 , nullptr }, /* 0x4A */ - { nullptr, 0 , nullptr }, /* 0x4B */ - { nullptr, 0 , nullptr }, /* 0x4C */ - { flop_12d, DEC_DECODED, "fisub." }, /* 0x4D, [p]fisub.{ss,dd} */ - { nullptr, 0 , nullptr }, /* 0x4E */ - { nullptr, 0 , nullptr }, /* 0x4F */ - { flop_12d, DEC_DECODED, "faddp" }, /* 0x50, [p]faddp */ - { flop_12d, DEC_DECODED, "faddz" }, /* 0x51, [p]faddz */ - { nullptr, 0 , nullptr }, /* 0x52 */ - { nullptr, 0 , nullptr }, /* 0x53 */ - { nullptr, 0 , nullptr }, /* 0x54 */ - { nullptr, 0 , nullptr }, /* 0x55 */ - { nullptr, 0 , nullptr }, /* 0x56 */ - { flop_12d, DEC_DECODED, "fzchkl" }, /* 0x57, [p]fzchkl */ - { nullptr, 0 , nullptr }, /* 0x58 */ - { nullptr, 0 , nullptr }, /* 0x59 */ - { flop_1d, DEC_DECODED, "form" }, /* 0x5A, [p]form.dd */ - { nullptr, 0 , nullptr }, /* 0x5B */ - { nullptr, 0 , nullptr }, /* 0x5C */ - { nullptr, 0 , nullptr }, /* 0x5D */ - { nullptr, 0 , nullptr }, /* 0x5E */ - { flop_12d, DEC_DECODED, "fzchks" }, /* 0x5F, [p]fzchks */ - { nullptr, 0 , nullptr }, /* 0x60 */ - { nullptr, 0 , nullptr }, /* 0x61 */ - { nullptr, 0 , nullptr }, /* 0x62 */ - { nullptr, 0 , nullptr }, /* 0x63 */ - { nullptr, 0 , nullptr }, /* 0x64 */ - { nullptr, 0 , nullptr }, /* 0x65 */ - { nullptr, 0 , nullptr }, /* 0x66 */ - { nullptr, 0 , nullptr }, /* 0x67 */ - { nullptr, 0 , nullptr }, /* 0x68 */ - { nullptr, 0 , nullptr }, /* 0x69 */ - { nullptr, 0 , nullptr }, /* 0x6A */ - { nullptr, 0 , nullptr }, /* 0x6B */ - { nullptr, 0 , nullptr }, /* 0x6C */ - { nullptr, 0 , nullptr }, /* 0x6D */ - { nullptr, 0 , nullptr }, /* 0x6E */ - { nullptr, 0 , nullptr }, /* 0x6F */ - { nullptr, 0 , nullptr }, /* 0x70 */ - { nullptr, 0 , nullptr }, /* 0x71 */ - { nullptr, 0 , nullptr }, /* 0x72 */ - { nullptr, 0 , nullptr }, /* 0x73 */ - { nullptr, 0 , nullptr }, /* 0x74 */ - { nullptr, 0 , nullptr }, /* 0x75 */ - { nullptr, 0 , nullptr }, /* 0x76 */ - { nullptr, 0 , nullptr }, /* 0x77 */ - { nullptr, 0 , nullptr }, /* 0x78 */ - { nullptr, 0 , nullptr }, /* 0x79 */ - { nullptr, 0 , nullptr }, /* 0x7A */ - { nullptr, 0 , nullptr }, /* 0x7B */ - { nullptr, 0 , nullptr }, /* 0x7C */ - { nullptr, 0 , nullptr }, /* 0x7D */ - { nullptr, 0 , nullptr }, /* 0x7E */ - { nullptr, 0 , nullptr }, /* 0x7F */ + { &i860_disassembler::flop_12d, DEC_DECODED, "r2p1." }, /* 0x00 pf[m]am */ + { &i860_disassembler::flop_12d, DEC_DECODED, "r2pt." }, /* 0x01 pf[m]am */ + { &i860_disassembler::flop_12d, DEC_DECODED, "r2ap1." }, /* 0x02 pf[m]am */ + { &i860_disassembler::flop_12d, DEC_DECODED, "r2apt." }, /* 0x03 pf[m]am */ + { &i860_disassembler::flop_12d, DEC_DECODED, "i2p1." }, /* 0x04 pf[m]am */ + { &i860_disassembler::flop_12d, DEC_DECODED, "i2pt." }, /* 0x05 pf[m]am */ + { &i860_disassembler::flop_12d, DEC_DECODED, "i2ap1." }, /* 0x06 pf[m]am */ + { &i860_disassembler::flop_12d, DEC_DECODED, "i2apt." }, /* 0x07 pf[m]am */ + { &i860_disassembler::flop_12d, DEC_DECODED, "rat1p2." }, /* 0x08 pf[m]am */ + { &i860_disassembler::flop_12d, DEC_DECODED, "m12apm." }, /* 0x09 pf[m]am */ + { &i860_disassembler::flop_12d, DEC_DECODED, "ra1p2." }, /* 0x0A pf[m]am */ + { &i860_disassembler::flop_12d, DEC_DECODED, "m12ttpa." }, /* 0x0B pf[m]am */ + { &i860_disassembler::flop_12d, DEC_DECODED, "iat1p2." }, /* 0x0C pf[m]am */ + { &i860_disassembler::flop_12d, DEC_DECODED, "m12tpm." }, /* 0x0D pf[m]am */ + { &i860_disassembler::flop_12d, DEC_DECODED, "ia1p2." }, /* 0x0E pf[m]am */ + { &i860_disassembler::flop_12d, DEC_DECODED, "m12tpa." }, /* 0x0F pf[m]am */ + { &i860_disassembler::flop_12d, DEC_DECODED, "r2s1." }, /* 0x10 pf[m]sm */ + { &i860_disassembler::flop_12d, DEC_DECODED, "r2st." }, /* 0x11 pf[m]sm */ + { &i860_disassembler::flop_12d, DEC_DECODED, "r2as1." }, /* 0x12 pf[m]sm */ + { &i860_disassembler::flop_12d, DEC_DECODED, "r2ast." }, /* 0x13 pf[m]sm */ + { &i860_disassembler::flop_12d, DEC_DECODED, "i2s1." }, /* 0x14 pf[m]sm */ + { &i860_disassembler::flop_12d, DEC_DECODED, "i2st." }, /* 0x15 pf[m]sm */ + { &i860_disassembler::flop_12d, DEC_DECODED, "i2as1." }, /* 0x16 pf[m]sm */ + { &i860_disassembler::flop_12d, DEC_DECODED, "i2ast." }, /* 0x17 pf[m]sm */ + { &i860_disassembler::flop_12d, DEC_DECODED, "rat1s2." }, /* 0x18 pf[m]sm */ + { &i860_disassembler::flop_12d, DEC_DECODED, "m12asm." }, /* 0x19 pf[m]sm */ + { &i860_disassembler::flop_12d, DEC_DECODED, "ra1s2." }, /* 0x1A pf[m]sm */ + { &i860_disassembler::flop_12d, DEC_DECODED, "m12ttsa." }, /* 0x1B pf[m]sm */ + { &i860_disassembler::flop_12d, DEC_DECODED, "iat1s2." }, /* 0x1C pf[m]sm */ + { &i860_disassembler::flop_12d, DEC_DECODED, "m12tsm." }, /* 0x1D pf[m]sm */ + { &i860_disassembler::flop_12d, DEC_DECODED, "ia1s2." }, /* 0x1E pf[m]sm */ + { &i860_disassembler::flop_12d, DEC_DECODED, "m12tsa." }, /* 0x1F pf[m]sm */ + { &i860_disassembler::flop_12d, DEC_DECODED, "fmul." }, /* 0x20 [p]fmul */ + { &i860_disassembler::flop_12d, DEC_DECODED, "fmlow." }, /* 0x21 fmlow.dd */ + { &i860_disassembler::flop_2d, DEC_DECODED, "frcp." }, /* 0x22 frcp.{ss,sd,dd} */ + { &i860_disassembler::flop_2d, DEC_DECODED, "frsqr." }, /* 0x23 frsqr.{ss,sd,dd} */ + { &i860_disassembler::flop_12d, DEC_DECODED, "pfmul3.dd" }, /* 0x24 pfmul3.dd */ + { nullptr, 0 , nullptr }, /* 0x25 */ + { nullptr, 0 , nullptr }, /* 0x26 */ + { nullptr, 0 , nullptr }, /* 0x27 */ + { nullptr, 0 , nullptr }, /* 0x28 */ + { nullptr, 0 , nullptr }, /* 0x29 */ + { nullptr, 0 , nullptr }, /* 0x2A */ + { nullptr, 0 , nullptr }, /* 0x2B */ + { nullptr, 0 , nullptr }, /* 0x2C */ + { nullptr, 0 , nullptr }, /* 0x2D */ + { nullptr, 0 , nullptr }, /* 0x2E */ + { nullptr, 0 , nullptr }, /* 0x2F */ + { &i860_disassembler::flop_12d, DEC_DECODED, "fadd." }, /* 0x30, [p]fadd.{ss,sd,dd} */ + { &i860_disassembler::flop_12d, DEC_DECODED, "fsub." }, /* 0x31, [p]fsub.{ss,sd,dd} */ + { &i860_disassembler::flop_1d, DEC_DECODED, "fix." }, /* 0x32, [p]fix.{ss,sd,dd} */ + { &i860_disassembler::flop_1d, DEC_DECODED, "famov." }, /* 0x33, [p]famov.{ss,sd,ds,dd} */ + { &i860_disassembler::flop_12d, DEC_DECODED, "f{gt,le}" }, /* 0x34, pf{gt,le}.{ss,dd} */ + { &i860_disassembler::flop_12d, DEC_DECODED, "feq." }, /* 0x35, pfeq.{ss,dd} */ + { nullptr, 0 , nullptr }, /* 0x36 */ + { nullptr, 0 , nullptr }, /* 0x37 */ + { nullptr, 0 , nullptr }, /* 0x38 */ + { nullptr, 0 , nullptr }, /* 0x39 */ + { &i860_disassembler::flop_1d, DEC_DECODED, "ftrunc." }, /* 0x3A, [p]ftrunc.{ss,sd,dd} */ + { nullptr, 0 , nullptr }, /* 0x3B */ + { nullptr, 0 , nullptr }, /* 0x3C */ + { nullptr, 0 , nullptr }, /* 0x3D */ + { nullptr, 0 , nullptr }, /* 0x3E */ + { nullptr, 0 , nullptr }, /* 0x3F */ + { &i860_disassembler::flop_fxfr, DEC_DECODED, "fxfr" }, /* 0x40, fxfr fsrc1,idest. */ + { nullptr, 0 , nullptr }, /* 0x41 */ + { nullptr, 0 , nullptr }, /* 0x42 */ + { nullptr, 0 , nullptr }, /* 0x43 */ + { nullptr, 0 , nullptr }, /* 0x44 */ + { nullptr, 0 , nullptr }, /* 0x45 */ + { nullptr, 0 , nullptr }, /* 0x46 */ + { nullptr, 0 , nullptr }, /* 0x47 */ + { nullptr, 0 , nullptr }, /* 0x48 */ + { &i860_disassembler::flop_12d, DEC_DECODED, "fiadd." }, /* 0x49, [p]fiadd.{ss,dd} */ + { nullptr, 0 , nullptr }, /* 0x4A */ + { nullptr, 0 , nullptr }, /* 0x4B */ + { nullptr, 0 , nullptr }, /* 0x4C */ + { &i860_disassembler::flop_12d, DEC_DECODED, "fisub." }, /* 0x4D, [p]fisub.{ss,dd} */ + { nullptr, 0 , nullptr }, /* 0x4E */ + { nullptr, 0 , nullptr }, /* 0x4F */ + { &i860_disassembler::flop_12d, DEC_DECODED, "faddp" }, /* 0x50, [p]faddp */ + { &i860_disassembler::flop_12d, DEC_DECODED, "faddz" }, /* 0x51, [p]faddz */ + { nullptr, 0 , nullptr }, /* 0x52 */ + { nullptr, 0 , nullptr }, /* 0x53 */ + { nullptr, 0 , nullptr }, /* 0x54 */ + { nullptr, 0 , nullptr }, /* 0x55 */ + { nullptr, 0 , nullptr }, /* 0x56 */ + { &i860_disassembler::flop_12d, DEC_DECODED, "fzchkl" }, /* 0x57, [p]fzchkl */ + { nullptr, 0 , nullptr }, /* 0x58 */ + { nullptr, 0 , nullptr }, /* 0x59 */ + { &i860_disassembler::flop_1d, DEC_DECODED, "form" }, /* 0x5A, [p]form.dd */ + { nullptr, 0 , nullptr }, /* 0x5B */ + { nullptr, 0 , nullptr }, /* 0x5C */ + { nullptr, 0 , nullptr }, /* 0x5D */ + { nullptr, 0 , nullptr }, /* 0x5E */ + { &i860_disassembler::flop_12d, DEC_DECODED, "fzchks" }, /* 0x5F, [p]fzchks */ + { nullptr, 0 , nullptr }, /* 0x60 */ + { nullptr, 0 , nullptr }, /* 0x61 */ + { nullptr, 0 , nullptr }, /* 0x62 */ + { nullptr, 0 , nullptr }, /* 0x63 */ + { nullptr, 0 , nullptr }, /* 0x64 */ + { nullptr, 0 , nullptr }, /* 0x65 */ + { nullptr, 0 , nullptr }, /* 0x66 */ + { nullptr, 0 , nullptr }, /* 0x67 */ + { nullptr, 0 , nullptr }, /* 0x68 */ + { nullptr, 0 , nullptr }, /* 0x69 */ + { nullptr, 0 , nullptr }, /* 0x6A */ + { nullptr, 0 , nullptr }, /* 0x6B */ + { nullptr, 0 , nullptr }, /* 0x6C */ + { nullptr, 0 , nullptr }, /* 0x6D */ + { nullptr, 0 , nullptr }, /* 0x6E */ + { nullptr, 0 , nullptr }, /* 0x6F */ + { nullptr, 0 , nullptr }, /* 0x70 */ + { nullptr, 0 , nullptr }, /* 0x71 */ + { nullptr, 0 , nullptr }, /* 0x72 */ + { nullptr, 0 , nullptr }, /* 0x73 */ + { nullptr, 0 , nullptr }, /* 0x74 */ + { nullptr, 0 , nullptr }, /* 0x75 */ + { nullptr, 0 , nullptr }, /* 0x76 */ + { nullptr, 0 , nullptr }, /* 0x77 */ + { nullptr, 0 , nullptr }, /* 0x78 */ + { nullptr, 0 , nullptr }, /* 0x79 */ + { nullptr, 0 , nullptr }, /* 0x7A */ + { nullptr, 0 , nullptr }, /* 0x7B */ + { nullptr, 0 , nullptr }, /* 0x7C */ + { nullptr, 0 , nullptr }, /* 0x7D */ + { nullptr, 0 , nullptr }, /* 0x7E */ + { nullptr, 0 , nullptr }, /* 0x7F */ }; /* Replaces tabs with spaces. */ -static void i860_dasm_tab_replacer(std::ostream &stream, const std::string &buf, int tab_size) +void i860_disassembler::i860_dasm_tab_replacer(std::ostream &stream, const std::string &buf, int tab_size) { int tab_count = 0; @@ -636,14 +613,11 @@ static void i860_dasm_tab_replacer(std::ostream &stream, const std::string &buf, } -static offs_t internal_disasm_i860(cpu_device *device, std::ostream &main_stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, int options) +offs_t i860_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - std::stringstream stream; + std::stringstream tstream; - uint32_t insn = (oprom[0] << 0) | - (oprom[1] << 8) | - (oprom[2] << 16) | - (oprom[3] << 24); + uint32_t insn = opcodes.r32(pc); int unrecognized_op = 1; int upper_6bits = (insn >> 26) & 0x3f; @@ -651,7 +625,7 @@ static offs_t internal_disasm_i860(cpu_device *device, std::ostream &main_stream if (flags & DEC_DECODED) { const char *s = decode_tbl[upper_6bits].mnemonic; - decode_tbl[upper_6bits].insn_dis (stream, (char *)s, pc, insn); + (this->*(decode_tbl[upper_6bits].insn_dis)) (tstream, (char *)s, pc, insn); unrecognized_op = 0; } else if (flags & DEC_MORE) @@ -663,7 +637,7 @@ static offs_t internal_disasm_i860(cpu_device *device, std::ostream &main_stream const char *s = fp_decode_tbl[insn & 0x7f].mnemonic; if (fp_flags & DEC_DECODED) { - fp_decode_tbl[insn & 0x7f].insn_dis (stream, (char *)s, pc, insn); + (this->*(fp_decode_tbl[insn & 0x7f].insn_dis)) (tstream, (char *)s, pc, insn); unrecognized_op = 0; } } @@ -674,25 +648,24 @@ static offs_t internal_disasm_i860(cpu_device *device, std::ostream &main_stream const char *s = core_esc_decode_tbl[insn & 0x3].mnemonic; if (esc_flags & DEC_DECODED) { - core_esc_decode_tbl[insn & 0x3].insn_dis (stream, (char *)s, pc, insn); + (this->*(core_esc_decode_tbl[insn & 0x3].insn_dis)) (tstream, (char *)s, pc, insn); unrecognized_op = 0; } } } if (unrecognized_op) - util::stream_format(stream, ".long\t%#08x", insn); + util::stream_format(tstream, ".long\t%#08x", insn); /* Replace tabs with spaces */ - i860_dasm_tab_replacer(main_stream, stream.str(), 10); + i860_dasm_tab_replacer(stream, tstream.str(), 10); /* Return number of bytes disassembled. */ /* MAME dasm flags haven't been added yet */ return (4); } - -CPU_DISASSEMBLE(i860) +u32 i860_disassembler::opcode_alignment() const { - return internal_disasm_i860(device, stream, pc, oprom, opram, options); + return 4; } diff --git a/src/devices/cpu/i860/i860dis.h b/src/devices/cpu/i860/i860dis.h new file mode 100644 index 00000000000..46847ba8648 --- /dev/null +++ b/src/devices/cpu/i860/i860dis.h @@ -0,0 +1,77 @@ +// license:BSD-3-Clause +// copyright-holders:Jason Eckhardt +/*************************************************************************** + + i860dis.c + + Disassembler for the Intel i860 emulator. + + Copyright (C) 1995-present Jason Eckhardt (jle@rice.edu) + +***************************************************************************/ + +#ifndef MAME_CPU_I860_I860DIS_H +#define MAME_CPU_I860_I860DIS_H + +#pragma once + +class i860_disassembler : public util::disasm_interface +{ +public: + i860_disassembler() = default; + virtual ~i860_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + /* Flags for the decode table. */ + enum + { + DEC_MORE = 1, /* More decoding necessary. */ + DEC_DECODED = 2 /* Fully decoded, go. */ + }; + + + struct decode_tbl_t + { + /* Disassembly function for this opcode. + Call with buffer, mnemonic, pc, insn. */ + void (i860_disassembler::*insn_dis)(std::ostream &, char *, uint32_t, uint32_t); + + /* Flags for this opcode. */ + char flags; + + /* Mnemonic of this opcode (sometimes partial when more decode is + done in disassembly routines-- e.g., loads and stores). */ + const char *mnemonic; + }; + + static const char *const cr2str[]; + static const decode_tbl_t decode_tbl[64]; + static const decode_tbl_t core_esc_decode_tbl[8]; + static const decode_tbl_t fp_decode_tbl[128]; + + int32_t sign_ext(uint32_t x, int n); + void int_12d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn); + void int_i2d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn); + void int_1d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn); + void int_cd(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn); + void int_1c(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn); + void int_1(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn); + void int_0(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn); + void flop_12d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn); + void flop_1d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn); + void flop_2d(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn); + void flop_fxfr(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn); + void int_12S(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn); + void int_i2S(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn); + void int_L(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn); + void int_ldx(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn); + void int_stx(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn); + void int_fldst(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn); + void int_flush(std::ostream &stream, char *mnemonic, uint32_t pc, uint32_t insn); + void i860_dasm_tab_replacer(std::ostream &stream, const std::string &buf, int tab_size); +}; + +#endif diff --git a/src/devices/cpu/i960/i960.cpp b/src/devices/cpu/i960/i960.cpp index dcffb837f95..5f7d140dcdf 100644 --- a/src/devices/cpu/i960/i960.cpp +++ b/src/devices/cpu/i960/i960.cpp @@ -2,10 +2,9 @@ // copyright-holders:Farfetch'd, R. Belmont #include "emu.h" #include "i960.h" +#include "i960dis.h" #include "debugger.h" -CPU_DISASSEMBLE( i960 ); - #ifdef _MSC_VER /* logb prototype is different for MS Visual C */ #include @@ -2209,9 +2208,7 @@ void i960_cpu_device::device_reset() m_rcache_pos = 0; } - -offs_t i960_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *i960_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( i960 ); - return CPU_DISASSEMBLE_NAME(i960)(this, stream, pc, oprom, opram, options); + return new i960_disassembler; } diff --git a/src/devices/cpu/i960/i960.h b/src/devices/cpu/i960/i960.h index 76d60109cf4..77f399960c5 100644 --- a/src/devices/cpu/i960/i960.h +++ b/src/devices/cpu/i960/i960.h @@ -97,9 +97,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 4; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 8; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/i960/i960dis.cpp b/src/devices/cpu/i960/i960dis.cpp index 43f81015240..5f4991fc77b 100644 --- a/src/devices/cpu/i960/i960dis.cpp +++ b/src/devices/cpu/i960/i960dis.cpp @@ -7,17 +7,10 @@ */ #include "emu.h" -#include "i960.h" #include "i960dis.h" -struct mnemonic_t -{ - const char *mnem; - unsigned short type; -}; - -static const mnemonic_t mnemonic[256] = { +const i960_disassembler::mnemonic_t i960_disassembler::mnemonic[256] = { { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, // 00 { "b", 8 }, { "call", 8 }, { "ret", 9 }, { "bal", 8 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, @@ -67,7 +60,7 @@ static const mnemonic_t mnemonic[256] = { { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 }, { "?", 0 } }; -static const mnemonic_t mnem_reg[100] = +const i960_disassembler::mnemonic_t i960_disassembler::mnem_reg[100] = { { "notbit", 0x580 }, { "and", 0x581 }, { "andnot", 0x582 }, { "setbit", 0x583 }, { "notand",0x584 }, { "xor", 0x586 }, { "or", 0x587 }, { "nor", 0x588 }, { "xnor",0x589 }, { "not",0x58a }, @@ -93,13 +86,13 @@ static const mnemonic_t mnem_reg[100] = { "ending_code",0 } }; -static const char *const constnames[32] = +const char *const i960_disassembler::constnames[32] = { "0x0", "0x1", "0x2", "0x3", "0x4", "0x5", "0x6", "0x7", "0x8", "0x9", "0xa", "0xb", "0xc", "0xd", "0xe", "0xf", "0x10", "0x11", "0x12", "0x13", "0x14", "0x15", "0x16", "0x17", "0x18", "0x19", "0x1a", "0x1b", "0x1c", "0x1d", "0x1e", "0x1f" }; -static const char *const regnames[32] = +const char *const i960_disassembler::regnames[32] = { "pfp","sp","rip","r3", "r4","r5","r6","r7", "r8","r9","r10","r11", "r12","r13","r14","r15", "g0","g1","g2","g3", "g4","g5","g6","g7", "g8","g9","g10","g11", "g12","g13","g14","fp", @@ -128,118 +121,120 @@ static const char *const regnames[32] = #define COBRSRC1 ((iCode >> 19) & 0x1f) #define COBRSRC2 ((iCode >> 14) & 0x1f) -static char *dis_decode_reg(unsigned long iCode, char* tmpStr,unsigned char cnt) +std::string i960_disassembler::dis_decode_reg(u32 iCode, unsigned char cnt) { - char src1[10]; - char src2[10]; - char dst[10]; + std::string src1, src2, dst; - if (S1) src1[0] = 0; + if (S1) + src1 = ""; else { - if(M1) sprintf(src1,"0x%lx",SRC1); - else sprintf(src1,"%s",regnames[SRC1]); + if(M1) + src1 = util::string_format("0x%lx", SRC1); + else + src1 = util::string_format("%s", regnames[SRC1]); } - if (S2) sprintf(src2,"reserved"); + + if (S2) + src2 = "reserved"; else { - if(M2) sprintf(src2,"0x%lx,",SRC2); - else sprintf(src2,"%s,",regnames[SRC2]); + if(M2) + src2 = util::string_format("0x%lx,", SRC2); + else + src2 = util::string_format("%s,", regnames[SRC2]); } - if(M3) dst[0] = 0; - else sprintf(dst,"%s,",regnames[DST]); + + if(M3) + dst = ""; + else + dst = util::string_format("%s,", regnames[DST]); + if (cnt == 1) - sprintf(tmpStr,"%s%s",dst,src1); + return util::string_format("%s%s", dst, src1); else - sprintf(tmpStr,"%s%s%s",dst,src2,src1); - return tmpStr; + return util::string_format("%s%s%s", dst, src2, src1); } -#define READ32(dis,offs) ((dis)->oprom[(offs) + 0] | ((dis)->oprom[(offs) + 1] << 8) | ((dis)->oprom[(offs) + 2] << 16) | ((dis)->oprom[(offs) + 3] << 24)) - -static void i960_disassemble(disassemble_t *diss) +offs_t i960_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - unsigned char op,op2; - unsigned char /*mode,*/ modeh, model; - unsigned char dst,abase,reg2; - unsigned short opc; - unsigned long iCode; - char tmpStr[256]; - long i; - - iCode = READ32(diss,0); - op = (unsigned char) (iCode >> 24); - op2 = (unsigned char) (iCode >> 7)&0xf; - - model = (unsigned char) (iCode >> 10) &0x3; - modeh = (unsigned char) (iCode >> 12) &0x3; + u32 IP = pc; + + u32 iCode = opcodes.r32(IP); + u8 op = (unsigned char) (iCode >> 24); + u8 op2 = (unsigned char) (iCode >> 7)&0xf; + u8 opc = 0; + u32 i = 0; + + u8 model = (unsigned char) (iCode >> 10) &0x3; + u8 modeh = (unsigned char) (iCode >> 12) &0x3; //mode = (unsigned char) (iCode >> 10) &0x7; - dst = (unsigned char) (iCode >> 19) &0x1f; - abase = (unsigned char) (iCode>>14)&0x1f; - reg2 = (unsigned char) (iCode)&0x1f; + u8 dst = (unsigned char) (iCode >> 19) &0x1f; + u8 abase = (unsigned char) (iCode>>14)&0x1f; + u8 reg2 = (unsigned char) (iCode)&0x1f; - diss->IPinc = 4; - diss->disflags = 0; + offs_t IPinc = 4; + offs_t disflags = 0; if (op == 0x09 || op == 0x0b || op == 0x66 || op == 0x85 || op == 0x86) - diss->disflags = DASMFLAG_STEP_OVER; + disflags = STEP_OVER; else if (op == 0x0a) - diss->disflags = DASMFLAG_STEP_OUT; + disflags = STEP_OUT; switch(mnemonic[op].type) { case 0: // not yet implemented - util::stream_format(diss->stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model); + util::stream_format(stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model); break; case 1: // memory access switch(modeh) { case 0: - util::stream_format(diss->stream, "%-8s%s,0x%lx",NEM,REG_DST, iCode&0xfff); + util::stream_format(stream, "%-8s%s,0x%lx",NEM,REG_DST, iCode&0xfff); break; case 1: switch (model) { case 0: - util::stream_format(diss->stream, "%-8s%s,(%s)",NEM,REG_DST, REG_ABASE); + util::stream_format(stream, "%-8s%s,(%s)",NEM,REG_DST, REG_ABASE); break; case 3: - util::stream_format(diss->stream, "%-8s%s,(%s)[%s*%ld]",NEM,REG_DST, REG_ABASE,REG_REG2,(iCode>>7)&0x7); + util::stream_format(stream, "%-8s%s,(%s)[%s*%ld]",NEM,REG_DST, REG_ABASE,REG_REG2,(iCode>>7)&0x7); break; default: - util::stream_format(diss->stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model); + util::stream_format(stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model); break; } break; case 2: - util::stream_format(diss->stream, "%-8s%s,0x%lx(%s)",NEM,REG_DST, iCode&0xfff,REG_ABASE); + util::stream_format(stream, "%-8s%s,0x%lx(%s)",NEM,REG_DST, iCode&0xfff,REG_ABASE); break; case 3: switch (model) { case 0: - util::stream_format(diss->stream, "%-8s%s,0x%x",NEM,REG_DST, READ32(diss,4)); - diss->IPinc = 8; + util::stream_format(stream, "%-8s%s,0x%x",NEM,REG_DST, opcodes.r32(IP + 4)); + IPinc = 8; break; case 1: - util::stream_format(diss->stream, "%-8s%s,0x%x(%s)",NEM,REG_DST, READ32(diss,4),REG_ABASE); - diss->IPinc = 8; + util::stream_format(stream, "%-8s%s,0x%x(%s)",NEM,REG_DST, opcodes.r32(IP + 4),REG_ABASE); + IPinc = 8; break; case 2: - util::stream_format(diss->stream, "%-8s%s,0x%x[%s*%ld]",NEM,REG_DST, READ32(diss,4),REG_REG2,(iCode>>7)&0x7); - diss->IPinc = 8; + util::stream_format(stream, "%-8s%s,0x%x[%s*%ld]",NEM,REG_DST, opcodes.r32(IP + 4),REG_REG2,(iCode>>7)&0x7); + IPinc = 8; break; case 3: - util::stream_format(diss->stream, "%-8s%s,0x%x(%s)[%s*%ld]",NEM,REG_DST, READ32(diss,4),REG_ABASE,REG_REG2,(iCode>>7)&0x7); - diss->IPinc = 8; + util::stream_format(stream, "%-8s%s,0x%x(%s)[%s*%ld]",NEM,REG_DST, opcodes.r32(IP + 4),REG_ABASE,REG_REG2,(iCode>>7)&0x7); + IPinc = 8; break; default: - util::stream_format(diss->stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model); + util::stream_format(stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model); break; } break; default: - util::stream_format(diss->stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model); + util::stream_format(stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model); break; } break; @@ -253,8 +248,8 @@ static void i960_disassemble(disassemble_t *diss) i++; } - if (mnem_reg[i].type == opc) util::stream_format(diss->stream, "%-8s%s", mnem_reg[i].mnem,dis_decode_reg(iCode,tmpStr,1)); - else util::stream_format(diss->stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model); + if (mnem_reg[i].type == opc) util::stream_format(stream, "%-8s%s", mnem_reg[i].mnem,dis_decode_reg(iCode,1)); + else util::stream_format(stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model); break; case 3: i = 0; @@ -266,38 +261,34 @@ static void i960_disassemble(disassemble_t *diss) i++; } - if (mnem_reg[i].type == opc) util::stream_format(diss->stream, "%-8s%s", mnem_reg[i].mnem,dis_decode_reg(iCode,tmpStr,0)); - else util::stream_format(diss->stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model); + if (mnem_reg[i].type == opc) util::stream_format(stream, "%-8s%s", mnem_reg[i].mnem,dis_decode_reg(iCode,0)); + else util::stream_format(stream, "%s %02x:%01x %08lx %1x %1x",mnemonic[op].mnem,op,op2,iCode, modeh, model); break; case 6: // bitpos and branch type - util::stream_format(diss->stream, "%-8s%ld,%s,0x%lx",NEM, COBRSRC1, REG_COBR_SRC2,((((long)iCode&0x00fffffc)<<19)>>19) + (diss->IP)); + util::stream_format(stream, "%-8s%ld,%s,0x%lx",NEM, COBRSRC1, REG_COBR_SRC2,((((s32)iCode&0x00fffffc)<<19)>>19) + (IP)); break; case 7: // compare and branch type - util::stream_format(diss->stream, "%-8s%s,%s,0x%lx",NEM,REG_COBR_SRC1,REG_COBR_SRC2,((((long)iCode&0x00fffffc)<<19)>>19) + (diss->IP)); + util::stream_format(stream, "%-8s%s,%s,0x%lx",NEM,REG_COBR_SRC1,REG_COBR_SRC2,((((s32)iCode&0x00fffffc)<<19)>>19) + (IP)); break; case 8: // target type - util::stream_format(diss->stream, "%-8s%08lx",NEM,((((long)iCode&0x00fffffc)<<8)>>8) + (diss->IP)); + util::stream_format(stream, "%-8s%08lx",NEM,((((s32)iCode&0x00fffffc)<<8)>>8) + (IP)); break; case 9: // no operands - util::stream_format(diss->stream, "%s",NEM); + util::stream_format(stream, "%s",NEM); break; case 10: // TEST type: register only - util::stream_format(diss->stream, "%s %s", NEM, REG_DST); + util::stream_format(stream, "%s %s", NEM, REG_DST); break; default: - diss->stream << "???"; + stream << "???"; break; } -} - + return IPinc | disflags | SUPPORTED; +} -CPU_DISASSEMBLE(i960) +u32 i960_disassembler::opcode_alignment() const { - disassemble_t dis(stream, pc, oprom); - - i960_disassemble(&dis); - - return dis.IPinc | dis.disflags | DASMFLAG_SUPPORTED; + return 4; } diff --git a/src/devices/cpu/i960/i960dis.h b/src/devices/cpu/i960/i960dis.h index 94e364fd666..2bc52697648 100644 --- a/src/devices/cpu/i960/i960dis.h +++ b/src/devices/cpu/i960/i960dis.h @@ -1,18 +1,33 @@ // license:BSD-3-Clause // copyright-holders:Farfetch'd, R. Belmont -#ifndef __I960DIS_H__ -#define __I960DIS_H__ +#ifndef MAME_CPU_I960_I960DIS_H +#define MAME_CPU_I960_I960DIS_H -struct disassemble_t +#pragma once + +class i960_disassembler : public util::disasm_interface { - disassemble_t(std::ostream &s, unsigned long ip, const uint8_t *opr) - : stream(s), IP(ip), oprom(opr) { } - - std::ostream &stream; // output stream - unsigned long IP; - unsigned long IPinc; - const uint8_t *oprom; - uint32_t disflags; +public: + i960_disassembler() = default; + virtual ~i960_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + struct mnemonic_t + { + const char *mnem; + unsigned short type; + }; + + static const mnemonic_t mnemonic[256]; + static const mnemonic_t mnem_reg[100]; + static const char *const constnames[32]; + static const char *const regnames[32]; + + std::string dis_decode_reg(u32 iCode, unsigned char cnt); + }; -#endif /* __I960DIS_H__ */ +#endif diff --git a/src/devices/cpu/ie15/ie15.cpp b/src/devices/cpu/ie15/ie15.cpp index e09d99c51a8..dd070e7f711 100644 --- a/src/devices/cpu/ie15/ie15.cpp +++ b/src/devices/cpu/ie15/ie15.cpp @@ -2,6 +2,7 @@ // copyright-holders:Sergey Svishchev #include "emu.h" #include "ie15.h" +#include "ie15dasm.h" #include "debugger.h" @@ -149,34 +150,12 @@ void ie15_cpu_device::state_string_export(const device_state_entry &entry, std:: } //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes +// create_disassembler //------------------------------------------------- -uint32_t ie15_cpu_device::disasm_min_opcode_bytes() const +util::disasm_interface *ie15_cpu_device::create_disassembler() { - return 1; -} - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t ie15_cpu_device::disasm_max_opcode_bytes() const -{ - return 2; -} - -//------------------------------------------------- -// disasm_disassemble - call the disassembly -// helper function -//------------------------------------------------- - -offs_t ie15_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) -{ - extern CPU_DISASSEMBLE( ie15 ); - return CPU_DISASSEMBLE_NAME(ie15)(nullptr, stream, pc, oprom, opram, 0); + return new ie15_disassembler; } //************************************************************************** diff --git a/src/devices/cpu/ie15/ie15.h b/src/devices/cpu/ie15/ie15.h index 2a39a663fed..f990da84276 100644 --- a/src/devices/cpu/ie15/ie15.h +++ b/src/devices/cpu/ie15/ie15.h @@ -44,9 +44,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void execute_one(int opcode); diff --git a/src/devices/cpu/ie15/ie15dasm.cpp b/src/devices/cpu/ie15/ie15dasm.cpp index f13e8f52e44..1318c58d6d5 100644 --- a/src/devices/cpu/ie15/ie15dasm.cpp +++ b/src/devices/cpu/ie15/ie15dasm.cpp @@ -1,34 +1,37 @@ // license:BSD-3-Clause // copyright-holders:Sergey Svishchev #include "emu.h" +#include "ie15dasm.h" -#define OP(A) oprom[(A) - PC] -#define ARG(A) opram[(A) - PC] +u32 ie15_disassembler::opcode_alignment() const +{ + return 1; +} -CPU_DISASSEMBLE(ie15) +offs_t ie15_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { uint32_t flags = 0; uint8_t op; unsigned PC = pc; - op = OP(pc++); + op = opcodes.r8(pc++); switch (op & 0xf0) { case 0x00: util::stream_format(stream, "add r%d", op & 0x0f); break; case 0x10: - util::stream_format(stream, "jmp $%04x", (((op & 0x0f) << 8) | ARG(pc)) + 1); + util::stream_format(stream, "jmp $%04x", (((op & 0x0f) << 8) | params.r8(pc)) + 1); pc+=1; break; case 0x20: - util::stream_format(stream, "ldc r%d, #$%02x", (op & 0x0f), ARG(pc)); + util::stream_format(stream, "ldc r%d, #$%02x", (op & 0x0f), params.r8(pc)); pc+=1; break; case 0x30: switch (op) { case 0x30: - util::stream_format(stream, "lca #$%02x", ARG(pc)); + util::stream_format(stream, "lca #$%02x", params.r8(pc)); pc+=1; break; case 0x33: @@ -123,5 +126,5 @@ CPU_DISASSEMBLE(ie15) break; } - return (pc - PC) | flags | DASMFLAG_SUPPORTED; + return (pc - PC) | flags | SUPPORTED; } diff --git a/src/devices/cpu/ie15/ie15dasm.h b/src/devices/cpu/ie15/ie15dasm.h new file mode 100644 index 00000000000..fb85a7a3d1c --- /dev/null +++ b/src/devices/cpu/ie15/ie15dasm.h @@ -0,0 +1,19 @@ +// license:BSD-3-Clause +// copyright-holders:Sergey Svishchev + +#ifndef MAME_CPU_IE15_IE15DASM_H +#define MAME_CPU_IE15_IE15DASM_H + +#pragma once + +class ie15_disassembler : public util::disasm_interface +{ +public: + ie15_disassembler() = default; + virtual ~ie15_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/jaguar/jagdasm.cpp b/src/devices/cpu/jaguar/jagdasm.cpp index 538f35b4b48..97c049594d6 100644 --- a/src/devices/cpu/jaguar/jagdasm.cpp +++ b/src/devices/cpu/jaguar/jagdasm.cpp @@ -9,27 +9,16 @@ ***************************************************************************/ #include "emu.h" -#include "jaguar.h" - - -/*************************************************************************** - MEMORY ACCESSORS -***************************************************************************/ - -#define ROPCODE(offs) ((oprom[offs] << 8) | oprom[(offs) + 1]) - +#include "jagdasm.h" /*************************************************************************** STATIC VARIABLES ***************************************************************************/ -static constexpr unsigned JAGUAR_VARIANT_GPU = 0; -static constexpr unsigned JAGUAR_VARIANT_DSP = 1; - -static const uint8_t convert_zero[32] = +const uint8_t jaguar_disassembler::convert_zero[32] = { 32,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31 }; -static const char *const condition[32] = +const char *const jaguar_disassembler::condition[32] = { "", "nz,", @@ -72,20 +61,18 @@ static const char *const condition[32] = CODE CODE ***************************************************************************/ -static inline char *signed_16bit(int16_t val) +std::string jaguar_disassembler::signed_16bit(int16_t val) { - static char temp[10]; if (val < 0) - sprintf(temp, "-$%x", -val); + return util::string_format("-$%x", -val); else - sprintf(temp, "$%x", val); - return temp; + return util::string_format("$%x", val); } -static unsigned dasmjag(int variant, std::ostream &stream, unsigned pc, const uint8_t *oprom) +offs_t jaguar_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { uint32_t flags = 0; - int op = ROPCODE(0); + int op = opcodes.r16(pc); int reg1 = (op >> 5) & 31; int reg2 = op & 31; int size = 2; @@ -126,12 +113,12 @@ static unsigned dasmjag(int variant, std::ostream &stream, unsigned pc, const ui case 30: util::stream_format(stream, "cmp r%d,r%d", reg1, reg2); break; case 31: util::stream_format(stream, "cmpq %s,r%d", signed_16bit((int16_t)(reg1 << 11) >> 11), reg2);break; - case 32: if (variant == JAGUAR_VARIANT_GPU) + case 32: if (m_variant == JAGUAR_VARIANT_GPU) util::stream_format(stream, "sat8 r%d", reg2); else util::stream_format(stream, "subqmod $%x,r%d", convert_zero[reg1], reg2); break; - case 33: if (variant == JAGUAR_VARIANT_GPU) + case 33: if (m_variant == JAGUAR_VARIANT_GPU) util::stream_format(stream, "sat16 r%d", reg2); else util::stream_format(stream, "sat16s r%d", reg2); @@ -140,11 +127,11 @@ static unsigned dasmjag(int variant, std::ostream &stream, unsigned pc, const ui case 35: util::stream_format(stream, "moveq %d,r%d", reg1, reg2); break; case 36: util::stream_format(stream, "moveta r%d,r%d", reg1, reg2); break; case 37: util::stream_format(stream, "movefa r%d,r%d", reg1, reg2); break; - case 38: util::stream_format(stream, "movei $%x,r%d", ROPCODE(2) | (ROPCODE(4)<<16), reg2); size = 6; break; + case 38: util::stream_format(stream, "movei $%x,r%d", opcodes.r32(pc+2), reg2); size = 6; break; case 39: util::stream_format(stream, "loadb (r%d),r%d", reg1, reg2); break; case 40: util::stream_format(stream, "loadw (r%d),r%d", reg1, reg2); break; case 41: util::stream_format(stream, "load (r%d),r%d", reg1, reg2); break; - case 42: if (variant == JAGUAR_VARIANT_GPU) + case 42: if (m_variant == JAGUAR_VARIANT_GPU) util::stream_format(stream, "loadp (r%d),r%d", reg1, reg2); else util::stream_format(stream, "sat32s r%d", reg2); @@ -154,7 +141,7 @@ static unsigned dasmjag(int variant, std::ostream &stream, unsigned pc, const ui case 45: util::stream_format(stream, "storeb r%d,(r%d)", reg2, reg1); break; case 46: util::stream_format(stream, "storew r%d,(r%d)", reg2, reg1); break; case 47: util::stream_format(stream, "store r%d,(r%d)", reg2, reg1); break; - case 48: if (variant == JAGUAR_VARIANT_GPU) + case 48: if (m_variant == JAGUAR_VARIANT_GPU) util::stream_format(stream, "storep r%d,(r%d)", reg2, reg1); else util::stream_format(stream, "mirror r%d", reg2); @@ -172,12 +159,12 @@ static unsigned dasmjag(int variant, std::ostream &stream, unsigned pc, const ui case 59: util::stream_format(stream, "load (r15+r%d),r%d", reg1, reg2); break; case 60: util::stream_format(stream, "store r%d,(r14+r%d)", reg2, reg1); break; case 61: util::stream_format(stream, "store r%d,(r15+r%d)", reg2, reg1); break; - case 62: if (variant == JAGUAR_VARIANT_GPU) + case 62: if (m_variant == JAGUAR_VARIANT_GPU) util::stream_format(stream, "sat24 r%d", reg2); else util::stream_format(stream, "illegal"); break; - case 63: if (variant == JAGUAR_VARIANT_GPU) + case 63: if (m_variant == JAGUAR_VARIANT_GPU) util::stream_format(stream, reg1 ? "unpack r%d" : "pack r%d", reg2); @@ -186,15 +173,14 @@ static unsigned dasmjag(int variant, std::ostream &stream, unsigned pc, const ui break; } - return size | flags | DASMFLAG_SUPPORTED; + return size | flags | SUPPORTED; } -CPU_DISASSEMBLE( jaguargpu ) +jaguar_disassembler::jaguar_disassembler(u32 variant) : m_variant(variant) { - return dasmjag(JAGUAR_VARIANT_GPU, stream, pc, oprom); } -CPU_DISASSEMBLE( jaguardsp ) +uint32_t jaguar_disassembler::opcode_alignment() const { - return dasmjag(JAGUAR_VARIANT_DSP, stream, pc, oprom); + return 2; } diff --git a/src/devices/cpu/jaguar/jagdasm.h b/src/devices/cpu/jaguar/jagdasm.h new file mode 100644 index 00000000000..232fda13b1f --- /dev/null +++ b/src/devices/cpu/jaguar/jagdasm.h @@ -0,0 +1,37 @@ +// license:BSD-3-Clause +// copyright-holders:Aaron Giles +/*************************************************************************** + + jagdasm.c + Disassembler for the portable Jaguar DSP emulator. + Written by Aaron Giles + +***************************************************************************/ + +#ifndef MAME_CPU_JAGUAR_JAGDASM_H +#define MAME_CPU_JAGUAR_JAGDASM_H + +#pragma once + +class jaguar_disassembler : public util::disasm_interface +{ +public: + static constexpr unsigned JAGUAR_VARIANT_GPU = 0; + static constexpr unsigned JAGUAR_VARIANT_DSP = 1; + + jaguar_disassembler(u32 variant); + virtual ~jaguar_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const uint8_t convert_zero[32]; + static const char *const condition[32]; + + u32 m_variant; + + static std::string signed_16bit(int16_t val); +}; + +#endif diff --git a/src/devices/cpu/jaguar/jaguar.cpp b/src/devices/cpu/jaguar/jaguar.cpp index 3b52ae1bfcc..9039b25ad72 100644 --- a/src/devices/cpu/jaguar/jaguar.cpp +++ b/src/devices/cpu/jaguar/jaguar.cpp @@ -11,6 +11,7 @@ #include "emu.h" #include "debugger.h" #include "jaguar.h" +#include "jagdasm.h" #define LOG_GPU_IO 0 @@ -1436,16 +1437,12 @@ WRITE32_MEMBER( jaguardsp_cpu_device::ctrl_w ) } } - -offs_t jaguargpu_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *jaguargpu_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( jaguargpu ); - return CPU_DISASSEMBLE_NAME(jaguargpu)(this, stream, pc, oprom, opram, options); + return new jaguar_disassembler(jaguar_disassembler::JAGUAR_VARIANT_GPU); } - -offs_t jaguardsp_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *jaguardsp_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( jaguardsp ); - return CPU_DISASSEMBLE_NAME(jaguardsp)(this, stream, pc, oprom, opram, options); + return new jaguar_disassembler(jaguar_disassembler::JAGUAR_VARIANT_DSP); } diff --git a/src/devices/cpu/jaguar/jaguar.h b/src/devices/cpu/jaguar/jaguar.h index 1bc5ddf8d64..ae79ffe1d8a 100644 --- a/src/devices/cpu/jaguar/jaguar.h +++ b/src/devices/cpu/jaguar/jaguar.h @@ -120,10 +120,6 @@ protected: // device_state_interface overrides virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; - // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 6; } - address_space_config m_program_config; /* core registers */ @@ -249,7 +245,7 @@ public: protected: virtual void execute_run() override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; }; @@ -266,7 +262,7 @@ protected: virtual uint32_t execute_input_lines() const override { return 6; } virtual void execute_run() override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; }; diff --git a/src/devices/cpu/lc8670/lc8670.cpp b/src/devices/cpu/lc8670/lc8670.cpp index c78a0acd4c8..e93c134cab5 100644 --- a/src/devices/cpu/lc8670/lc8670.cpp +++ b/src/devices/cpu/lc8670/lc8670.cpp @@ -18,6 +18,7 @@ #include "emu.h" #include "debugger.h" #include "lc8670.h" +#include "lc8670dsm.h" //*************************************************************************** // DEBUGGING @@ -1777,3 +1778,8 @@ int lc8670_cpu_device::op_xor() return 1; } + +util::disasm_interface *lc8670_cpu_device::create_disassembler() +{ + return new lc8670_disassembler; +} diff --git a/src/devices/cpu/lc8670/lc8670.h b/src/devices/cpu/lc8670/lc8670.h index a6de4f7c98a..40727da5fb9 100644 --- a/src/devices/cpu/lc8670/lc8670.h +++ b/src/devices/cpu/lc8670/lc8670.h @@ -115,9 +115,7 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: // helpers @@ -142,7 +140,6 @@ private: void timer0_tick(bool ext_line = false); void timer1_tick(); void base_timer_tick(); - static void dasm_arg(uint8_t op, char *buffer, offs_t pc, int arg, const uint8_t *oprom, int &pos); // opcodes handlers int op_nop(); @@ -240,33 +237,6 @@ private: // opcodes table typedef int (lc8670_cpu_device::*op_handler)(); static const op_handler s_opcode_table[80]; - - // disassembler - enum - { - OP_NULL, - OP_R8, - OP_R8RI, - OP_R16, - OP_RI, - OP_A12, - OP_A16, - OP_I8, - OP_B3, - OP_D9, - OP_D9B3, - OP_RII8 - }; - - // disasm table - struct dasm_entry - { - const char *str; - uint8_t arg1; - uint8_t arg2; - bool inv; - }; - static const dasm_entry s_dasm_table[80]; }; DECLARE_DEVICE_TYPE(LC8670, lc8670_cpu_device) diff --git a/src/devices/cpu/lc8670/lc8670dsm.cpp b/src/devices/cpu/lc8670/lc8670dsm.cpp index d1a223fc3a8..540b4d55377 100644 --- a/src/devices/cpu/lc8670/lc8670dsm.cpp +++ b/src/devices/cpu/lc8670/lc8670dsm.cpp @@ -7,10 +7,14 @@ ******************************************************************************/ #include "emu.h" -#include "debugger.h" -#include "lc8670.h" +#include "lc8670dsm.h" -const lc8670_cpu_device::dasm_entry lc8670_cpu_device::s_dasm_table[] = +u32 lc8670_disassembler::opcode_alignment() const +{ + return 1; +} + +const lc8670_disassembler::dasm_entry lc8670_disassembler::s_dasm_table[] = { { "NOP" , OP_NULL, OP_NULL, 0 }, // 0x0* { "BR" , OP_R8 , OP_NULL, 0 }, @@ -94,7 +98,7 @@ const lc8670_cpu_device::dasm_entry lc8670_cpu_device::s_dasm_table[] = { "SET1", OP_D9B3, OP_NULL, 0 }, }; -void lc8670_cpu_device::dasm_arg(uint8_t op, char *buffer, offs_t pc, int arg, const uint8_t *oprom, int &pos) +void lc8670_disassembler::dasm_arg(uint8_t op, char *buffer, offs_t pc, int arg, const data_buffer &opcodes, offs_t &pos) { switch( arg ) { @@ -105,71 +109,88 @@ void lc8670_cpu_device::dasm_arg(uint8_t op, char *buffer, offs_t pc, int arg, c pc++; // fall through case OP_R8RI: - buffer += sprintf(buffer, "%04x", (pc + 1 + oprom[pos] - (oprom[pos]&0x80 ? 0x100 : 0)) & 0xffff); + buffer += sprintf(buffer, "%04x", (pc + 1 + opcodes.r8(pos) - (opcodes.r8(pos)&0x80 ? 0x100 : 0)) & 0xffff); pos++; break; case OP_R16: - buffer += sprintf(buffer, "%04x", (pc + 2 + ((oprom[pos+1]<<8) | oprom[pos])) & 0xffff); + buffer += sprintf(buffer, "%04x", (pc + 2 + ((opcodes.r8(pos+1)<<8) | opcodes.r8(pos))) & 0xffff); pos += 2; break; case OP_RI: buffer += sprintf(buffer, "@%x", op & 0x03); break; case OP_A12: - buffer += sprintf(buffer, "%04x", ((pc + 2) & 0xf000) | ((op & 0x10)<<7) | ((op & 0x07)<<8) | oprom[pos]); + buffer += sprintf(buffer, "%04x", ((pc + 2) & 0xf000) | ((op & 0x10)<<7) | ((op & 0x07)<<8) | opcodes.r8(pos)); pos++; break; case OP_A16: - buffer += sprintf(buffer, "%04x", (oprom[pos]<<8) | oprom[pos+1]); + buffer += sprintf(buffer, "%04x", (opcodes.r8(pos)<<8) | opcodes.r8(pos+1)); pos += 2; break; case OP_I8: - buffer += sprintf(buffer, "#$%02x", oprom[pos++]); + buffer += sprintf(buffer, "#$%02x", opcodes.r8(pos++)); break; case OP_B3: buffer += sprintf(buffer, "%x", op & 0x07); break; case OP_D9: - buffer += sprintf(buffer, "($%03x)", ((op & 0x01)<<8) | oprom[pos]); + buffer += sprintf(buffer, "($%03x)", ((op & 0x01)<<8) | opcodes.r8(pos)); pos++; break; case OP_D9B3: - buffer += sprintf(buffer, "($%03x)", ((op & 0x10)<<4) | oprom[pos]); + buffer += sprintf(buffer, "($%03x)", ((op & 0x10)<<4) | opcodes.r8(pos)); buffer += sprintf(buffer, ",%x", op & 0x07); pos++; break; case OP_RII8: buffer += sprintf(buffer, "@%x", op & 0x03); - buffer += sprintf(buffer, ",#$%02x", oprom[pos]); + buffer += sprintf(buffer, ",#$%02x", opcodes.r8(pos)); pos++; break; } } //------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t lc8670_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +offs_t lc8670_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - int pos = 0; + offs_t pos = pc; char arg1[16], arg2[16]; - uint8_t op = oprom[pos++]; + uint8_t op = opcodes.r8(pos); + + int idx; + switch (op & 0x0f) + { + case 0: case 1: + idx = op & 0x0f; + break; + case 2: case 3: + idx = 2; + break; + case 4: case 5: case 6: case 7: + idx = 3; + break; + default: + idx = 4; + break; + } - int op_idx = decode_op(op); + int op_idx = ((op>>4) & 0x0f) * 5 + idx; const dasm_entry *inst = &s_dasm_table[op_idx]; util::stream_format(stream, "%-8s", inst->str); - dasm_arg(op, inst->inv ? arg2 : arg1, pc+0, inst->arg1, oprom, pos); - dasm_arg(op, inst->inv ? arg1 : arg2, pc+1, inst->arg2, oprom, pos); + dasm_arg(op, inst->inv ? arg2 : arg1, pc+0, inst->arg1, opcodes, pos); + dasm_arg(op, inst->inv ? arg1 : arg2, pc+1, inst->arg2, opcodes, pos); stream << arg1; if (inst->arg2 != OP_NULL) stream << "," << arg2; - return pos; + return pos - pc; } diff --git a/src/devices/cpu/lc8670/lc8670dsm.h b/src/devices/cpu/lc8670/lc8670dsm.h new file mode 100644 index 00000000000..c59da2add6d --- /dev/null +++ b/src/devices/cpu/lc8670/lc8670dsm.h @@ -0,0 +1,54 @@ +// license:BSD-3-Clause +// copyright-holders:Sandro Ronco +/****************************************************************************** + + Sanyo LC8670 disassembler + +******************************************************************************/ + +#ifndef MAME_CPU_LC8670_LC8670DSM_H +#define MAME_CPU_LC8670_LC8670DSM_H + +#pragma once + +class lc8670_disassembler : public util::disasm_interface +{ +public: + lc8670_disassembler() = default; + virtual ~lc8670_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + // disassembler + enum + { + OP_NULL, + OP_R8, + OP_R8RI, + OP_R16, + OP_RI, + OP_A12, + OP_A16, + OP_I8, + OP_B3, + OP_D9, + OP_D9B3, + OP_RII8 + }; + + // disasm table + struct dasm_entry + { + const char *str; + uint8_t arg1; + uint8_t arg2; + bool inv; + }; + static const dasm_entry s_dasm_table[80]; + + void dasm_arg(uint8_t op, char *buffer, offs_t pc, int arg, const data_buffer &opcodes, offs_t &pos); +}; + +#endif diff --git a/src/devices/cpu/lh5801/5801dasm.cpp b/src/devices/cpu/lh5801/5801dasm.cpp index 2cf6f105b8d..f289f4760a0 100644 --- a/src/devices/cpu/lh5801/5801dasm.cpp +++ b/src/devices/cpu/lh5801/5801dasm.cpp @@ -9,104 +9,14 @@ *****************************************************************************/ #include "emu.h" -#include "debugger.h" - -#include "lh5801.h" +#include "5801dasm.h" #if defined(SEC) #undef SEC #endif -namespace { - -class Entry -{ -public: - enum Ins - { - ILL, ILL2, PREFD, NOP, - - LDA, STA, LDI, LDX, STX, - LDE, SDE, LIN, SIN, - TIN, // (x++)->(y++) - ADC, ADI, ADR, SBC, SBI, - DCA, DCS, // bcd add and sub - CPA, CPI, CIN, // A compared with (x++) - AND, ANI, ORA, ORI, EOR, EAI, BIT, BII, - INC, DEC, - DRL, DRR, // digit rotates - ROL, ROR, - SHL, SHR, - AEX, // A nibble swap - - BCR, BCS, BHR, BHS, BZR, BZS, BVR, BVS, - BCH, LOP, // loop with ul - JMP, SJP, RTN, RTI, HLT, - VCR, VCS, VHR, VHS, VVS, VZR, VZS, - VMJ, VEJ, - PSH, POP, ATT, TTA, - REC, SEC, RIE, SIE, - - AM0, AM1, // load timer reg - ITA, // reads input port - ATP, // akku send to data bus - CDV, // clears internal divider - OFF, // clears bf flip flop - RDP, SDP,// reset display flip flop - RPU, SPU,// flip flop pu off - RPV, SPV // flip flop pv off - }; - - enum Adr - { - Imp, - Reg, - Vec, // imm byte (vector at 0xffxx) - Vej, - Imm, - RegImm, - Imm16, - RegImm16, - ME0, - ME0Imm, - Abs, - AbsImm, - ME1, - ME1Imm, - ME1Abs, - ME1AbsImm, - RelP, - RelM - }; - - enum Regs - { - RegNone, - A, - XL, XH, X, - YL, YH, Y, - UL, UH, U, - P, S - }; - const char *ins_name() const { return ins_names[ins]; } - const char *reg_name() const { return reg_names[reg]; } - - Ins ins; - Adr adr; - Regs reg; - - static const Entry table[0x100]; - static const Entry table_fd[0x100]; - -protected: - Entry(Ins i, Adr a = Imp, Regs r = RegNone) : ins(i), adr(a), reg(r) { } - - static const char *const ins_names[]; - static const char *const reg_names[]; -}; - -const char *const Entry::ins_names[]={ +const char *const lh5801_disassembler::ins_names[]={ "ILL", "ILL", nullptr, "NOP", "LDA", "STA", "LDI", "LDX", "STX", "LDE", "SDE", "LIN", "SIN", @@ -138,11 +48,11 @@ const char *const Entry::ins_names[]={ "RPV", "SPV", }; -const char *const Entry::reg_names[]= { +const char *const lh5801_disassembler::reg_names[]= { nullptr, "A", "XL", "XH", "X", "YL", "YH", "Y", "UL", "UH", "U", "P", "S" }; -const Entry Entry::table[0x100]={ +const lh5801_disassembler::Entry lh5801_disassembler::table[0x100]={ { SBC, Reg, XL }, // 0 { SBC, ME0, X }, { ADC, Reg, XL }, @@ -401,7 +311,7 @@ const Entry Entry::table[0x100]={ { ILL } }; -const Entry Entry::table_fd[0x100]={ +const lh5801_disassembler::Entry lh5801_disassembler::table_fd[0x100]={ { ILL2 }, // 0x00 { SBC, ME1, X }, { ILL2 }, @@ -660,90 +570,93 @@ const Entry Entry::table_fd[0x100]={ { ILL2 } }; -} // anonymous namespace +u32 lh5801_disassembler::opcode_alignment() const +{ + return 1; +} -CPU_DISASSEMBLE(lh5801) +offs_t lh5801_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - int pos = 0; + offs_t pos = pc; int oper; uint16_t absolut; const Entry *entry; int temp; - oper=oprom[pos++]; - entry=Entry::table+oper; + oper=opcodes.r8(pos++); + entry=table+oper; - if (Entry::table[oper].ins==Entry::PREFD) { - oper=oprom[pos++]; - entry=Entry::table_fd+oper; + if (table[oper].ins==PREFD) { + oper=opcodes.r8(pos++); + entry=table_fd+oper; } switch (entry->ins) { - case Entry::ILL: + case ILL: util::stream_format(stream, "%s %02x", entry->ins_name(), oper);break; - case Entry::ILL2: + case ILL2: util::stream_format(stream, "%s fd%02x", entry->ins_name(), oper);break; default: switch(entry->adr) { - case Entry::Imp: + case Imp: util::stream_format(stream, "%s", entry->ins_name());break; - case Entry::Reg: + case Reg: util::stream_format(stream, "%s %s", entry->ins_name(),entry->reg_name());break; - case Entry::RegImm: + case RegImm: util::stream_format(stream, "%s %s,%02x", entry->ins_name(), - entry->reg_name(), oprom[pos++]); + entry->reg_name(), opcodes.r8(pos++)); break; - case Entry::RegImm16: - absolut=oprom[pos++]<<8; - absolut|=oprom[pos++]; + case RegImm16: + absolut=opcodes.r8(pos++)<<8; + absolut|=opcodes.r8(pos++); util::stream_format(stream, "%s %s,%04x", entry->ins_name(),entry->reg_name(),absolut ); break; - case Entry::Vec: - util::stream_format(stream, "%s (ff%02x)", entry->ins_name(),oprom[pos++]);break; - case Entry::Vej: + case Vec: + util::stream_format(stream, "%s (ff%02x)", entry->ins_name(),opcodes.r8(pos++));break; + case Vej: util::stream_format(stream, "%s (ff%02x)", entry->ins_name(), oper);break; - case Entry::Imm: - util::stream_format(stream, "%s %02x", entry->ins_name(),oprom[pos++]);break; - case Entry::Imm16: - absolut=oprom[pos++]<<8; - absolut|=oprom[pos++]; + case Imm: + util::stream_format(stream, "%s %02x", entry->ins_name(),opcodes.r8(pos++));break; + case Imm16: + absolut=opcodes.r8(pos++)<<8; + absolut|=opcodes.r8(pos++); util::stream_format(stream, "%s %04x", entry->ins_name(),absolut);break; - case Entry::RelP: - temp=oprom[pos++]; + case RelP: + temp=opcodes.r8(pos++); util::stream_format(stream, "%s %04x", entry->ins_name(),pc+pos+temp);break; - case Entry::RelM: - temp=oprom[pos++]; + case RelM: + temp=opcodes.r8(pos++); util::stream_format(stream, "%s %04x", entry->ins_name(),pc+pos-temp);break; - case Entry::Abs: - absolut=oprom[pos++]<<8; - absolut|=oprom[pos++]; + case Abs: + absolut=opcodes.r8(pos++)<<8; + absolut|=opcodes.r8(pos++); util::stream_format(stream, "%s (%04x)", entry->ins_name(),absolut);break; - case Entry::ME1Abs: - absolut=oprom[pos++]<<8; - absolut|=oprom[pos++]; + case ME1Abs: + absolut=opcodes.r8(pos++)<<8; + absolut|=opcodes.r8(pos++); util::stream_format(stream, "%s #(%04x)", entry->ins_name(),absolut);break; - case Entry::AbsImm: - absolut=oprom[pos++]<<8; - absolut|=oprom[pos++]; + case AbsImm: + absolut=opcodes.r8(pos++)<<8; + absolut|=opcodes.r8(pos++); util::stream_format(stream, "%s (%04x),%02x", entry->ins_name(),absolut, - oprom[pos++]);break; - case Entry::ME1AbsImm: - absolut=oprom[pos++]<<8; - absolut|=oprom[pos++]; + opcodes.r8(pos++));break; + case ME1AbsImm: + absolut=opcodes.r8(pos++)<<8; + absolut|=opcodes.r8(pos++); util::stream_format(stream, "%s #(%04x),%02x", entry->ins_name(),absolut, - oprom[pos++]);break; - case Entry::ME0: + opcodes.r8(pos++));break; + case ME0: util::stream_format(stream, "%s (%s)", entry->ins_name(),entry->reg_name());break; - case Entry::ME0Imm: - util::stream_format(stream, "%s (%s),%02x", entry->ins_name(),entry->reg_name(),oprom[pos++]); + case ME0Imm: + util::stream_format(stream, "%s (%s),%02x", entry->ins_name(),entry->reg_name(),opcodes.r8(pos++)); break; - case Entry::ME1: + case ME1: util::stream_format(stream, "%s #(%s)", entry->ins_name(),entry->reg_name());break; - case Entry::ME1Imm: - util::stream_format(stream, "%s #(%s),%02x", entry->ins_name(),entry->reg_name(),oprom[pos++]); + case ME1Imm: + util::stream_format(stream, "%s #(%s),%02x", entry->ins_name(),entry->reg_name(),opcodes.r8(pos++)); break; } } - return pos; + return pos - pc; } diff --git a/src/devices/cpu/lh5801/5801dasm.h b/src/devices/cpu/lh5801/5801dasm.h new file mode 100644 index 00000000000..9a6b66b0c5b --- /dev/null +++ b/src/devices/cpu/lh5801/5801dasm.h @@ -0,0 +1,110 @@ +// license:BSD-3-Clause +// copyright-holders:Peter Trauner +/***************************************************************************** + * + * disasm.c + * portable lh5801 emulator interface + * + * + *****************************************************************************/ + +#ifndef MAME_CPU_LH5801_5801DASM_H +#define MAME_CPU_LH5801_5801DASM_H + +#pragma once + +class lh5801_disassembler : public util::disasm_interface +{ +public: + lh5801_disassembler() = default; + virtual ~lh5801_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum Ins + { + ILL, ILL2, PREFD, NOP, + + LDA, STA, LDI, LDX, STX, + LDE, SDE, LIN, SIN, + TIN, // (x++)->(y++) + ADC, ADI, ADR, SBC, SBI, + DCA, DCS, // bcd add and sub + CPA, CPI, CIN, // A compared with (x++) + AND, ANI, ORA, ORI, EOR, EAI, BIT, BII, + INC, DEC, + DRL, DRR, // digit rotates + ROL, ROR, + SHL, SHR, + AEX, // A nibble swap + + BCR, BCS, BHR, BHS, BZR, BZS, BVR, BVS, + BCH, LOP, // loop with ul + JMP, SJP, RTN, RTI, HLT, + VCR, VCS, VHR, VHS, VVS, VZR, VZS, + VMJ, VEJ, + PSH, POP, ATT, TTA, + REC, SEC, RIE, SIE, + + AM0, AM1, // load timer reg + ITA, // reads input port + ATP, // akku send to data bus + CDV, // clears internal divider + OFF, // clears bf flip flop + RDP, SDP,// reset display flip flop + RPU, SPU,// flip flop pu off + RPV, SPV // flip flop pv off + }; + + enum Adr + { + Imp, + Reg, + Vec, // imm byte (vector at 0xffxx) + Vej, + Imm, + RegImm, + Imm16, + RegImm16, + ME0, + ME0Imm, + Abs, + AbsImm, + ME1, + ME1Imm, + ME1Abs, + ME1AbsImm, + RelP, + RelM + }; + + enum Regs + { + RegNone, + A, + XL, XH, X, + YL, YH, Y, + UL, UH, U, + P, S + }; + + struct Entry { + Ins ins; + Adr adr; + Regs reg; + + const char *ins_name() const { return ins_names[ins]; } + const char *reg_name() const { return reg_names[reg]; } + Entry(Ins i, Adr a = Imp, Regs r = RegNone) : ins(i), adr(a), reg(r) { } + }; + + static const char *const ins_names[]; + static const char *const reg_names[]; + + static const Entry table[0x100]; + static const Entry table_fd[0x100]; +}; + +#endif diff --git a/src/devices/cpu/lh5801/lh5801.cpp b/src/devices/cpu/lh5801/lh5801.cpp index 2b4a3708e44..1a28c90fc05 100644 --- a/src/devices/cpu/lh5801/lh5801.cpp +++ b/src/devices/cpu/lh5801/lh5801.cpp @@ -16,6 +16,7 @@ #include "emu.h" #include "lh5801.h" +#include "5801dasm.h" #include "debugger.h" @@ -256,8 +257,7 @@ void lh5801_cpu_device::execute_set_input(int irqline, int state) } } -offs_t lh5801_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *lh5801_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( lh5801 ); - return CPU_DISASSEMBLE_NAME(lh5801)(this, stream, pc, oprom, opram, options); + return new lh5801_disassembler; } diff --git a/src/devices/cpu/lh5801/lh5801.h b/src/devices/cpu/lh5801/lh5801.h index bc9ce08cdd6..51ffa7c00cd 100644 --- a/src/devices/cpu/lh5801/lh5801.h +++ b/src/devices/cpu/lh5801/lh5801.h @@ -93,9 +93,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 5; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/lr35902/lr35902.cpp b/src/devices/cpu/lr35902/lr35902.cpp index cab2e820802..95a20eeaaf3 100644 --- a/src/devices/cpu/lr35902/lr35902.cpp +++ b/src/devices/cpu/lr35902/lr35902.cpp @@ -41,6 +41,7 @@ #include "emu.h" #include "lr35902.h" +#include "lr35902d.h" #include "debugger.h" /* Flag bit definitions */ @@ -231,14 +232,11 @@ void lr35902_cpu_device::device_reset() m_entering_halt = false; } - -offs_t lr35902_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *lr35902_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( lr35902 ); - return CPU_DISASSEMBLE_NAME(lr35902)(this, stream, pc, oprom, opram, options); + return new lr35902_disassembler; } - void lr35902_cpu_device::check_interrupts() { uint8_t irq = m_IE & m_IF; diff --git a/src/devices/cpu/lr35902/lr35902.h b/src/devices/cpu/lr35902/lr35902.h index 9364599be27..0d33bbbe548 100644 --- a/src/devices/cpu/lr35902/lr35902.h +++ b/src/devices/cpu/lr35902/lr35902.h @@ -89,9 +89,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; inline void cycles_passed(uint8_t cycles); inline uint8_t mem_read_byte(uint16_t addr); diff --git a/src/devices/cpu/lr35902/lr35902d.cpp b/src/devices/cpu/lr35902/lr35902d.cpp index a723cac408d..5b27f37778e 100644 --- a/src/devices/cpu/lr35902/lr35902d.cpp +++ b/src/devices/cpu/lr35902/lr35902d.cpp @@ -8,21 +8,9 @@ *****************************************************************************/ #include "emu.h" -#include "debugger.h" -#include "lr35902.h" +#include "lr35902d.h" -enum e_mnemonics -{ - zADC, zADD, zAND, zBIT, zCALL, zCCF, zCP, - zCPL, zDAA, zDB, zDEC, zDI, zEI, zHLT, - zIN, zINC, zJP, zJR, zLD, zNOP, zOR, - zPOP, zPUSH, zRES, zRET, zRETI, zRL, zRLA, - zRLC, zRLCA, zRR, zRRA, zRRC, zRRCA, zRST, - zSBC, zSCF, zSET, zSLA, zSLL, zSRA, zSRL, - zSTOP, zSUB, zXOR, zSWAP -}; - -static const char *const s_mnemonic[] = +const char *const lr35902_disassembler::s_mnemonic[] = { "adc", "add", "and", "bit", "call","ccf", "cp", "cpl", "daa", "db", "dec", "di", "ei", "halt", @@ -33,26 +21,17 @@ static const char *const s_mnemonic[] = "stop","sub", "xor", "swap" }; -#define _OVER DASMFLAG_STEP_OVER -#define _OUT DASMFLAG_STEP_OUT - -static const uint32_t s_flags[] = { - 0 ,0 ,0 ,0 ,_OVER,0 ,0 , - 0 ,0 ,0 ,0 ,0 ,0 ,_OVER, - 0 ,0 ,0 ,0 ,0 ,0 ,0 , - 0 ,0 ,0 ,_OUT ,_OUT ,0 ,0 , - 0 ,0 ,0 ,0 ,0 ,0 ,_OVER, - 0 ,0 ,0 ,0 ,0 ,0 ,0 , - _OVER,0 ,0 ,0 -}; - -struct lr35902dasm -{ - uint8_t mnemonic; - const char *arguments; +const uint32_t lr35902_disassembler::s_flags[] = { + 0 ,0 ,0 ,0 ,STEP_OVER,0 ,0 , + 0 ,0 ,0 ,0 ,0 ,0 ,STEP_OVER, + 0 ,0 ,0 ,0 ,0 ,0 ,0 , + 0 ,0 ,0 ,STEP_OUT ,STEP_OUT ,0 ,0 , + 0 ,0 ,0 ,0 ,0 ,0 ,STEP_OVER, + 0 ,0 ,0 ,0 ,0 ,0 ,0 , + STEP_OVER,0 ,0 ,0 }; -static const lr35902dasm mnemonic_cb[256] = { +const lr35902_disassembler::lr35902dasm lr35902_disassembler::mnemonic_cb[256] = { {zRLC,"b"}, {zRLC,"c"}, {zRLC,"d"}, {zRLC,"e"}, {zRLC,"h"}, {zRLC,"l"}, {zRLC,"(hl)"}, {zRLC,"a"}, {zRRC,"b"}, {zRRC,"c"}, {zRRC,"d"}, {zRRC,"e"}, @@ -119,7 +98,7 @@ static const lr35902dasm mnemonic_cb[256] = { {zSET,"7,h"}, {zSET,"7,l"}, {zSET,"7,(hl)"},{zSET,"7,a"} }; -static const lr35902dasm mnemonic_main[256]= { +const lr35902_disassembler::lr35902dasm lr35902_disassembler::mnemonic_main[256]= { {zNOP,nullptr}, {zLD,"bc,N"}, {zLD,"(bc),a"}, {zINC,"bc"}, {zINC,"b"}, {zDEC,"b"}, {zLD,"b,B"}, {zRLCA,nullptr}, {zLD,"(W),sp"}, {zADD,"hl,bc"}, {zLD,"a,(bc)"}, {zDEC,"bc"}, @@ -186,11 +165,16 @@ static const lr35902dasm mnemonic_main[256]= { {zDB,"fc"}, {zDB,"fd"}, {zCP,"B"}, {zRST,"V"} }; +u32 lr35902_disassembler::opcode_alignment() const +{ + return 1; +} + /**************************************************************************** * Disassemble opcode at PC and return number of bytes it takes ****************************************************************************/ -CPU_DISASSEMBLE(lr35902) +offs_t lr35902_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { const lr35902dasm *d; const char /* *symbol,*/ *src; @@ -201,11 +185,11 @@ CPU_DISASSEMBLE(lr35902) //symbol = nullptr; - op = oprom[pos++]; + op = opcodes.r8(pos++); op1 = 0; /* keep GCC happy */ if( op == 0xcb ) { - op = oprom[pos++]; + op = opcodes.r8(pos++); d = &mnemonic_cb[op]; } else { d = &mnemonic_main[op]; @@ -220,12 +204,12 @@ CPU_DISASSEMBLE(lr35902) util::stream_format(stream, "$%02X,$%02X", op, op1); break; case 'A': - ea = opram[pos] + (opram[pos+1] << 8); + ea = params.r16(pos); pos += 2; util::stream_format(stream, "$%04X", ea); break; case 'B': /* Byte op arg */ - ea = opram[pos++]; + ea = params.r8(pos++); util::stream_format(stream, "$%02X", ea); break; case '(': /* Memory byte at (...) */ @@ -235,7 +219,7 @@ CPU_DISASSEMBLE(lr35902) } else if( !strncmp( src, "(hl)", 4) ) { } else if( !strncmp( src, "(sp)", 4) ) { } else if( !strncmp( src, "(F)", 3) ) { - ea = 0xFF00 + opram[pos++]; + ea = 0xFF00 + params.r8(pos++); util::stream_format(stream, "$%02X", ea); src++; } else if( !strncmp( src, "(C)", 3) ) { @@ -244,12 +228,12 @@ CPU_DISASSEMBLE(lr35902) } break; case 'N': /* Immediate 16 bit */ - ea = opram[pos] + (opram[pos+1] << 8); + ea = params.r16(pos); pos += 2; util::stream_format(stream, "$%04X", ea); break; case 'O': /* Offset relative to PC */ - offset = (int8_t) opram[pos++]; + offset = (int8_t) params.r8(pos++); util::stream_format(stream, "$%04X", pc + offset + 2); break; case 'V': /* Restart vector */ @@ -257,7 +241,7 @@ CPU_DISASSEMBLE(lr35902) util::stream_format(stream, "$%02X", ea); break; case 'W': /* Memory address word */ - ea = opram[pos] + (opram[pos+1] << 8); + ea = params.r16(pos); pos += 2; util::stream_format(stream, "$%04X", ea); break; @@ -271,5 +255,5 @@ CPU_DISASSEMBLE(lr35902) util::stream_format(stream, "%s", s_mnemonic[d->mnemonic]); } - return pos | s_flags[d->mnemonic] | DASMFLAG_SUPPORTED; + return pos | s_flags[d->mnemonic] | SUPPORTED; } diff --git a/src/devices/cpu/lr35902/lr35902d.h b/src/devices/cpu/lr35902/lr35902d.h new file mode 100644 index 00000000000..550a8bdaef8 --- /dev/null +++ b/src/devices/cpu/lr35902/lr35902d.h @@ -0,0 +1,48 @@ +// license:BSD-3-Clause +// copyright-holders:Wilbert Pol +/***************************************************************************** + * + * lr35902d.c + * Portable Sharp LR35902 disassembler + * + *****************************************************************************/ + +#ifndef MAME_CPU_LR35902_LR35902DASM_H +#define MAME_CPU_LR35902_LR35902DASM_H + +#pragma once + +class lr35902_disassembler : public util::disasm_interface +{ +public: + lr35902_disassembler() = default; + virtual ~lr35902_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum e_mnemonics + { + zADC, zADD, zAND, zBIT, zCALL, zCCF, zCP, + zCPL, zDAA, zDB, zDEC, zDI, zEI, zHLT, + zIN, zINC, zJP, zJR, zLD, zNOP, zOR, + zPOP, zPUSH, zRES, zRET, zRETI, zRL, zRLA, + zRLC, zRLCA, zRR, zRRA, zRRC, zRRCA, zRST, + zSBC, zSCF, zSET, zSLA, zSLL, zSRA, zSRL, + zSTOP, zSUB, zXOR, zSWAP + }; + + struct lr35902dasm + { + uint8_t mnemonic; + const char *arguments; + }; + + static const char *const s_mnemonic[]; + static const uint32_t s_flags[]; + static const lr35902dasm mnemonic_cb[256]; + static const lr35902dasm mnemonic_main[256]; +}; + +#endif diff --git a/src/devices/cpu/m37710/m37710.cpp b/src/devices/cpu/m37710/m37710.cpp index 1c6b78f1b06..e8a0af3b858 100644 --- a/src/devices/cpu/m37710/m37710.cpp +++ b/src/devices/cpu/m37710/m37710.cpp @@ -939,21 +939,20 @@ void m37710_cpu_device::m37710_set_irq_line(int line, int state) (this->*m_set_line)(line, state); } -/* Disassemble an instruction */ -#include "m7700ds.h" - - -CPU_DISASSEMBLE( m37710 ) +bool m37710_cpu_device::get_m_flag() const { - return m7700_disassemble(stream, (pc&0xffff), pc>>16, oprom, 0, 0); + return FLAG_M; } - -offs_t m37710_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +bool m37710_cpu_device::get_x_flag() const { - return m7700_disassemble(stream, (pc&0xffff), pc>>16, oprom, FLAG_M, FLAG_X); + return FLAG_X; } +util::disasm_interface *m37710_cpu_device::create_disassembler() +{ + return new m7700_disassembler(this); +} void m37710_cpu_device::m37710_restore_state() { diff --git a/src/devices/cpu/m37710/m37710.h b/src/devices/cpu/m37710/m37710.h index 69e2ccffb26..6daaa2d26da 100644 --- a/src/devices/cpu/m37710/m37710.h +++ b/src/devices/cpu/m37710/m37710.h @@ -12,6 +12,9 @@ M37710 CPU Emulator v0.1 */ +#include "m7700ds.h" + + /* ======================================================================== */ /* =============================== DEFINES ================================ */ /* ======================================================================== */ @@ -94,7 +97,7 @@ enum #define M37710_INTERNAL_ROM_REGION "internal" #define M37710_INTERNAL_ROM(_tag) (_tag ":" M37710_INTERNAL_ROM_REGION) -class m37710_cpu_device : public cpu_device +class m37710_cpu_device : public cpu_device, public m7700_disassembler::config { public: DECLARE_READ8_MEMBER( m37710_internal_r ); @@ -124,9 +127,9 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 6; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; + virtual bool get_m_flag() const override; + virtual bool get_x_flag() const override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/m37710/m7700ds.cpp b/src/devices/cpu/m37710/m7700ds.cpp index ed81e320a3c..bf8f791935b 100644 --- a/src/devices/cpu/m37710/m7700ds.cpp +++ b/src/devices/cpu/m37710/m7700ds.cpp @@ -12,76 +12,9 @@ Based on G65C816 CPU Emulator by Karl Stenerud #include "emu.h" #include "m7700ds.h" -#ifdef SEC -#undef SEC -#endif - #define ADDRESS_24BIT(A) ((A)&0xffffff) -namespace { - -class m7700_opcode_struct -{ -public: - bool is_call() const { return m_name == op::JSR; } - bool is_return() const { return (m_name == op::RTS) || (m_name == op::RTI); } - const char *name() const { return s_opnames[unsigned(m_name)]; } - - static const m7700_opcode_struct &get(unsigned char ins) { return s_opcodes[ins]; } - static const m7700_opcode_struct &get_prefix42(unsigned char ins) { return s_opcodes_prefix42[ins]; } - static const m7700_opcode_struct &get_prefix89(unsigned char ins) { return s_opcodes_prefix89[ins]; } - - unsigned char flag; - unsigned char ea; - -protected: - enum class op : unsigned - { - ADC , AND , ASL , BCC , BCS , BEQ , BIT , BMI , BNE , BPL , BRA , - BRK , BRL , BVC , BVS , CLC , CLD , CLI , CLV , CMP , COP , CPX , - CPY , DEA , DEC , DEX , DEY , EOR , INA , INC , INX , INY , JML , - JMP , JSL , JSR , LDA , LDX , LDY , LSR , MVN , MVP , NOP , ORA , - PEA , PEI , PER , PHA , PHT , PHD , PHK , PHP , PHX , PHY , PLA , - PLB , PLD , PLP , PLX , PLY , CLP , ROL , ROR , RTI , RTL , RTS , - SBC , SEC , SED , SEI , SEP , STA , STP , STX , STY , STZ , TAX , - TAY , TCS , TCD , TDC , TRB , TSB , TSC , TSX , TXA , TXS , TXY , - TYA , TYX , WAI , WDM , XBA , XCE , MPY , DIV , MPYS, DIVS, RLA , - EXTS, EXTZ , LDT , LDM , UNK , SEB , SEM , CLM , STB , LDB , ADCB , - SBCB, EORB , TBX , CMPB, INB , DEB , TXB , TYB , LSRB, ORB , CLB , - BBC, BBS, TBY, ANDB, PUL , PSH , PLAB, XAB , PHB - }; - - m7700_opcode_struct(op n, unsigned char f, unsigned char e) - : flag(f) - , ea(e) - , m_name(n) - { - } - - op m_name; - - static const char *const s_opnames[]; - static const m7700_opcode_struct s_opcodes[256]; - static const m7700_opcode_struct s_opcodes_prefix42[256]; - static const m7700_opcode_struct s_opcodes_prefix89[256]; -}; - -enum -{ - IMP , ACC , RELB, RELW, IMM , A , AI , AL , ALX , AX , AXI , - AY , D , DI , DIY , DLI , DLIY, DX , DXI , DY , S , SIY , - SIG , MVN , MVP , PEA , PEI , PER , LDM4, LDM5, LDM4X, LDM5X, - BBCD, BBCA, ACCB -}; - -enum -{ - I, /* ignore */ - M, /* check m bit */ - X /* check x bit */ -}; - -const char *const m7700_opcode_struct::s_opnames[] = +const char *const m7700_disassembler::s_opnames[] = { "ADC", "AND", "ASL", "BCC", "BCS", "BEQ", "BIT", "BMI", "BNE", "BPL", "BRA", "BRK", "BRL", "BVC", "BVS", "CLC", "CLD", "CLI", "CLV", "CMP", "COP", "CPX", @@ -97,7 +30,7 @@ const char *const m7700_opcode_struct::s_opnames[] = "BBC", "BBS", "TBY", "ANDB","PUL", "PSH", "PLB", "XAB", "PHB", }; -const m7700_opcode_struct m7700_opcode_struct::s_opcodes[256] = +const m7700_disassembler::m7700_opcode_struct m7700_disassembler::s_opcodes[256] = { {op::BRK, I, SIG }, {op::ORA, M, DXI }, {op::UNK, I, SIG }, {op::ORA, M, S }, {op::SEB, M, LDM4 }, {op::ORA, M, D }, {op::ASL, M, D }, {op::ORA, M, DLI }, @@ -180,7 +113,7 @@ const m7700_opcode_struct m7700_opcode_struct::s_opcodes[256] = {op::JSR, I, AXI }, {op::SBC, M, AX }, {op::INC, M, AX }, {op::SBC, M, ALX } }; -const m7700_opcode_struct m7700_opcode_struct::s_opcodes_prefix42[256] = +const m7700_disassembler::m7700_opcode_struct m7700_disassembler::s_opcodes_prefix42[256] = { {op::BRK, I, SIG }, {op::ORB, M, DXI }, {op::COP, I, SIG }, {op::ORB, M, S }, {op::TSB, M, D }, {op::ORB, M, D }, {op::ASL, M, D }, {op::ORB, M, DLI }, @@ -263,7 +196,7 @@ const m7700_opcode_struct m7700_opcode_struct::s_opcodes_prefix42[256] = {op::JSR, I, AXI }, {op::SBCB,M, AX }, {op::INC, M, AX }, {op::SBCB, M, ALX } }; -const m7700_opcode_struct m7700_opcode_struct::s_opcodes_prefix89[256] = +const m7700_disassembler::m7700_opcode_struct m7700_disassembler::s_opcodes_prefix89[256] = { {op::BRK, I, SIG }, {op::MPY, M, DXI }, {op::COP, I, SIG }, {op::MPY, M, S }, {op::TSB, M, D }, {op::MPY, M, D }, {op::ASL, M, D }, {op::MPY, M, DLI }, @@ -346,71 +279,54 @@ const m7700_opcode_struct m7700_opcode_struct::s_opcodes_prefix89[256] = {op::JSR, I, AXI }, {op::SBC, M, AX }, {op::INC, M, AX }, {op::SBC, M, ALX } }; -} // anonymous namespace - -static inline unsigned int read_8(const uint8_t *oprom, unsigned int offset) +inline std::string m7700_disassembler::int_8_str(unsigned int val) { - return oprom[offset]; -} - -static inline unsigned int read_16(const uint8_t *oprom, unsigned int offset) -{ - unsigned int val = read_8(oprom, offset); - return val | (read_8(oprom, offset+1)<<8); -} - -static inline unsigned int read_24(const uint8_t *oprom, unsigned int offset) -{ - unsigned int val = read_8(oprom, offset); - val |= (read_8(oprom, offset+1)<<8); - return val | (read_8(oprom, offset+2)<<16); -} - -static inline char* int_8_str(unsigned int val) -{ - static char str[20]; - val &= 0xff; if(val & 0x80) - sprintf(str, "-$%x", (0-val) & 0x7f); + return util::string_format("-$%x", (0-val) & 0xff); else - sprintf(str, "$%x", val & 0x7f); - - return str; + return util::string_format("$%x", val & 0xff); } -static inline char* int_16_str(unsigned int val) +inline std::string m7700_disassembler::int_16_str(unsigned int val) { - static char str[20]; - val &= 0xffff; if(val & 0x8000) - sprintf(str, "-$%x", (0-val) & 0x7fff); + return util::string_format("-$%x", (0-val) & 0xffff); else - sprintf(str, "$%x", val & 0x7fff); + return util::string_format("$%x", val & 0xffff); +} - return str; +m7700_disassembler::m7700_disassembler(config *conf) : m_config(conf) +{ } +u32 m7700_disassembler::opcode_alignment() const +{ + return 1; +} -int m7700_disassemble(std::ostream &stream, unsigned int pc, unsigned int pb, const uint8_t *oprom, int m_flag, int x_flag) +offs_t m7700_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { unsigned int instruction; const m7700_opcode_struct *opcode; int var; signed char varS; int length = 1; - unsigned int address; //unsigned int start; uint32_t flags = 0; - pb <<= 16; + offs_t address = pc; + u32 pb = pc & 0xffff0000; + pc &= 0xffff; address = pc | pb; - //start = address; - instruction = read_8(oprom,0); + instruction = opcodes.r8(address); + + int m_flag = m_config->get_m_flag(); + int x_flag = m_config->get_x_flag(); // check for prefixes switch (instruction) @@ -418,16 +334,14 @@ int m7700_disassemble(std::ostream &stream, unsigned int pc, unsigned int pb, co case 0x42: address++; length++; - oprom++; - instruction = read_8(oprom,0); + instruction = opcodes.r8(address); opcode = &m7700_opcode_struct::get_prefix42(instruction); break; case 0x89: address++; length++; - oprom++; - instruction = read_8(oprom,0); + instruction = opcodes.r8(address); opcode = &m7700_opcode_struct::get_prefix89(instruction); break; @@ -437,9 +351,9 @@ int m7700_disassemble(std::ostream &stream, unsigned int pc, unsigned int pb, co } if (opcode->is_call()) - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; else if (opcode->is_return()) - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; stream << opcode->name(); @@ -454,189 +368,184 @@ int m7700_disassemble(std::ostream &stream, unsigned int pc, unsigned int pb, co util::stream_format(stream, " B"); break; case RELB: - varS = read_8(oprom,1); + varS = opcodes.r8(address + 1); length++; util::stream_format(stream, " %06x (%s)", pb | ((pc + length + varS)&0xffff), int_8_str(varS)); break; case RELW: case PER : - var = read_16(oprom,1); + var = opcodes.r16(address + 1); length += 2; util::stream_format(stream, " %06x (%s)", pb | ((pc + length + var)&0xffff), int_16_str(var)); break; case IMM : if((opcode->flag == M && !m_flag) || (opcode->flag == X && !x_flag)) { - util::stream_format(stream, " #$%04x", read_16(oprom,1)); + util::stream_format(stream, " #$%04x", opcodes.r16(address + 1)); length += 2; } else { - util::stream_format(stream, " #$%02x", read_8(oprom,1)); + util::stream_format(stream, " #$%02x", opcodes.r8(address + 1)); length++; } break; case BBCD: if((opcode->flag == M && !m_flag) || (opcode->flag == X && !x_flag)) { - varS = read_8(oprom,4); + varS = opcodes.r8(address + 4); length += 4; - util::stream_format(stream, " #$%04x, $%02x, %06x (%s)", read_16(oprom,2), read_8(oprom,1), pb | ((pc + length + varS)&0xffff), int_8_str(varS)); + util::stream_format(stream, " #$%04x, $%02x, %06x (%s)", opcodes.r16(address + 2), opcodes.r8(address + 1), pb | ((pc + length + varS)&0xffff), int_8_str(varS)); } else { - varS = read_8(oprom,3); + varS = opcodes.r8(address + 3); length += 3; - util::stream_format(stream, " #$%02x, $%02x, %06x (%s)", read_8(oprom,2), read_8(oprom,1), pb | ((pc + length + varS)&0xffff), int_8_str(varS)); + util::stream_format(stream, " #$%02x, $%02x, %06x (%s)", opcodes.r8(address + 2), opcodes.r8(address + 1), pb | ((pc + length + varS)&0xffff), int_8_str(varS)); } break; case BBCA: if((opcode->flag == M && !m_flag) || (opcode->flag == X && !x_flag)) { length += 5; - varS = read_8(oprom,5); - util::stream_format(stream, " #$%04x, $%04x, %06x (%s)", read_16(oprom,3), read_16(oprom,1), pb | ((pc + length + varS)&0xffff), int_8_str(varS)); + varS = opcodes.r8(address + 5); + util::stream_format(stream, " #$%04x, $%04x, %06x (%s)", opcodes.r16(address + 3), opcodes.r16(address + 1), pb | ((pc + length + varS)&0xffff), int_8_str(varS)); } else { length += 4; - varS = read_8(oprom,4); - util::stream_format(stream, " #$%02x, $%04x, %06x (%s)", read_8(oprom,3), read_16(oprom,1), pb | ((pc + length + varS)&0xffff), int_8_str(varS)); + varS = opcodes.r8(address + 4); + util::stream_format(stream, " #$%02x, $%04x, %06x (%s)", opcodes.r8(address + 3), opcodes.r16(address + 1), pb | ((pc + length + varS)&0xffff), int_8_str(varS)); } break; case LDM4: if((opcode->flag == M && !m_flag) || (opcode->flag == X && !x_flag)) { - util::stream_format(stream, " #$%04x, $%02x", read_16(oprom,2), read_8(oprom,1)); + util::stream_format(stream, " #$%04x, $%02x", opcodes.r16(address + 2), opcodes.r8(address + 1)); length += 3; } else { - util::stream_format(stream, " #$%02x, $%02x", read_8(oprom,2), read_8(oprom,1)); + util::stream_format(stream, " #$%02x, $%02x", opcodes.r8(address + 2), opcodes.r8(address + 1)); length += 2; } break; case LDM5: if((opcode->flag == M && !m_flag) || (opcode->flag == X && !x_flag)) { - util::stream_format(stream, " #$%04x, $%04x", read_16(oprom,3), read_16(oprom,1)); + util::stream_format(stream, " #$%04x, $%04x", opcodes.r16(address + 3), opcodes.r16(address + 1)); length += 4; } else { - util::stream_format(stream, " #$%02x, $%04x", read_8(oprom,3), read_16(oprom,1)); + util::stream_format(stream, " #$%02x, $%04x", opcodes.r8(address + 3), opcodes.r16(address + 1)); length += 3; } break; case LDM4X: if((opcode->flag == M && !m_flag) || (opcode->flag == X && !x_flag)) { - util::stream_format(stream, " #$%04x, $%02x, X", read_16(oprom,2), read_8(oprom,1)); + util::stream_format(stream, " #$%04x, $%02x, X", opcodes.r16(address + 2), opcodes.r8(address + 1)); length += 3; } else { - util::stream_format(stream, " #$%02x, $%02x, X", read_8(oprom,2), read_8(oprom,1)); + util::stream_format(stream, " #$%02x, $%02x, X", opcodes.r8(address + 2), opcodes.r8(address + 1)); length += 2; } break; case LDM5X: if((opcode->flag == M && !m_flag) || (opcode->flag == X && !x_flag)) { - util::stream_format(stream, " #$%04x, $%04x, X", read_16(oprom,3), read_16(oprom,1)); + util::stream_format(stream, " #$%04x, $%04x, X", opcodes.r16(address + 3), opcodes.r16(address + 1)); length += 4; } else { - util::stream_format(stream, " #$%02x, $%04x, X", read_8(oprom,3), read_16(oprom,1)); + util::stream_format(stream, " #$%02x, $%04x, X", opcodes.r8(address + 3), opcodes.r16(address + 1)); length += 3; } break; case A : case PEA : - util::stream_format(stream, " $%04x", read_16(oprom,1)); + util::stream_format(stream, " $%04x", opcodes.r16(address + 1)); length += 2; break; case AI : - util::stream_format(stream, " ($%04x)", read_16(oprom,1)); + util::stream_format(stream, " ($%04x)", opcodes.r16(address + 1)); length += 2; break; case AL : - util::stream_format(stream, " $%06x", read_24(oprom,1)); + util::stream_format(stream, " $%06x", opcodes.r32(address + 1) & 0xffffff); length += 3; break; case ALX : - util::stream_format(stream, " $%06x,X", read_24(oprom,1)); + util::stream_format(stream, " $%06x,X", opcodes.r32(address + 1) & 0xffffff); length += 3; break; case AX : - util::stream_format(stream, " $%04x,X", read_16(oprom,1)); + util::stream_format(stream, " $%04x,X", opcodes.r16(address + 1)); length += 2; break; case AXI : - util::stream_format(stream, " ($%04x,X)", read_16(oprom,1)); + util::stream_format(stream, " ($%04x,X)", opcodes.r16(address + 1)); length += 2; break; case AY : - util::stream_format(stream, " $%04x,Y", read_16(oprom,1)); + util::stream_format(stream, " $%04x,Y", opcodes.r16(address + 1)); length += 2; break; case D : - util::stream_format(stream, " $%02x", read_8(oprom,1)); + util::stream_format(stream, " $%02x", opcodes.r8(address + 1)); length++; break; case DI : case PEI : - util::stream_format(stream, " ($%02x)", read_8(oprom,1)); + util::stream_format(stream, " ($%02x)", opcodes.r8(address + 1)); length++; break; case DIY : - util::stream_format(stream, " ($%02x),Y", read_8(oprom,1)); + util::stream_format(stream, " ($%02x),Y", opcodes.r8(address + 1)); length++; break; case DLI : - util::stream_format(stream, " [$%02x]", read_8(oprom,1)); + util::stream_format(stream, " [$%02x]", opcodes.r8(address + 1)); length++; break; case DLIY: - util::stream_format(stream, " [$%02x],Y", read_8(oprom,1)); + util::stream_format(stream, " [$%02x],Y", opcodes.r8(address + 1)); length++; break; case DX : - util::stream_format(stream, " $%02x,X", read_8(oprom,1)); + util::stream_format(stream, " $%02x,X", opcodes.r8(address + 1)); length++; break; case DXI : - util::stream_format(stream, " ($%02x,X)", read_8(oprom,1)); + util::stream_format(stream, " ($%02x,X)", opcodes.r8(address + 1)); length++; break; case DY : - util::stream_format(stream, " $%02x,Y", read_8(oprom,1)); + util::stream_format(stream, " $%02x,Y", opcodes.r8(address + 1)); length++; break; case S : - util::stream_format(stream, " %s,S", int_8_str(read_8(oprom,1))); + util::stream_format(stream, " %s,S", int_8_str(opcodes.r8(address + 1))); length++; break; case SIY : - util::stream_format(stream, " (%s,S),Y", int_8_str(read_8(oprom,1))); + util::stream_format(stream, " (%s,S),Y", int_8_str(opcodes.r8(address + 1))); length++; break; case SIG : - util::stream_format(stream, " #$%02x", read_8(oprom,1)); + util::stream_format(stream, " #$%02x", opcodes.r8(address + 1)); length++; break; case MVN : case MVP : - util::stream_format(stream, " $%02x, $%02x", read_8(oprom,2), read_8(oprom,1)); + util::stream_format(stream, " $%02x, $%02x", opcodes.r8(address + 2), opcodes.r8(address + 1)); length += 2; break; } - return length | flags | DASMFLAG_SUPPORTED; -} - -CPU_DISASSEMBLE(m37710_generic) -{ - return m7700_disassemble(stream, (pc&0xffff), pc>>16, oprom, 0, 0); + return length | flags | SUPPORTED; } diff --git a/src/devices/cpu/m37710/m7700ds.h b/src/devices/cpu/m37710/m7700ds.h index 061070bf407..6a30eb1af61 100644 --- a/src/devices/cpu/m37710/m7700ds.h +++ b/src/devices/cpu/m37710/m7700ds.h @@ -18,6 +18,86 @@ All rights reserved. */ -int m7700_disassemble(std::ostream &stream, unsigned int pc, unsigned int pb, const uint8_t *oprom, int m_flag, int x_flag); +class m7700_disassembler : public util::disasm_interface +{ +public: + struct config { + virtual ~config() = default; + + virtual bool get_m_flag() const = 0; + virtual bool get_x_flag() const = 0; + }; + + m7700_disassembler(config *conf); + virtual ~m7700_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum class op : unsigned + { + ADC , AND , ASL , BCC , BCS , BEQ , BIT , BMI , BNE , BPL , BRA , + BRK , BRL , BVC , BVS , CLC , CLD , CLI , CLV , CMP , COP , CPX , + CPY , DEA , DEC , DEX , DEY , EOR , INA , INC , INX , INY , JML , + JMP , JSL , JSR , LDA , LDX , LDY , LSR , MVN , MVP , NOP , ORA , + PEA , PEI , PER , PHA , PHT , PHD , PHK , PHP , PHX , PHY , PLA , + PLB , PLD , PLP , PLX , PLY , CLP , ROL , ROR , RTI , RTL , RTS , + SBC , SEC , SED , SEI , SEP , STA , STP , STX , STY , STZ , TAX , + TAY , TCS , TCD , TDC , TRB , TSB , TSC , TSX , TXA , TXS , TXY , + TYA , TYX , WAI , WDM , XBA , XCE , MPY , DIV , MPYS, DIVS, RLA , + EXTS, EXTZ , LDT , LDM , UNK , SEB , SEM , CLM , STB , LDB , ADCB , + SBCB, EORB , TBX , CMPB, INB , DEB , TXB , TYB , LSRB, ORB , CLB , + BBC, BBS, TBY, ANDB, PUL , PSH , PLAB, XAB , PHB + }; + + enum + { + IMP , ACC , RELB, RELW, IMM , A , AI , AL , ALX , AX , AXI , + AY , D , DI , DIY , DLI , DLIY, DX , DXI , DY , S , SIY , + SIG , MVN , MVP , PEA , PEI , PER , LDM4, LDM5, LDM4X, LDM5X, + BBCD, BBCA, ACCB + }; + + enum + { + I, /* ignore */ + M, /* check m bit */ + X /* check x bit */ + }; + + class m7700_opcode_struct + { + public: + bool is_call() const { return m_name == op::JSR; } + bool is_return() const { return (m_name == op::RTS) || (m_name == op::RTI); } + const char *name() const { return s_opnames[unsigned(m_name)]; } + + static const m7700_opcode_struct &get(unsigned char ins) { return s_opcodes[ins]; } + static const m7700_opcode_struct &get_prefix42(unsigned char ins) { return s_opcodes_prefix42[ins]; } + static const m7700_opcode_struct &get_prefix89(unsigned char ins) { return s_opcodes_prefix89[ins]; } + + unsigned char flag; + unsigned char ea; + op m_name; + + m7700_opcode_struct(op n, unsigned char f, unsigned char e) + : flag(f) + , ea(e) + , m_name(n) + { + } + }; + + static const char *const s_opnames[]; + static const m7700_opcode_struct s_opcodes[256]; + static const m7700_opcode_struct s_opcodes_prefix42[256]; + static const m7700_opcode_struct s_opcodes_prefix89[256]; + + config *m_config; + + std::string int_8_str(unsigned int val); + std::string int_16_str(unsigned int val); +}; #endif /* __M7700DS_H__ */ diff --git a/src/devices/cpu/m6502/deco16.cpp b/src/devices/cpu/m6502/deco16.cpp index 163403228d9..e5121676253 100644 --- a/src/devices/cpu/m6502/deco16.cpp +++ b/src/devices/cpu/m6502/deco16.cpp @@ -10,6 +10,7 @@ #include "emu.h" #include "deco16.h" +#include "deco16d.h" #define DECO16_VERBOSE 1 @@ -22,12 +23,11 @@ deco16_device::deco16_device(const machine_config &mconfig, const char *tag, dev { } -offs_t deco16_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *deco16_device::create_disassembler() { - return disassemble_generic(stream, pc, oprom, opram, options, disasm_entries); + return new deco16_disassembler; } - void deco16_device::device_start() { if(direct_disabled) diff --git a/src/devices/cpu/m6502/deco16.h b/src/devices/cpu/m6502/deco16.h index c3f55764553..1c980b2e4c6 100644 --- a/src/devices/cpu/m6502/deco16.h +++ b/src/devices/cpu/m6502/deco16.h @@ -12,14 +12,14 @@ #define MAME_CPU_M6502_DECO16_H #include "m6502.h" +#include "deco16d.h" class deco16_device : public m6502_device { public: deco16_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - static const disasm_entry disasm_entries[0x100]; + virtual util::disasm_interface *create_disassembler() override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; virtual void do_exec_full() override; virtual void do_exec_partial() override; diff --git a/src/devices/cpu/m6502/deco16d.cpp b/src/devices/cpu/m6502/deco16d.cpp new file mode 100644 index 00000000000..1fba8c3ba45 --- /dev/null +++ b/src/devices/cpu/m6502/deco16d.cpp @@ -0,0 +1,16 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + deco16d.cpp + + 6502, reverse-engineered DECO variant, disassembler + +***************************************************************************/ + +#include "deco16d.h" +#include "cpu/m6502/deco16d.hxx" + +deco16_disassembler::deco16_disassembler() : m6502_base_disassembler(disasm_entries) +{ +} diff --git a/src/devices/cpu/m6502/deco16d.h b/src/devices/cpu/m6502/deco16d.h new file mode 100644 index 00000000000..3658da9ea9a --- /dev/null +++ b/src/devices/cpu/m6502/deco16d.h @@ -0,0 +1,28 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + deco16d.h + + 6502, reverse-engineered DECO variant, disassembler + +***************************************************************************/ + +#ifndef MAME_CPU_M6502_DECO16D_H +#define MAME_CPU_M6502_DECO16D_H + +#pragma once + +#include "m6502d.h" + +class deco16_disassembler : public m6502_base_disassembler +{ +public: + deco16_disassembler(); + virtual ~deco16_disassembler() = default; + +private: + static const disasm_entry disasm_entries[0x100]; +}; + +#endif diff --git a/src/devices/cpu/m6502/m4510.cpp b/src/devices/cpu/m6502/m4510.cpp index 852d3e5807a..5848f66970d 100644 --- a/src/devices/cpu/m6502/m4510.cpp +++ b/src/devices/cpu/m6502/m4510.cpp @@ -10,6 +10,7 @@ #include "emu.h" #include "m4510.h" +#include "m4510d.h" DEFINE_DEVICE_TYPE(M4510, m4510_device, "m4510", "M4510") @@ -26,9 +27,9 @@ m4510_device::m4510_device(const machine_config &mconfig, const char *tag, devic sprogram_config.m_page_shift = 13; } -offs_t m4510_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *m4510_device::create_disassembler() { - return disassemble_generic(stream, pc, oprom, opram, options, disasm_entries); + return new m4510_disassembler; } void m4510_device::device_start() diff --git a/src/devices/cpu/m6502/m4510.h b/src/devices/cpu/m6502/m4510.h index b093c8aeb56..a41a0620c93 100644 --- a/src/devices/cpu/m6502/m4510.h +++ b/src/devices/cpu/m6502/m4510.h @@ -19,9 +19,8 @@ class m4510_device : public m65ce02_device { public: m4510_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - static const disasm_entry disasm_entries[0x100]; + virtual util::disasm_interface *create_disassembler() override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; virtual void do_exec_full() override; virtual void do_exec_partial() override; diff --git a/src/devices/cpu/m6502/m4510d.cpp b/src/devices/cpu/m6502/m4510d.cpp new file mode 100644 index 00000000000..6e7f0bcbb67 --- /dev/null +++ b/src/devices/cpu/m6502/m4510d.cpp @@ -0,0 +1,16 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + m4510d.cpp + + 65ce02 with a mmu and a port, disassembler + +***************************************************************************/ + +#include "m4510d.h" +#include "cpu/m6502/m4510d.hxx" + +m4510_disassembler::m4510_disassembler() : m6502_base_disassembler(disasm_entries) +{ +} diff --git a/src/devices/cpu/m6502/m4510d.h b/src/devices/cpu/m6502/m4510d.h new file mode 100644 index 00000000000..1c025cfb8e7 --- /dev/null +++ b/src/devices/cpu/m6502/m4510d.h @@ -0,0 +1,28 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + m4510d.h + + 65ce02 with a mmu and a port, disassembler + +***************************************************************************/ + +#ifndef MAME_CPU_M6502_M4510D_H +#define MAME_CPU_M6502_M4510D_H + +#pragma once + +#include "m6502d.h" + +class m4510_disassembler : public m6502_base_disassembler +{ +public: + m4510_disassembler(); + virtual ~m4510_disassembler() = default; + +private: + static const disasm_entry disasm_entries[0x100]; +}; + +#endif diff --git a/src/devices/cpu/m6502/m6502.cpp b/src/devices/cpu/m6502/m6502.cpp index f498ca87771..9046d766487 100644 --- a/src/devices/cpu/m6502/m6502.cpp +++ b/src/devices/cpu/m6502/m6502.cpp @@ -11,6 +11,7 @@ #include "emu.h" #include "debugger.h" #include "m6502.h" +#include "m6502d.h" DEFINE_DEVICE_TYPE(M6502, m6502_device, "m6502", "M6502") @@ -453,179 +454,6 @@ void m6502_device::state_string_export(const device_state_entry &entry, std::str } } - -uint32_t m6502_device::disasm_min_opcode_bytes() const -{ - return 1; -} - -uint32_t m6502_device::disasm_max_opcode_bytes() const -{ - return 4; -} - -offs_t m6502_device::disassemble_generic(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options, const disasm_entry *table) -{ - const disasm_entry &e = table[oprom[0] | inst_state_base]; - uint32_t flags = e.flags | DASMFLAG_SUPPORTED; - util::stream_format(stream, "%s", e.opcode); - - switch(e.mode) { - case DASM_non: - flags |= 1; - break; - - case DASM_aba: - util::stream_format(stream, " $%02x%02x", opram[2], opram[1]); - flags |= 3; - break; - - case DASM_abx: - util::stream_format(stream, " $%02x%02x, x", opram[2], opram[1]); - flags |= 3; - break; - - case DASM_aby: - util::stream_format(stream, " $%02x%02x, y", opram[2], opram[1]); - flags |= 3; - break; - - case DASM_acc: - util::stream_format(stream, " a"); - flags |= 1; - break; - - case DASM_adr: - util::stream_format(stream, " $%02x%02x", opram[2], opram[1]); - flags |= 3; - break; - - case DASM_bzp: - util::stream_format(stream, "%d $%02x", (oprom[0] >> 4) & 7, opram[1]); - flags |= 2; - break; - - case DASM_iax: - util::stream_format(stream, " ($%02x%02x, x)", opram[2], opram[1]); - flags |= 3; - break; - - case DASM_idx: - util::stream_format(stream, " ($%02x, x)", opram[1]); - flags |= 2; - break; - - case DASM_idy: - util::stream_format(stream, " ($%02x), y", opram[1]); - flags |= 2; - break; - - case DASM_idz: - util::stream_format(stream, " ($%02x), z", opram[1]); - flags |= 2; - break; - - case DASM_imm: - util::stream_format(stream, " #$%02x", opram[1]); - flags |= 2; - break; - - case DASM_imp: - flags |= 1; - break; - - case DASM_ind: - util::stream_format(stream, " ($%02x%02x)", opram[2], opram[1]); - flags |= 3; - break; - - case DASM_isy: - util::stream_format(stream, " ($%02x, s), y", opram[1]); - flags |= 2; - break; - - case DASM_iw2: - util::stream_format(stream, " #$%02x%02x", opram[2], opram[1]); - flags |= 3; - break; - - case DASM_iw3: - util::stream_format(stream, " #$%02x%02x%02x", opram[3], opram[2], opram[1]); - flags |= 4; - break; - - case DASM_rel: - util::stream_format(stream, " $%04x", (pc & 0xf0000) | uint16_t(pc + 2 + int8_t(opram[1]))); - flags |= 2; - break; - - case DASM_rw2: - util::stream_format(stream, " $%04x", (pc & 0xf0000) | uint16_t(pc + 2 + int16_t((opram[2] << 8) | opram[1]))); - flags |= 3; - break; - - case DASM_zpb: - util::stream_format(stream, "%d $%02x, $%04x", (oprom[0] >> 4) & 7, opram[1], (pc & 0xf0000) | uint16_t(pc + 3 + int8_t(opram[2]))); - flags |= 3; - break; - - case DASM_zpg: - util::stream_format(stream, " $%02x", opram[1]); - flags |= 2; - break; - - case DASM_zpi: - util::stream_format(stream, " ($%02x)", opram[1]); - flags |= 2; - break; - - case DASM_zpx: - util::stream_format(stream, " $%02x, x", opram[1]); - flags |= 2; - break; - - case DASM_zpy: - util::stream_format(stream, " $%02x, y", opram[1]); - flags |= 2; - break; - - case DASM_imz: - util::stream_format(stream, " #$%02x, $%02x", opram[1], opram[2]); - flags |= 3; - break; - - case DASM_spg: - util::stream_format(stream, " \\$%02x", opram[1]); - flags |= 2; - break; - - case DASM_biz: - util::stream_format(stream, " %d, $%02x", (opram[0] >> 5) & 7, opram[1]); - flags |= 2; - break; - - case DASM_bzr: - util::stream_format(stream, " %d, $%02x, $%04x", (opram[0] >> 5) & 7, opram[1], (pc & 0xf0000) | uint16_t(pc + 3 + int8_t(opram[2]))); - flags |= 3; - break; - - case DASM_bar: - util::stream_format(stream, " %d, a, $%04x", (opram[0] >> 5) & 7, (pc & 0xf0000) | uint16_t(pc + 3 + int8_t(opram[1]))); - flags |= 2; - break; - - case DASM_bac: - util::stream_format(stream, " %d, a", (opram[0] >> 5) & 7); - flags |= 1; - break; - - default: - fprintf(stderr, "Unhandled dasm mode %d\n", e.mode); - abort(); - } - return flags; -} - void m6502_device::prefetch() { sync = true; @@ -662,12 +490,11 @@ void m6502_device::set_nz(uint8_t v) P |= F_Z; } -offs_t m6502_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *m6502_device::create_disassembler() { - return disassemble_generic(stream, pc, oprom, opram, options, disasm_entries); + return new m6502_disassembler; } - uint8_t m6502_device::memory_interface::read_9(uint16_t adr) { return read(adr); diff --git a/src/devices/cpu/m6502/m6502.h b/src/devices/cpu/m6502/m6502.h index 71bc63a534e..9bbc1bdeee2 100644 --- a/src/devices/cpu/m6502/m6502.h +++ b/src/devices/cpu/m6502/m6502.h @@ -68,49 +68,10 @@ protected: virtual uint8_t read_arg(uint16_t adr) override; }; - struct disasm_entry { - const char *opcode; - int mode; - offs_t flags; - }; - enum { STATE_RESET = 0xff00 }; - enum { - DASM_non, /* no additional arguments */ - DASM_aba, /* absolute */ - DASM_abx, /* absolute + X */ - DASM_aby, /* absolute + Y */ - DASM_acc, /* accumulator */ - DASM_adr, /* absolute address (jmp,jsr) */ - DASM_bzp, /* zero page with bit selection */ - DASM_iax, /* indirect + X (65c02 jmp) */ - DASM_idx, /* zero page pre indexed */ - DASM_idy, /* zero page post indexed */ - DASM_idz, /* zero page post indexed (65ce02) */ - DASM_imm, /* immediate */ - DASM_imp, /* implicit */ - DASM_ind, /* indirect (jmp) */ - DASM_isy, /* zero page pre indexed sp and post indexed Y (65ce02) */ - DASM_iw2, /* immediate word (65ce02) */ - DASM_iw3, /* augment (65ce02) */ - DASM_rel, /* relative */ - DASM_rw2, /* relative word (65cs02, 65ce02) */ - DASM_zpb, /* zero page and branch (65c02 bbr, bbs) */ - DASM_zpg, /* zero page */ - DASM_zpi, /* zero page indirect (65c02) */ - DASM_zpx, /* zero page + X */ - DASM_zpy, /* zero page + Y */ - DASM_imz, /* load immediate byte, store to zero page address (M740) */ - DASM_spg, /* "special page": implied FF00 OR immediate value (M740)*/ - DASM_biz, /* bit, zero page (M740) */ - DASM_bzr, /* bit, zero page, relative offset (M740) */ - DASM_bar, /* bit, accumulator, relative offset (M740) */ - DASM_bac /* bit, accumulator (M740) */ - }; - enum { F_N = 0x80, F_V = 0x40, @@ -145,9 +106,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; address_space_config program_config, sprogram_config; @@ -170,9 +129,6 @@ protected: bool nmi_state, irq_state, apu_irq_state, v_state; bool irq_taken, sync, direct_disabled, inhibit_interrupts; - static const disasm_entry disasm_entries[0x100]; - - offs_t disassemble_generic(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options, const disasm_entry *table); uint8_t read(uint16_t adr) { return mintf->read(adr); } uint8_t read_9(uint16_t adr) { return mintf->read_9(adr); } void write(uint16_t adr, uint8_t val) { mintf->write(adr, val); } diff --git a/src/devices/cpu/m6502/m6502d.cpp b/src/devices/cpu/m6502/m6502d.cpp new file mode 100644 index 00000000000..8b8918e5ccf --- /dev/null +++ b/src/devices/cpu/m6502/m6502d.cpp @@ -0,0 +1,192 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + m6502d.cpp + + Mostek 6502, original NMOS variant, disassembler + +***************************************************************************/ + +#include "m6502d.h" +#include "cpu/m6502/m6502d.hxx" + +m6502_base_disassembler::m6502_base_disassembler(const disasm_entry *_table) : table(_table) +{ +} + +u32 m6502_base_disassembler::get_instruction_bank() const +{ + return 0; +} + +u32 m6502_base_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t m6502_base_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + const disasm_entry &e = table[opcodes.r8(pc) | get_instruction_bank()]; + uint32_t flags = e.flags | SUPPORTED; + util::stream_format(stream, "%s", e.opcode); + + switch(e.mode) { + case DASM_non: + flags |= 1; + break; + + case DASM_aba: + util::stream_format(stream, " $%02x%02x", params.r8(pc+2), params.r8(pc+1)); + flags |= 3; + break; + + case DASM_abx: + util::stream_format(stream, " $%02x%02x, x", params.r8(pc+2), params.r8(pc+1)); + flags |= 3; + break; + + case DASM_aby: + util::stream_format(stream, " $%02x%02x, y", params.r8(pc+2), params.r8(pc+1)); + flags |= 3; + break; + + case DASM_acc: + util::stream_format(stream, " a"); + flags |= 1; + break; + + case DASM_adr: + util::stream_format(stream, " $%02x%02x", params.r8(pc+2), params.r8(pc+1)); + flags |= 3; + break; + + case DASM_bzp: + util::stream_format(stream, "%d $%02x", (opcodes.r8(pc) >> 4) & 7, params.r8(pc+1)); + flags |= 2; + break; + + case DASM_iax: + util::stream_format(stream, " ($%02x%02x, x)", params.r8(pc+2), params.r8(pc+1)); + flags |= 3; + break; + + case DASM_idx: + util::stream_format(stream, " ($%02x, x)", params.r8(pc+1)); + flags |= 2; + break; + + case DASM_idy: + util::stream_format(stream, " ($%02x), y", params.r8(pc+1)); + flags |= 2; + break; + + case DASM_idz: + util::stream_format(stream, " ($%02x), z", params.r8(pc+1)); + flags |= 2; + break; + + case DASM_imm: + util::stream_format(stream, " #$%02x", params.r8(pc+1)); + flags |= 2; + break; + + case DASM_imp: + flags |= 1; + break; + + case DASM_ind: + util::stream_format(stream, " ($%02x%02x)", params.r8(pc+2), params.r8(pc+1)); + flags |= 3; + break; + + case DASM_isy: + util::stream_format(stream, " ($%02x, s), y", params.r8(pc+1)); + flags |= 2; + break; + + case DASM_iw2: + util::stream_format(stream, " #$%02x%02x", params.r8(pc+2), params.r8(pc+1)); + flags |= 3; + break; + + case DASM_iw3: + util::stream_format(stream, " #$%02x%02x%02x", params.r8(pc+3), params.r8(pc+2), params.r8(pc+1)); + flags |= 4; + break; + + case DASM_rel: + util::stream_format(stream, " $%04x", (pc & 0xf0000) | uint16_t(pc + 2 + int8_t(params.r8(pc+1)))); + flags |= 2; + break; + + case DASM_rw2: + util::stream_format(stream, " $%04x", (pc & 0xf0000) | uint16_t(pc + 2 + int16_t((params.r8(pc+2) << 8) | params.r8(pc+1)))); + flags |= 3; + break; + + case DASM_zpb: + util::stream_format(stream, "%d $%02x, $%04x", (opcodes.r8(pc) >> 4) & 7, params.r8(pc+1), (pc & 0xf0000) | uint16_t(pc + 3 + int8_t(params.r8(pc+2)))); + flags |= 3; + break; + + case DASM_zpg: + util::stream_format(stream, " $%02x", params.r8(pc+1)); + flags |= 2; + break; + + case DASM_zpi: + util::stream_format(stream, " ($%02x)", params.r8(pc+1)); + flags |= 2; + break; + + case DASM_zpx: + util::stream_format(stream, " $%02x, x", params.r8(pc+1)); + flags |= 2; + break; + + case DASM_zpy: + util::stream_format(stream, " $%02x, y", params.r8(pc+1)); + flags |= 2; + break; + + case DASM_imz: + util::stream_format(stream, " #$%02x, $%02x", params.r8(pc+1), params.r8(pc+2)); + flags |= 3; + break; + + case DASM_spg: + util::stream_format(stream, " \\$%02x", params.r8(pc+1)); + flags |= 2; + break; + + case DASM_biz: + util::stream_format(stream, " %d, $%02x", (opcodes.r8(pc) >> 5) & 7, params.r8(pc+1)); + flags |= 2; + break; + + case DASM_bzr: + util::stream_format(stream, " %d, $%02x, $%04x", (opcodes.r8(pc) >> 5) & 7, params.r8(pc+1), (pc & 0xf0000) | uint16_t(pc + 3 + int8_t(params.r8(pc+2)))); + flags |= 3; + break; + + case DASM_bar: + util::stream_format(stream, " %d, a, $%04x", (opcodes.r8(pc) >> 5) & 7, (pc & 0xf0000) | uint16_t(pc + 3 + int8_t(params.r8(pc+1)))); + flags |= 2; + break; + + case DASM_bac: + util::stream_format(stream, " %d, a", (opcodes.r8(pc) >> 5) & 7); + flags |= 1; + break; + + default: + fprintf(stderr, "Unhandled dasm mode %d\n", e.mode); + abort(); + } + return flags; +} + +m6502_disassembler::m6502_disassembler() : m6502_base_disassembler(disasm_entries) +{ +} diff --git a/src/devices/cpu/m6502/m6502d.h b/src/devices/cpu/m6502/m6502d.h new file mode 100644 index 00000000000..7b23417f753 --- /dev/null +++ b/src/devices/cpu/m6502/m6502d.h @@ -0,0 +1,81 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + m6502d.h + + Mostek 6502, original NMOS variant, disassembler + +***************************************************************************/ + +#ifndef MAME_CPU_M6502_M6502D_H +#define MAME_CPU_M6502_M6502D_H + +#pragma once + +class m6502_base_disassembler : public util::disasm_interface +{ +public: + struct disasm_entry { + const char *opcode; + int mode; + offs_t flags; + }; + + m6502_base_disassembler(const disasm_entry *table); + virtual ~m6502_base_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +protected: + enum { + DASM_non, /* no additional arguments */ + DASM_aba, /* absolute */ + DASM_abx, /* absolute + X */ + DASM_aby, /* absolute + Y */ + DASM_acc, /* accumulator */ + DASM_adr, /* absolute address (jmp,jsr) */ + DASM_bzp, /* zero page with bit selection */ + DASM_iax, /* indirect + X (65c02 jmp) */ + DASM_idx, /* zero page pre indexed */ + DASM_idy, /* zero page post indexed */ + DASM_idz, /* zero page post indexed (65ce02) */ + DASM_imm, /* immediate */ + DASM_imp, /* implicit */ + DASM_ind, /* indirect (jmp) */ + DASM_isy, /* zero page pre indexed sp and post indexed Y (65ce02) */ + DASM_iw2, /* immediate word (65ce02) */ + DASM_iw3, /* augment (65ce02) */ + DASM_rel, /* relative */ + DASM_rw2, /* relative word (65cs02, 65ce02) */ + DASM_zpb, /* zero page and branch (65c02 bbr, bbs) */ + DASM_zpg, /* zero page */ + DASM_zpi, /* zero page indirect (65c02) */ + DASM_zpx, /* zero page + X */ + DASM_zpy, /* zero page + Y */ + DASM_imz, /* load immediate byte, store to zero page address (M740) */ + DASM_spg, /* "special page": implied FF00 OR immediate value (M740)*/ + DASM_biz, /* bit, zero page (M740) */ + DASM_bzr, /* bit, zero page, relative offset (M740) */ + DASM_bar, /* bit, accumulator, relative offset (M740) */ + DASM_bac /* bit, accumulator (M740) */ + }; + + virtual u32 get_instruction_bank() const; + +private: + const disasm_entry *table; +}; + +class m6502_disassembler : public m6502_base_disassembler +{ +public: + m6502_disassembler(); + virtual ~m6502_disassembler() = default; + +private: + static const disasm_entry disasm_entries[0x100]; +}; + +#endif diff --git a/src/devices/cpu/m6502/m6502make.py b/src/devices/cpu/m6502/m6502make.py index 8bcd85f8e21..b874b7c5ba9 100755 --- a/src/devices/cpu/m6502/m6502make.py +++ b/src/devices/cpu/m6502/m6502make.py @@ -6,7 +6,7 @@ from __future__ import print_function USAGE = """ Usage: -%s device_name {opc.lst|-} disp.lst device.inc +%s prefix {opc.lst|-} disp.lst device.inc deviced.inc """ import sys import logging @@ -59,7 +59,7 @@ def emit(f, text): print(text, file=f) FULL_PROLOG="""\ -void %(device)s::%(opcode)s_full() +void %(device)s_device::%(opcode)s_full() { """ @@ -82,7 +82,7 @@ FULL_NONE="""\ """ PARTIAL_PROLOG="""\ -void %(device)s::%(opcode)s_partial() +void %(device)s_device::%(opcode)s_partial() { switch(inst_substate) { case 0: @@ -158,7 +158,7 @@ def save_opcodes(f, device, opcodes): DO_EXEC_FULL_PROLOG="""\ -void %(device)s::do_exec_full() +void %(device)s_device::do_exec_full() { \tswitch(inst_state) { """ @@ -169,7 +169,7 @@ DO_EXEC_FULL_EPILOG="""\ """ DO_EXEC_PARTIAL_PROLOG="""\ -void %(device)s::do_exec_partial() +void %(device)s_device::do_exec_partial() { \tswitch(inst_state) { """ @@ -180,7 +180,7 @@ DO_EXEC_PARTIAL_EPILOG="""\ """ DISASM_PROLOG="""\ -const %(device)s::disasm_entry %(device)s::disasm_entries[0x%(disasm_count)x] = { +const %(device)s_disassembler::disasm_entry %(device)s_disassembler::disasm_entries[0x%(disasm_count)x] = { """ DISASM_EPILOG="""\ @@ -194,25 +194,31 @@ def save_tables(f, device, states): "disasm_count": total_states-1 } - emit(f, DO_EXEC_FULL_PROLOG % d) for n, state in enumerate(states): if state == ".": continue if n < total_states - 1: - emit(f, "\tcase 0x%02x: %s_full(); break;\n" % (n, state)) + emit(f, "\tcase 0x%02x: %s_full(); break;" % (n, state)) else: - emit(f, "\tcase %s: %s_full(); break;\n" % ("STATE_RESET", state)) + emit(f, "\tcase %s: %s_full(); break;" % ("STATE_RESET", state)) emit(f, DO_EXEC_FULL_EPILOG % d) emit(f, DO_EXEC_PARTIAL_PROLOG % d) for n, state in enumerate(states): if state == ".": continue if n < total_states - 1: - emit(f, "\tcase 0x%02x: %s_partial(); break;\n" % (n, state)) + emit(f, "\tcase 0x%02x: %s_partial(); break;" % (n, state)) else: - emit(f, "\tcase %s: %s_partial(); break;\n" % ("STATE_RESET", state)) + emit(f, "\tcase %s: %s_partial(); break;" % ("STATE_RESET", state)) emit(f, DO_EXEC_PARTIAL_EPILOG % d) +def save_dasm(f, device, states): + total_states = len(states) + + d = { "device": device, + "disasm_count": total_states-1 + } + emit(f, DISASM_PROLOG % d ) for n, state in enumerate(states): if state == ".": continue @@ -222,13 +228,13 @@ def save_tables(f, device, states): mode = tokens[-1] extra = "0" if opc in ["jsr", "bsr"]: - extra = "DASMFLAG_STEP_OVER" + extra = "STEP_OVER" elif opc in ["rts", "rti", "rtn"]: - extra = "DASMFLAG_STEP_OUT" - emit(f, '\t{ "%s", DASM_%s, %s },\n' % (opc, mode, extra)) + extra = "STEP_OUT" + emit(f, '\t{ "%s", DASM_%s, %s },' % (opc, mode, extra)) emit(f, DISASM_EPILOG % d) -def save(fname, device, opcodes, states): +def saves(fname, device, opcodes, states): logging.info("saving: %s", fname) try: f = open(fname, "w") @@ -236,12 +242,24 @@ def save(fname, device, opcodes, states): err = sys.exc_info()[1] logging.error("cannot write file %s [%s]", fname, err) sys.exit(1) - save_opcodes(f,device, opcodes) + save_opcodes(f, device, opcodes) emit(f, "\n") save_tables(f, device, states) f.close() +def saved(fname, device, opcodes, states): + logging.info("saving: %s", fname) + try: + f = open(fname, "w") + except Exception: + err = sys.exc_info()[1] + logging.error("cannot write file %s [%s]", fname, err) + sys.exit(1) + save_dasm(f, device, states) + f.close() + + def main(argv): debug = False logformat=("%(levelname)s:" @@ -255,25 +273,29 @@ def main(argv): logging.basicConfig(level=logging.WARNING, format=logformat) - if len(argv) != 5: + if len(argv) != 6: print(USAGE % argv[0]) return 1 - device_name = argv[1] + mode = argv[1] + device_name = argv[2] opcodes = [] - if argv[2] != "-": - opcodes = load_opcodes(argv[2]) + if argv[3] != "-": + opcodes = load_opcodes(argv[3]) logging.info("found %d opcodes", len(opcodes)) else: logging.info("skipping opcode reading") - states = load_disp(argv[3]) + states = load_disp(argv[4]) logging.info("loaded %s states", len(states)) assert (len(states) & 0xff) == 1 - save(argv[4], device_name, opcodes, states) + if mode == 's': + saves(argv[5], device_name, opcodes, states) + else: + saved(argv[5], device_name, opcodes, states) # ====================================================================== diff --git a/src/devices/cpu/m6502/m6509.cpp b/src/devices/cpu/m6502/m6509.cpp index 729b919fb50..e1af60eac4b 100644 --- a/src/devices/cpu/m6502/m6509.cpp +++ b/src/devices/cpu/m6502/m6509.cpp @@ -10,6 +10,7 @@ #include "emu.h" #include "m6509.h" +#include "m6509d.h" DEFINE_DEVICE_TYPE(M6509, m6509_device, "m6509", "M6509") @@ -54,12 +55,11 @@ void m6509_device::state_export(const device_state_entry &entry) } } -offs_t m6509_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *m6509_device::create_disassembler() { - return disassemble_generic(stream, pc, oprom, opram, options, disasm_entries); + return new m6509_disassembler; } - m6509_device::mi_6509_normal::mi_6509_normal(m6509_device *_base) { base = _base; diff --git a/src/devices/cpu/m6502/m6509.h b/src/devices/cpu/m6502/m6509.h index 0057f900c83..c8fa2ba937e 100644 --- a/src/devices/cpu/m6502/m6509.h +++ b/src/devices/cpu/m6502/m6509.h @@ -17,9 +17,7 @@ class m6509_device : public m6502_device { public: m6509_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - static const disasm_entry disasm_entries[0x100]; - - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void do_exec_full() override; virtual void do_exec_partial() override; diff --git a/src/devices/cpu/m6502/m6509d.cpp b/src/devices/cpu/m6502/m6509d.cpp new file mode 100644 index 00000000000..93ef8d684a0 --- /dev/null +++ b/src/devices/cpu/m6502/m6509d.cpp @@ -0,0 +1,16 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + m6509d.cpp + + 6502 with banking and extended address bus, disassembler + +***************************************************************************/ + +#include "m6509d.h" +#include "cpu/m6502/m6509d.hxx" + +m6509_disassembler::m6509_disassembler() : m6502_base_disassembler(disasm_entries) +{ +} diff --git a/src/devices/cpu/m6502/m6509d.h b/src/devices/cpu/m6502/m6509d.h new file mode 100644 index 00000000000..196b2d66de2 --- /dev/null +++ b/src/devices/cpu/m6502/m6509d.h @@ -0,0 +1,28 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + m6509d.h + + 6502 with banking and extended address bus, disassembler + +***************************************************************************/ + +#ifndef MAME_CPU_M6502_M6509D_H +#define MAME_CPU_M6502_M6509D_H + +#pragma once + +#include "m6502d.h" + +class m6509_disassembler : public m6502_base_disassembler +{ +public: + m6509_disassembler(); + virtual ~m6509_disassembler() = default; + +private: + static const disasm_entry disasm_entries[0x100]; +}; + +#endif diff --git a/src/devices/cpu/m6502/m6510.cpp b/src/devices/cpu/m6502/m6510.cpp index e4b4585eaaa..a8fb427210b 100644 --- a/src/devices/cpu/m6502/m6510.cpp +++ b/src/devices/cpu/m6502/m6510.cpp @@ -10,6 +10,7 @@ #include "emu.h" #include "m6510.h" +#include "m6510d.h" DEFINE_DEVICE_TYPE(M6510, m6510_device, "m6510", "M6510") @@ -33,9 +34,9 @@ void m6510_device::set_pulls(uint8_t _pullup, uint8_t _floating) floating = _floating; } -offs_t m6510_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *m6510_device::create_disassembler() { - return disassemble_generic(stream, pc, oprom, opram, options, disasm_entries); + return new m6510_disassembler; } void m6510_device::device_start() diff --git a/src/devices/cpu/m6502/m6510.h b/src/devices/cpu/m6502/m6510.h index d3819f4899f..84f2cea32c7 100644 --- a/src/devices/cpu/m6502/m6510.h +++ b/src/devices/cpu/m6502/m6510.h @@ -32,9 +32,7 @@ public: write_port.set_callback(wr); } - static const disasm_entry disasm_entries[0x100]; - - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void do_exec_full() override; virtual void do_exec_partial() override; diff --git a/src/devices/cpu/m6502/m6510d.cpp b/src/devices/cpu/m6502/m6510d.cpp new file mode 100644 index 00000000000..79dacde3473 --- /dev/null +++ b/src/devices/cpu/m6502/m6510d.cpp @@ -0,0 +1,16 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + m6510d.cpp + + 6502 with 6 i/o pins, also known as 8500, disassembler + +***************************************************************************/ + +#include "m6510d.h" +#include "cpu/m6502/m6510d.hxx" + +m6510_disassembler::m6510_disassembler() : m6502_base_disassembler(disasm_entries) +{ +} diff --git a/src/devices/cpu/m6502/m6510d.h b/src/devices/cpu/m6502/m6510d.h new file mode 100644 index 00000000000..ddf94f93626 --- /dev/null +++ b/src/devices/cpu/m6502/m6510d.h @@ -0,0 +1,28 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + m6510d.h + + 6502 with 6 i/o pins, also known as 8500, disassembler + +***************************************************************************/ + +#ifndef MAME_CPU_M6502_M6510D_H +#define MAME_CPU_M6502_M6510D_H + +#pragma once + +#include "m6502d.h" + +class m6510_disassembler : public m6502_base_disassembler +{ +public: + m6510_disassembler(); + virtual ~m6510_disassembler() = default; + +private: + static const disasm_entry disasm_entries[0x100]; +}; + +#endif diff --git a/src/devices/cpu/m6502/m65c02.cpp b/src/devices/cpu/m6502/m65c02.cpp index d109cc502bf..bc79ea84231 100644 --- a/src/devices/cpu/m6502/m65c02.cpp +++ b/src/devices/cpu/m6502/m65c02.cpp @@ -11,6 +11,7 @@ #include "emu.h" #include "m65c02.h" +#include "m65c02d.h" DEFINE_DEVICE_TYPE(M65C02, m65c02_device, "m65c02", "M65C02") @@ -24,9 +25,9 @@ m65c02_device::m65c02_device(const machine_config &mconfig, device_type type, co { } -offs_t m65c02_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *m65c02_device::create_disassembler() { - return disassemble_generic(stream, pc, oprom, opram, options, disasm_entries); + return new m65c02_disassembler; } #include "cpu/m6502/m65c02.hxx" diff --git a/src/devices/cpu/m6502/m65c02.h b/src/devices/cpu/m6502/m65c02.h index 828556e5f83..c1898912b03 100644 --- a/src/devices/cpu/m6502/m65c02.h +++ b/src/devices/cpu/m6502/m65c02.h @@ -19,9 +19,7 @@ class m65c02_device : public m6502_device { public: m65c02_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - static const disasm_entry disasm_entries[0x100]; - - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void do_exec_full() override; virtual void do_exec_partial() override; diff --git a/src/devices/cpu/m6502/m65c02d.cpp b/src/devices/cpu/m6502/m65c02d.cpp new file mode 100644 index 00000000000..19be44c2db8 --- /dev/null +++ b/src/devices/cpu/m6502/m65c02d.cpp @@ -0,0 +1,17 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + m65c02d.cpp + + Mostek 6502, CMOS variant with some additional instructions (but + not the bitwise ones), disassembler + +***************************************************************************/ + +#include "m65c02d.h" +#include "cpu/m6502/m65c02d.hxx" + +m65c02_disassembler::m65c02_disassembler() : m6502_base_disassembler(disasm_entries) +{ +} diff --git a/src/devices/cpu/m6502/m65c02d.h b/src/devices/cpu/m6502/m65c02d.h new file mode 100644 index 00000000000..d9599e548bb --- /dev/null +++ b/src/devices/cpu/m6502/m65c02d.h @@ -0,0 +1,29 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + m65c02d.h + + Mostek 6502, CMOS variant with some additional instructions (but + not the bitwise ones), disassembler + +***************************************************************************/ + +#ifndef MAME_CPU_M6502_M65C02D_H +#define MAME_CPU_M6502_M65C02D_H + +#pragma once + +#include "m6502d.h" + +class m65c02_disassembler : public m6502_base_disassembler +{ +public: + m65c02_disassembler(); + virtual ~m65c02_disassembler() = default; + +private: + static const disasm_entry disasm_entries[0x100]; +}; + +#endif diff --git a/src/devices/cpu/m6502/m65ce02.cpp b/src/devices/cpu/m6502/m65ce02.cpp index 239e900ed6d..e416cfa0089 100644 --- a/src/devices/cpu/m6502/m65ce02.cpp +++ b/src/devices/cpu/m6502/m65ce02.cpp @@ -10,6 +10,7 @@ #include "emu.h" #include "m65ce02.h" +#include "m65ce02d.h" DEFINE_DEVICE_TYPE(M65CE02, m65ce02_device, "m65ce02", "M65CE02") @@ -23,9 +24,9 @@ m65ce02_device::m65ce02_device(const machine_config &mconfig, device_type type, { } -offs_t m65ce02_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *m65ce02_device::create_disassembler() { - return disassemble_generic(stream, pc, oprom, opram, options, disasm_entries); + return new m65ce02_disassembler; } void m65ce02_device::init() diff --git a/src/devices/cpu/m6502/m65ce02.h b/src/devices/cpu/m6502/m65ce02.h index 191123683f6..e3c7a440ca8 100644 --- a/src/devices/cpu/m6502/m65ce02.h +++ b/src/devices/cpu/m6502/m65ce02.h @@ -18,9 +18,7 @@ class m65ce02_device : public m65c02_device { public: m65ce02_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - static const disasm_entry disasm_entries[0x100]; - - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void do_exec_full() override; virtual void do_exec_partial() override; diff --git a/src/devices/cpu/m6502/m65ce02d.cpp b/src/devices/cpu/m6502/m65ce02d.cpp new file mode 100644 index 00000000000..5c79ee06e21 --- /dev/null +++ b/src/devices/cpu/m6502/m65ce02d.cpp @@ -0,0 +1,16 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + m65ce02d.cpp + + 6502 with Z register and some more stuff, disassembler + +***************************************************************************/ + +#include "m65ce02d.h" +#include "cpu/m6502/m65ce02d.hxx" + +m65ce02_disassembler::m65ce02_disassembler() : m6502_base_disassembler(disasm_entries) +{ +} diff --git a/src/devices/cpu/m6502/m65ce02d.h b/src/devices/cpu/m6502/m65ce02d.h new file mode 100644 index 00000000000..ea5cd8f072f --- /dev/null +++ b/src/devices/cpu/m6502/m65ce02d.h @@ -0,0 +1,28 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + m65ce02d.h + + 6502 with Z register and some more stuff, disassembler + +***************************************************************************/ + +#ifndef MAME_CPU_M6502_M65CE02D_H +#define MAME_CPU_M6502_M65CE02D_H + +#pragma once + +#include "m6502d.h" + +class m65ce02_disassembler : public m6502_base_disassembler +{ +public: + m65ce02_disassembler(); + virtual ~m65ce02_disassembler() = default; + +private: + static const disasm_entry disasm_entries[0x100]; +}; + +#endif diff --git a/src/devices/cpu/m6502/m740.cpp b/src/devices/cpu/m6502/m740.cpp index 807eac55b09..cce9289b1de 100644 --- a/src/devices/cpu/m6502/m740.cpp +++ b/src/devices/cpu/m6502/m740.cpp @@ -23,9 +23,14 @@ m740_device::m740_device(const machine_config &mconfig, device_type type, const { } -offs_t m740_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +u32 m740_device::get_state_base() const { - return disassemble_generic(stream, pc, oprom, opram, options, disasm_entries); + return inst_state_base; +} + +util::disasm_interface *m740_device::create_disassembler() +{ + return new m740_disassembler(this); } void m740_device::device_start() diff --git a/src/devices/cpu/m6502/m740.h b/src/devices/cpu/m6502/m740.h index 350ea8bced6..be7245e328c 100644 --- a/src/devices/cpu/m6502/m740.h +++ b/src/devices/cpu/m6502/m740.h @@ -12,8 +12,9 @@ #define MAME_CPU_M6502_M740_H #include "m6502.h" +#include "m740d.h" -class m740_device : public m6502_device { +class m740_device : public m6502_device, public m740_disassembler::config { public: enum { @@ -41,11 +42,9 @@ public: virtual void device_start() override; virtual void device_reset() override; - static const disasm_entry disasm_entries[0x200]; - virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void do_exec_full() override; virtual void do_exec_partial() override; virtual void execute_set_input(int inputnum, int state) override; @@ -55,6 +54,9 @@ protected: #define O(o) void o ## _full(); void o ## _partial() + u32 inst_state_base; /* Current instruction bank */ + virtual u32 get_state_base() const override; + uint8_t do_clb(uint8_t in, uint8_t bit); uint8_t do_seb(uint8_t in, uint8_t bit); uint8_t do_rrf(uint8_t in); diff --git a/src/devices/cpu/m6502/m740d.cpp b/src/devices/cpu/m6502/m740d.cpp new file mode 100644 index 00000000000..bed918d4999 --- /dev/null +++ b/src/devices/cpu/m6502/m740d.cpp @@ -0,0 +1,21 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + m740d.cpp + + Mitsubishi M740 series (M507xx/M509xx), disassembler + +***************************************************************************/ + +#include "m740d.h" +#include "cpu/m6502/m740d.hxx" + +m740_disassembler::m740_disassembler(config *_conf) : m6502_base_disassembler(disasm_entries), conf(_conf) +{ +} + +u32 m740_disassembler::get_instruction_bank() const +{ + return conf->get_state_base(); +} diff --git a/src/devices/cpu/m6502/m740d.h b/src/devices/cpu/m6502/m740d.h new file mode 100644 index 00000000000..80029cc56a8 --- /dev/null +++ b/src/devices/cpu/m6502/m740d.h @@ -0,0 +1,37 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + m740d.h + + Mitsubishi M740 series (M507xx/M509xx), disassembler + +***************************************************************************/ + +#ifndef MAME_CPU_M6502_M740D_H +#define MAME_CPU_M6502_M740D_H + +#pragma once + +#include "m6502d.h" + +class m740_disassembler : public m6502_base_disassembler +{ +public: + struct config { + virtual ~config() = default; + virtual u32 get_state_base() const = 0; + }; + + m740_disassembler(config *conf); + virtual ~m740_disassembler() = default; + +protected: + virtual u32 get_instruction_bank() const override; + +private: + static const disasm_entry disasm_entries[0x200]; + config *conf; +}; + +#endif diff --git a/src/devices/cpu/m6502/n2a03.cpp b/src/devices/cpu/m6502/n2a03.cpp index ca3a8a9b87b..f989d8d50f3 100644 --- a/src/devices/cpu/m6502/n2a03.cpp +++ b/src/devices/cpu/m6502/n2a03.cpp @@ -10,6 +10,7 @@ #include "emu.h" #include "n2a03.h" +#include "n2a03d.h" DEFINE_DEVICE_TYPE(N2A03, n2a03_device, "n2a03", "N2A03") @@ -56,9 +57,9 @@ n2a03_device::n2a03_device(const machine_config &mconfig, const char *tag, devic program_config.m_internal_map = ADDRESS_MAP_NAME(n2a03_map); } -offs_t n2a03_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *n2a03_device::create_disassembler() { - return disassemble_generic(stream, pc, oprom, opram, options, disasm_entries); + return new n2a03_disassembler; } void n2a03_device::device_start() diff --git a/src/devices/cpu/m6502/n2a03.h b/src/devices/cpu/m6502/n2a03.h index 0a4cf346797..42e5eac8257 100644 --- a/src/devices/cpu/m6502/n2a03.h +++ b/src/devices/cpu/m6502/n2a03.h @@ -19,9 +19,8 @@ class n2a03_device : public m6502_device { public: n2a03_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - static const disasm_entry disasm_entries[0x100]; + virtual util::disasm_interface *create_disassembler() override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; virtual void do_exec_full() override; virtual void do_exec_partial() override; virtual void device_clock_changed() override; diff --git a/src/devices/cpu/m6502/n2a03d.cpp b/src/devices/cpu/m6502/n2a03d.cpp new file mode 100644 index 00000000000..452e9ef1753 --- /dev/null +++ b/src/devices/cpu/m6502/n2a03d.cpp @@ -0,0 +1,16 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + n2a03d.cpp + + 6502, NES variant, disassembler + +***************************************************************************/ + +#include "n2a03d.h" +#include "cpu/m6502/n2a03d.hxx" + +n2a03_disassembler::n2a03_disassembler() : m6502_base_disassembler(disasm_entries) +{ +} diff --git a/src/devices/cpu/m6502/n2a03d.h b/src/devices/cpu/m6502/n2a03d.h new file mode 100644 index 00000000000..568df91c23a --- /dev/null +++ b/src/devices/cpu/m6502/n2a03d.h @@ -0,0 +1,28 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + n2a03d.h + + 6502, NES variant, disassembler + +***************************************************************************/ + +#ifndef MAME_CPU_M6502_N2A03D_H +#define MAME_CPU_M6502_N2A03D_H + +#pragma once + +#include "m6502d.h" + +class n2a03_disassembler : public m6502_base_disassembler +{ +public: + n2a03_disassembler(); + virtual ~n2a03_disassembler() = default; + +private: + static const disasm_entry disasm_entries[0x100]; +}; + +#endif diff --git a/src/devices/cpu/m6502/or65c02.lst b/src/devices/cpu/m6502/or65c02.lst new file mode 100644 index 00000000000..e69de29bb2d diff --git a/src/devices/cpu/m6502/r65c02.cpp b/src/devices/cpu/m6502/r65c02.cpp index 53c5b40b662..ab7bb936876 100644 --- a/src/devices/cpu/m6502/r65c02.cpp +++ b/src/devices/cpu/m6502/r65c02.cpp @@ -10,6 +10,7 @@ #include "emu.h" #include "r65c02.h" +#include "r65c02d.h" DEFINE_DEVICE_TYPE(R65C02, r65c02_device, "r65c02", "R65C02") @@ -23,9 +24,9 @@ r65c02_device::r65c02_device(const machine_config &mconfig, device_type type, co { } -offs_t r65c02_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *r65c02_device::create_disassembler() { - return disassemble_generic(stream, pc, oprom, opram, options, disasm_entries); + return new r65c02_disassembler; } #include "cpu/m6502/r65c02.hxx" diff --git a/src/devices/cpu/m6502/r65c02.h b/src/devices/cpu/m6502/r65c02.h index 41cea972944..d6c88417bd6 100644 --- a/src/devices/cpu/m6502/r65c02.h +++ b/src/devices/cpu/m6502/r65c02.h @@ -17,9 +17,7 @@ class r65c02_device : public m65c02_device { public: r65c02_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - static const disasm_entry disasm_entries[0x100]; - - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void do_exec_full() override; virtual void do_exec_partial() override; diff --git a/src/devices/cpu/m6502/r65c02d.cpp b/src/devices/cpu/m6502/r65c02d.cpp new file mode 100644 index 00000000000..3b93c1b715a --- /dev/null +++ b/src/devices/cpu/m6502/r65c02d.cpp @@ -0,0 +1,16 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + r65c02d.cpp + + Rockwell 65c02, CMOS variant with bitwise instructions, disassembler + +***************************************************************************/ + +#include "r65c02d.h" +#include "cpu/m6502/r65c02d.hxx" + +r65c02_disassembler::r65c02_disassembler() : m6502_base_disassembler(disasm_entries) +{ +} diff --git a/src/devices/cpu/m6502/r65c02d.h b/src/devices/cpu/m6502/r65c02d.h new file mode 100644 index 00000000000..5f5f3a4a58a --- /dev/null +++ b/src/devices/cpu/m6502/r65c02d.h @@ -0,0 +1,28 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + r65c02d.h + + Rockwell 65c02, CMOS variant with bitwise instructions, disassembler + +***************************************************************************/ + +#ifndef MAME_CPU_M6502_R65C02D_H +#define MAME_CPU_M6502_R65C02D_H + +#pragma once + +#include "m6502d.h" + +class r65c02_disassembler : public m6502_base_disassembler +{ +public: + r65c02_disassembler(); + virtual ~r65c02_disassembler() = default; + +private: + static const disasm_entry disasm_entries[0x100]; +}; + +#endif diff --git a/src/devices/cpu/m6800/6800dasm.cpp b/src/devices/cpu/m6800/6800dasm.cpp index 781af28f468..dcd174e0cba 100644 --- a/src/devices/cpu/m6800/6800dasm.cpp +++ b/src/devices/cpu/m6800/6800dasm.cpp @@ -20,43 +20,9 @@ */ #include "emu.h" -#include "debugger.h" -#include "m6800.h" +#include "6800dasm.h" -enum addr_mode { - inh, /* inherent */ - rel, /* relative */ - imb, /* immediate (byte) */ - imw, /* immediate (word) */ - dir, /* direct address */ - imd, /* HD63701YO: immediate, direct address */ - ext, /* extended address */ - idx, /* x + byte offset */ - imx, /* HD63701YO: immediate, x + byte offset */ - sx1 /* HD63701YO: undocumented opcodes: byte from (s+1) */ -}; - -enum op_names { - aba=0, abx, adca, adcb, adda, addb, addd, aim, - anda, andb, asl, asla, aslb, asld, asr, asra, - asrb, bcc, bcs, beq, bge, bgt, bhi, bita, - bitb, ble, bls, blt, bmi, bne, bpl, bra, - brn, bsr, bvc, bvs, cba, clc, cli, clr, - clra, clrb, clv, cmpa, cmpb, cmpx, com, coma, - comb, daa, dec, deca, decb, des, dex, eim, - eora, eorb, ill, inc, inca, incb, ins, inx, - jmp, jsr, lda, ldb, ldd, lds, ldx, lsr, - lsra, lsrb, lsrd, mul, neg, nega, negb, nop, - oim, ora, orb, psha, pshb, pshx, pula, pulb, - pulx, rol, rola, rolb, ror, rora, rorb, rti, - rts, sba, sbca, sbcb, sec, sev, sta, stb, - _std, sei, sts, stx, suba, subb, subd, swi, - wai, tab, tap, tba, tim, tpa, tst, tsta, - tstb, tsx, txs, asx1, asx2, xgdx, addx, adcx, - bitx -}; - -static const char *const op_name_str[] = { +const char *const m680x_disassembler::op_name_str[] = { "aba", "abx", "adca", "adcb", "adda", "addb", "addd", "aim", "anda", "andb", "asl", "asla", "aslb", "asld", "asr", "asra", "asrb", "bcc", "bcs", "beq", "bge", "bgt", "bhi", "bita", @@ -84,7 +50,7 @@ static const char *const op_name_str[] = { * 2 invalid opcode for 1:6800/6802/6808, 2:6801/6803, 4:HD63701 */ -static const uint8_t table[0x104][3] = { +const uint8_t m680x_disassembler::table[0x104][3] = { {ill, inh,7},{nop, inh,0},{ill, inh,7},{ill, inh,7},/* 00 */ {lsrd,inh,1},{asld,inh,1},{tap, inh,0},{tpa, inh,0}, {inx, inh,0},{dex, inh,0},{clv, inh,0},{sev, inh,0}, @@ -160,20 +126,23 @@ static const uint8_t table[0x104][3] = { {stx,imx,0} }; -/* some macros to keep things short */ -#define OP oprom[0] -#define ARG1 opram[1] -#define ARG2 opram[2] -#define ARGW (opram[1]<<8) + opram[2] +m680x_disassembler::m680x_disassembler(int subtype) : m_subtype(subtype) +{ +} + +u32 m680x_disassembler::opcode_alignment() const +{ + return 1; +} -static unsigned Dasm680x (int subtype, std::ostream &stream, unsigned pc, const uint8_t *oprom, const uint8_t *opram) +offs_t m680x_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - uint32_t flags = 0; + offs_t flags = 0; int invalid_mask; - int code = OP; + int code = opcodes.r8(pc); uint8_t opcode, args, invalid; - switch( subtype ) + switch( m_subtype ) { case 6800: case 6802: case 6808: case 8105: invalid_mask = 1; @@ -186,14 +155,14 @@ static unsigned Dasm680x (int subtype, std::ostream &stream, unsigned pc, const } /* NSC-8105 is a special case */ - if (subtype == 8105) + if (m_subtype == 8105) { /* swap bits */ code = (code & 0x3c) | ((code & 0x41) << 1) | ((code & 0x82) >> 1); /* and check for extra instruction */ - if (code == 0xfc) code = 0x0100; - if (code == 0xec) code = 0x0101; + if (code == 0xfc) code = 0x0100; + if (code == 0xec) code = 0x0101; if (code == 0x7b) code = 0x0102; if (code == 0x71) code = 0x0103; } @@ -203,14 +172,14 @@ static unsigned Dasm680x (int subtype, std::ostream &stream, unsigned pc, const invalid = table[code][2]; if (opcode == bsr || opcode == jsr) - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; else if (opcode == rti || opcode == rts) - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; if ( invalid & invalid_mask ) /* invalid for this cpu type ? */ { stream << "illegal"; - return 1 | flags | DASMFLAG_SUPPORTED; + return 1 | flags | SUPPORTED; } util::stream_format(stream, "%-5s", op_name_str[opcode]); @@ -218,73 +187,33 @@ static unsigned Dasm680x (int subtype, std::ostream &stream, unsigned pc, const switch( args ) { case rel: /* relative */ - util::stream_format(stream, "$%04X", pc + (int8_t)ARG1 + 2); - return 2 | flags | DASMFLAG_SUPPORTED; + util::stream_format(stream, "$%04X", pc + (int8_t)params.r8(pc+1) + 2); + return 2 | flags | SUPPORTED; case imb: /* immediate (byte) */ - util::stream_format(stream, "#$%02X", ARG1); - return 2 | flags | DASMFLAG_SUPPORTED; + util::stream_format(stream, "#$%02X", params.r8(pc+1)); + return 2 | flags | SUPPORTED; case imw: /* immediate (word) */ - util::stream_format(stream, "#$%04X", ARGW); - return 3 | flags | DASMFLAG_SUPPORTED; + util::stream_format(stream, "#$%04X", params.r16(pc+1)); + return 3 | flags | SUPPORTED; case idx: /* indexed + byte offset */ - util::stream_format(stream, "(x+$%02X)", ARG1); - return 2 | flags | DASMFLAG_SUPPORTED; + util::stream_format(stream, "(x+$%02X)", params.r8(pc+1)); + return 2 | flags | SUPPORTED; case imx: /* immediate, indexed + byte offset */ - util::stream_format(stream, "#$%02X,(x+$%02x)", ARG1, ARG2); - return 3 | flags | DASMFLAG_SUPPORTED; + util::stream_format(stream, "#$%02X,(x+$%02x)", params.r8(pc+1), params.r8(pc+2)); + return 3 | flags | SUPPORTED; case dir: /* direct address */ - util::stream_format(stream, "$%02X", ARG1); - return 2 | flags | DASMFLAG_SUPPORTED; + util::stream_format(stream, "$%02X", params.r8(pc+1)); + return 2 | flags | SUPPORTED; case imd: /* immediate, direct address */ - util::stream_format(stream, "#$%02X,$%02X", ARG1, ARG2); - return 3 | flags | DASMFLAG_SUPPORTED; + util::stream_format(stream, "#$%02X,$%02X", params.r8(pc+1), params.r8(pc+2)); + return 3 | flags | SUPPORTED; case ext: /* extended address */ - util::stream_format(stream, "$%04X", ARGW); - return 3 | flags | DASMFLAG_SUPPORTED; + util::stream_format(stream, "$%04X", params.r16(pc+1)); + return 3 | flags | SUPPORTED; case sx1: /* byte from address (s + 1) */ util::stream_format(stream, "(s+1)"); - return 1 | flags | DASMFLAG_SUPPORTED; + return 1 | flags | SUPPORTED; default: - return 1 | flags | DASMFLAG_SUPPORTED; + return 1 | flags | SUPPORTED; } } - -CPU_DISASSEMBLE( m6800 ) -{ - return Dasm680x(6800,stream,pc,oprom,opram); -} - -CPU_DISASSEMBLE( m6801 ) -{ - return Dasm680x(6801,stream,pc,oprom,opram); -} - -CPU_DISASSEMBLE( m6802 ) -{ - return Dasm680x(6802,stream,pc,oprom,opram); -} - -CPU_DISASSEMBLE( m6803 ) -{ - return Dasm680x(6803,stream,pc,oprom,opram); -} - -CPU_DISASSEMBLE( m6808 ) -{ - return Dasm680x(6808,stream,pc,oprom,opram); -} - -CPU_DISASSEMBLE( hd6301 ) -{ - return Dasm680x(6301,stream,pc,oprom,opram); -} - -CPU_DISASSEMBLE( hd63701 ) -{ - return Dasm680x(63701,stream,pc,oprom,opram); -} - -CPU_DISASSEMBLE( nsc8105 ) -{ - return Dasm680x(8105,stream,pc,oprom,opram); -} diff --git a/src/devices/cpu/m6800/6800dasm.h b/src/devices/cpu/m6800/6800dasm.h new file mode 100644 index 00000000000..a535e1299c0 --- /dev/null +++ b/src/devices/cpu/m6800/6800dasm.h @@ -0,0 +1,76 @@ +// license:BSD-3-Clause +// copyright-holders:Aaron Giles +/* + * A quick-hack 6803/6808 disassembler + * + * Note: this is not the good and proper way to disassemble anything, but it works + * + * I'm afraid to put my name on it, but I feel obligated: + * This code written by Aaron Giles (agiles@sirius.com) for the MAME project + * + * History: + * 990314 HJB + * The disassembler knows about valid opcodes for M6800/1/2/3/8 and HD63701. + * 990302 HJB + * Changed the string array into a table of opcode names (or tokens) and + * argument types. This second try should give somewhat better results. + * Named the undocumented HD63701YO opcodes $12 and $13 'asx1' and 'asx2', + * since 'add contents of stack to x register' is what they do. + * + */ + +#ifndef MAME_CPU_M6800_6800DASM_H +#define MAME_CPU_M6800_6800DASM_H + +#pragma once + +class m680x_disassembler : public util::disasm_interface +{ +public: + m680x_disassembler(int subtype); + virtual ~m680x_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum addr_mode { + inh, /* inherent */ + rel, /* relative */ + imb, /* immediate (byte) */ + imw, /* immediate (word) */ + dir, /* direct address */ + imd, /* HD63701YO: immediate, direct address */ + ext, /* extended address */ + idx, /* x + byte offset */ + imx, /* HD63701YO: immediate, x + byte offset */ + sx1 /* HD63701YO: undocumented opcodes: byte from (s+1) */ + }; + + enum op_names { + aba=0, abx, adca, adcb, adda, addb, addd, aim, + anda, andb, asl, asla, aslb, asld, asr, asra, + asrb, bcc, bcs, beq, bge, bgt, bhi, bita, + bitb, ble, bls, blt, bmi, bne, bpl, bra, + brn, bsr, bvc, bvs, cba, clc, cli, clr, + clra, clrb, clv, cmpa, cmpb, cmpx, com, coma, + comb, daa, dec, deca, decb, des, dex, eim, + eora, eorb, ill, inc, inca, incb, ins, inx, + jmp, jsr, lda, ldb, ldd, lds, ldx, lsr, + lsra, lsrb, lsrd, mul, neg, nega, negb, nop, + oim, ora, orb, psha, pshb, pshx, pula, pulb, + pulx, rol, rola, rolb, ror, rora, rorb, rti, + rts, sba, sbca, sbcb, sec, sev, sta, stb, + _std, sei, sts, stx, suba, subb, subd, swi, + wai, tab, tap, tba, tim, tpa, tst, tsta, + tstb, tsx, txs, asx1, asx2, xgdx, addx, adcx, + bitx + }; + + static const char *const op_name_str[]; + static const uint8_t table[0x104][3]; + + int m_subtype; +}; + +#endif diff --git a/src/devices/cpu/m6800/m6800.cpp b/src/devices/cpu/m6800/m6800.cpp index c640a5ce3f2..a8be5ed2f25 100644 --- a/src/devices/cpu/m6800/m6800.cpp +++ b/src/devices/cpu/m6800/m6800.cpp @@ -579,30 +579,22 @@ void m6800_cpu_device::execute_run() } while( m_icount>0 ); } - -offs_t m6800_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *m6800_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( m6800 ); - return CPU_DISASSEMBLE_NAME(m6800)(this, stream, pc, oprom, opram, options); + return new m680x_disassembler(6800); } - -offs_t m6802_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *m6802_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( m6802 ); - return CPU_DISASSEMBLE_NAME(m6802)(this, stream, pc, oprom, opram, options); + return new m680x_disassembler(6802); } - -offs_t m6808_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *m6808_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( m6808 ); - return CPU_DISASSEMBLE_NAME(m6808)(this, stream, pc, oprom, opram, options); + return new m680x_disassembler(6808); } - -offs_t nsc8105_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *nsc8105_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( nsc8105 ); - return CPU_DISASSEMBLE_NAME(nsc8105)(this, stream, pc, oprom, opram, options); + return new m680x_disassembler(8105); } diff --git a/src/devices/cpu/m6800/m6800.h b/src/devices/cpu/m6800/m6800.h index d541deba9ac..e5b5135bfb5 100644 --- a/src/devices/cpu/m6800/m6800.h +++ b/src/devices/cpu/m6800/m6800.h @@ -7,6 +7,7 @@ #pragma once +#include "6800dasm.h" enum { @@ -65,9 +66,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; address_space_config m_program_config; address_space_config m_decrypted_opcodes_config; @@ -374,7 +373,7 @@ protected: virtual uint64_t execute_clocks_to_cycles(uint64_t clocks) const override { return (clocks + 4 - 1) / 4; } virtual uint64_t execute_cycles_to_clocks(uint64_t cycles) const override { return (cycles * 4); } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; }; @@ -384,7 +383,7 @@ public: m6808_cpu_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); protected: - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; }; @@ -394,7 +393,7 @@ public: nsc8105_cpu_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); protected: - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; }; diff --git a/src/devices/cpu/m6800/m6801.cpp b/src/devices/cpu/m6800/m6801.cpp index 87e2ce5e47c..3a32726e345 100644 --- a/src/devices/cpu/m6800/m6801.cpp +++ b/src/devices/cpu/m6800/m6801.cpp @@ -1259,32 +1259,24 @@ void m6801_cpu_device::m6801_clock_serial() } } - -offs_t m6801_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *m6801_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( m6801 ); - return CPU_DISASSEMBLE_NAME(m6801)(this, stream, pc, oprom, opram, options); + return new m680x_disassembler(6801); } - -offs_t m6803_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *m6803_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( m6803 ); - return CPU_DISASSEMBLE_NAME(m6803)(this, stream, pc, oprom, opram, options); + return new m680x_disassembler(6803); } - -offs_t hd6301_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *hd6301_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( hd6301 ); - return CPU_DISASSEMBLE_NAME(hd6301)(this, stream, pc, oprom, opram, options); + return new m680x_disassembler(6301); } - -offs_t hd63701_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *hd63701_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( hd63701 ); - return CPU_DISASSEMBLE_NAME(hd63701)(this, stream, pc, oprom, opram, options); + return new m680x_disassembler(63701); } void hd63701_cpu_device::TAKE_TRAP() diff --git a/src/devices/cpu/m6800/m6801.h b/src/devices/cpu/m6800/m6801.h index 3d2098d1f94..f071e3d75c5 100644 --- a/src/devices/cpu/m6800/m6801.h +++ b/src/devices/cpu/m6800/m6801.h @@ -87,7 +87,7 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; address_space_config m_io_config; @@ -158,7 +158,7 @@ public: m6803_cpu_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); protected: - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; }; @@ -170,7 +170,7 @@ public: protected: hd6301_cpu_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock); - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; }; @@ -180,7 +180,7 @@ public: hd63701_cpu_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); protected: - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void TAKE_TRAP() override; }; diff --git a/src/devices/cpu/m68000/m68000.h b/src/devices/cpu/m68000/m68000.h index 776f097967c..628fed61de8 100644 --- a/src/devices/cpu/m68000/m68000.h +++ b/src/devices/cpu/m68000/m68000.h @@ -110,8 +110,6 @@ enum M68K_FPSR, M68K_FPCR }; -unsigned int m68k_disassemble_raw(std::ostream &stream, unsigned int pc, const unsigned char* opdata, const unsigned char* argdata, unsigned int cpu_type); - class m68000_base_device; @@ -129,12 +127,8 @@ public: void clear_all(void); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 10; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; - - - + // device_disasm_interface overrides + virtual util::disasm_interface *create_disassembler() override; // device_execute_interface overrides virtual uint32_t execute_min_cycles() const override { return 4; }; @@ -407,9 +401,7 @@ public: m68000_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 10; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t execute_min_cycles() const override { return 4; }; virtual uint32_t execute_max_cycles() const override { return 158; }; @@ -432,9 +424,7 @@ public: // construction/destruction m68301_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 10; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t execute_min_cycles() const override { return 4; }; virtual uint32_t execute_max_cycles() const override { return 158; }; @@ -454,9 +444,7 @@ public: // construction/destruction m68008_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 10; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t execute_min_cycles() const override { return 4; }; virtual uint32_t execute_max_cycles() const override { return 158; }; @@ -473,9 +461,7 @@ public: // construction/destruction m68008plcc_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 10; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t execute_min_cycles() const override { return 4; }; virtual uint32_t execute_max_cycles() const override { return 158; }; @@ -492,9 +478,7 @@ public: // construction/destruction m68010_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 10; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t execute_min_cycles() const override { return 4; }; virtual uint32_t execute_max_cycles() const override { return 158; }; @@ -511,9 +495,7 @@ public: // construction/destruction m68ec020_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 20; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t execute_min_cycles() const override { return 2; }; virtual uint32_t execute_max_cycles() const override { return 158; }; @@ -530,9 +512,7 @@ public: // construction/destruction m68020_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 20; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t execute_min_cycles() const override { return 2; }; virtual uint32_t execute_max_cycles() const override { return 158; }; @@ -549,9 +529,7 @@ public: // construction/destruction m68020fpu_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 20; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t execute_min_cycles() const override { return 2; }; virtual uint32_t execute_max_cycles() const override { return 158; }; @@ -568,9 +546,7 @@ public: // construction/destruction m68020pmmu_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 20; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t execute_min_cycles() const override { return 2; }; virtual uint32_t execute_max_cycles() const override { return 158; }; @@ -587,9 +563,7 @@ public: // construction/destruction m68020hmmu_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 20; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t execute_min_cycles() const override { return 2; }; virtual uint32_t execute_max_cycles() const override { return 158; }; @@ -608,9 +582,7 @@ public: // construction/destruction m68ec030_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 20; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t execute_min_cycles() const override { return 2; }; virtual uint32_t execute_max_cycles() const override { return 158; }; @@ -627,9 +599,7 @@ public: // construction/destruction m68030_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 20; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t execute_min_cycles() const override { return 2; }; virtual uint32_t execute_max_cycles() const override { return 158; }; @@ -646,9 +616,7 @@ public: // construction/destruction m68ec040_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 20; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t execute_min_cycles() const override { return 2; }; virtual uint32_t execute_max_cycles() const override { return 158; }; @@ -665,9 +633,7 @@ public: // construction/destruction m68lc040_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 20; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t execute_min_cycles() const override { return 2; }; virtual uint32_t execute_max_cycles() const override { return 158; }; @@ -684,9 +650,7 @@ public: // construction/destruction m68040_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 20; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t execute_min_cycles() const override { return 2; }; virtual uint32_t execute_max_cycles() const override { return 158; }; @@ -703,9 +667,7 @@ public: // construction/destruction scc68070_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 10; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t execute_min_cycles() const override { return 4; }; virtual uint32_t execute_max_cycles() const override { return 158; }; @@ -725,9 +687,7 @@ public: // construction/destruction fscpu32_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 20; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t execute_min_cycles() const override { return 2; }; virtual uint32_t execute_max_cycles() const override { return 158; }; @@ -750,9 +710,7 @@ public: // construction/destruction mcf5206e_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; }; - virtual uint32_t disasm_max_opcode_bytes() const override { return 20; }; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual uint32_t execute_min_cycles() const override { return 2; }; virtual uint32_t execute_max_cycles() const override { return 158; }; diff --git a/src/devices/cpu/m68000/m68kcpu.cpp b/src/devices/cpu/m68000/m68kcpu.cpp index 1c0c79ccb37..44e1fd60446 100644 --- a/src/devices/cpu/m68000/m68kcpu.cpp +++ b/src/devices/cpu/m68000/m68kcpu.cpp @@ -31,6 +31,7 @@ static const char copyright_notice[] = #include "m68kfpu.hxx" #include "m68kmmu.h" +#include "m68kdasm.h" extern void m68040_fpu_op0(m68000_base_device *m68k); extern void m68040_fpu_op1(m68000_base_device *m68k); @@ -2134,80 +2135,100 @@ void m68000_base_device::init_cpu_coldfire(void) define_state(); } -CPU_DISASSEMBLE( dasm_m68000 ) +util::disasm_interface *m68000_base_device::create_disassembler() { - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_68000); + return new m68k_disassembler(m68k_disassembler::TYPE_68000); } -CPU_DISASSEMBLE( dasm_m68008 ) +util::disasm_interface *m68000_device::create_disassembler() { - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_68008); + return new m68k_disassembler(m68k_disassembler::TYPE_68000); } -CPU_DISASSEMBLE( dasm_m68010 ) +util::disasm_interface *m68301_device::create_disassembler() { - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_68010); + return new m68k_disassembler(m68k_disassembler::TYPE_68000); } -CPU_DISASSEMBLE( dasm_m68020 ) +util::disasm_interface *m68008_device::create_disassembler() { - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_68020); + return new m68k_disassembler(m68k_disassembler::TYPE_68008); } -CPU_DISASSEMBLE( dasm_m68030 ) +util::disasm_interface *m68008plcc_device::create_disassembler() { - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_68030); + return new m68k_disassembler(m68k_disassembler::TYPE_68008); } -CPU_DISASSEMBLE( dasm_m68ec030 ) +util::disasm_interface *m68010_device::create_disassembler() { - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_68EC030); + return new m68k_disassembler(m68k_disassembler::TYPE_68010); } -CPU_DISASSEMBLE( dasm_m68040 ) +util::disasm_interface *m68ec020_device::create_disassembler() { - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_68040); + return new m68k_disassembler(m68k_disassembler::TYPE_68020); } -CPU_DISASSEMBLE( dasm_m68ec040 ) +util::disasm_interface *m68020_device::create_disassembler() { - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_68EC040); + return new m68k_disassembler(m68k_disassembler::TYPE_68020); } -CPU_DISASSEMBLE( dasm_m68lc040 ) +util::disasm_interface *m68020fpu_device::create_disassembler() { - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_68LC040); + return new m68k_disassembler(m68k_disassembler::TYPE_68020); } -CPU_DISASSEMBLE( dasm_fscpu32 ) +util::disasm_interface *m68020pmmu_device::create_disassembler() { - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_FSCPU32); + return new m68k_disassembler(m68k_disassembler::TYPE_68020); } -CPU_DISASSEMBLE( dasm_coldfire ) +util::disasm_interface *m68020hmmu_device::create_disassembler() { - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_COLDFIRE); + return new m68k_disassembler(m68k_disassembler::TYPE_68020); } -offs_t m68000_base_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_m68000)(this, stream, pc, oprom, opram, options); } -offs_t m68000_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_m68000)(this, stream, pc, oprom, opram, options); } -offs_t m68301_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_m68000)(this, stream, pc, oprom, opram, options); } -offs_t m68008_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_m68008)(this, stream, pc, oprom, opram, options); } -offs_t m68008plcc_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_m68008)(this, stream, pc, oprom, opram, options); } -offs_t m68010_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_m68010)(this, stream, pc, oprom, opram, options); } -offs_t m68ec020_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_m68020)(this, stream, pc, oprom, opram, options); } -offs_t m68020_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_m68020)(this, stream, pc, oprom, opram, options); } -offs_t m68020fpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_m68020)(this, stream, pc, oprom, opram, options); } -offs_t m68020pmmu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_m68020)(this, stream, pc, oprom, opram, options); } -offs_t m68020hmmu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_m68020)(this, stream, pc, oprom, opram, options); } -offs_t m68ec030_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_m68ec030)(this, stream, pc, oprom, opram, options); } -offs_t m68030_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_m68030)(this, stream, pc, oprom, opram, options); } -offs_t m68ec040_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_m68ec040)(this, stream, pc, oprom, opram, options); } -offs_t m68lc040_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_m68lc040)(this, stream, pc, oprom, opram, options); } -offs_t m68040_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_m68040)(this, stream, pc, oprom, opram, options); } -offs_t scc68070_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_m68000)(this, stream, pc, oprom, opram, options); } -offs_t fscpu32_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_fscpu32)(this, stream, pc, oprom, opram, options); } -offs_t mcf5206e_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) { return CPU_DISASSEMBLE_NAME(dasm_coldfire)(this, stream, pc, oprom, opram, options); } +util::disasm_interface *m68ec030_device::create_disassembler() +{ + return new m68k_disassembler(m68k_disassembler::TYPE_68030); +} + +util::disasm_interface *m68030_device::create_disassembler() +{ + return new m68k_disassembler(m68k_disassembler::TYPE_68030); +} + +util::disasm_interface *m68ec040_device::create_disassembler() +{ + return new m68k_disassembler(m68k_disassembler::TYPE_68040); +} + +util::disasm_interface *m68lc040_device::create_disassembler() +{ + return new m68k_disassembler(m68k_disassembler::TYPE_68040); +} + +util::disasm_interface *m68040_device::create_disassembler() +{ + return new m68k_disassembler(m68k_disassembler::TYPE_68040); +} + +util::disasm_interface *scc68070_device::create_disassembler() +{ + return new m68k_disassembler(m68k_disassembler::TYPE_68000); +} + +util::disasm_interface *fscpu32_device::create_disassembler() +{ + return new m68k_disassembler(m68k_disassembler::TYPE_68340); +} + +util::disasm_interface *mcf5206e_device::create_disassembler() +{ + return new m68k_disassembler(m68k_disassembler::TYPE_COLDFIRE); +} /* Service an interrupt request and start exception processing */ diff --git a/src/devices/cpu/m68000/m68kdasm.cpp b/src/devices/cpu/m68000/m68kdasm.cpp index 5bd074f731e..d0a4d9aaade 100644 --- a/src/devices/cpu/m68000/m68kdasm.cpp +++ b/src/devices/cpu/m68000/m68kdasm.cpp @@ -18,640 +18,321 @@ /* ================================ INCLUDES ============================== */ /* ======================================================================== */ -#define m68ki_cpu_core void #include "emu.h" -#include "m68000.h" +#include "m68kdasm.h" -#ifndef DECL_SPEC -#define DECL_SPEC -#endif - -/* ======================================================================== */ -/* ============================ GENERAL DEFINES =========================== */ -/* ======================================================================== */ - -/* unsigned int and int must be at least 32 bits wide */ -#undef uint32_t -#define uint32_t unsigned int - -/* Bit Isolation Functions */ -#define BIT_0(A) ((A) & 0x00000001) -#define BIT_1(A) ((A) & 0x00000002) -#define BIT_2(A) ((A) & 0x00000004) -#define BIT_3(A) ((A) & 0x00000008) -#define BIT_4(A) ((A) & 0x00000010) -#define BIT_5(A) ((A) & 0x00000020) -#define BIT_6(A) ((A) & 0x00000040) -#define BIT_7(A) ((A) & 0x00000080) -#define BIT_8(A) ((A) & 0x00000100) -#define BIT_9(A) ((A) & 0x00000200) -#define BIT_A(A) ((A) & 0x00000400) -#define BIT_B(A) ((A) & 0x00000800) -#define BIT_C(A) ((A) & 0x00001000) -#define BIT_D(A) ((A) & 0x00002000) -#define BIT_E(A) ((A) & 0x00004000) -#define BIT_F(A) ((A) & 0x00008000) -#define BIT_10(A) ((A) & 0x00010000) -#define BIT_11(A) ((A) & 0x00020000) -#define BIT_12(A) ((A) & 0x00040000) -#define BIT_13(A) ((A) & 0x00080000) -#define BIT_14(A) ((A) & 0x00100000) -#define BIT_15(A) ((A) & 0x00200000) -#define BIT_16(A) ((A) & 0x00400000) -#define BIT_17(A) ((A) & 0x00800000) -#define BIT_18(A) ((A) & 0x01000000) -#define BIT_19(A) ((A) & 0x02000000) -#define BIT_1A(A) ((A) & 0x04000000) -#define BIT_1B(A) ((A) & 0x08000000) -#define BIT_1C(A) ((A) & 0x10000000) -#define BIT_1D(A) ((A) & 0x20000000) -#define BIT_1E(A) ((A) & 0x40000000) -#define BIT_1F(A) ((A) & 0x80000000) - -/* These are the CPU types understood by this disassembler */ -#define TYPE_68000 1 -#define TYPE_68008 2 -#define TYPE_68010 4 -#define TYPE_68020 8 -#define TYPE_68030 16 -#define TYPE_68040 32 -#define TYPE_68340 64 // (CPU32) -#define TYPE_COLDFIRE 128 - -#define M68000_ONLY (TYPE_68000 | TYPE_68008) - -#define M68010_ONLY TYPE_68010 -#define M68010_LESS (TYPE_68000 | TYPE_68008 | TYPE_68010) -#define M68010_PLUS (TYPE_68010 | TYPE_68020 | TYPE_68030 | TYPE_68040 | TYPE_68340 | TYPE_COLDFIRE) - -#define M68020_ONLY (TYPE_68020 | TYPE_68340) -#define M68020_LESS (TYPE_68010 | TYPE_68020 | TYPE_68340) -#define M68020_PLUS (TYPE_68020 | TYPE_68030 | TYPE_68040 | TYPE_68340 | TYPE_COLDFIRE) - -#define M68030_ONLY TYPE_68030 -#define M68030_LESS (TYPE_68010 | TYPE_68020 | TYPE_68030 | TYPE_68340 ) -#define M68030_PLUS (TYPE_68030 | TYPE_68040) - -#define M68040_PLUS TYPE_68040 - -#define COLDFIRE TYPE_COLDFIRE - -/* Extension word formats */ -#define EXT_8BIT_DISPLACEMENT(A) ((A)&0xff) -#define EXT_FULL(A) BIT_8(A) -#define EXT_EFFECTIVE_ZERO(A) (((A)&0xe4) == 0xc4 || ((A)&0xe2) == 0xc0) -#define EXT_BASE_REGISTER_PRESENT(A) (!BIT_7(A)) -#define EXT_INDEX_REGISTER_PRESENT(A) (!BIT_6(A)) -#define EXT_INDEX_REGISTER(A) (((A)>>12)&7) -#define EXT_INDEX_PRE_POST(A) (EXT_INDEX_PRESENT(A) && (A)&3) -#define EXT_INDEX_PRE(A) (EXT_INDEX_PRESENT(A) && ((A)&7) < 4 && ((A)&7) != 0) -#define EXT_INDEX_POST(A) (EXT_INDEX_PRESENT(A) && ((A)&7) > 4) -#define EXT_INDEX_SCALE(A) (((A)>>9)&3) -#define EXT_INDEX_LONG(A) BIT_B(A) -#define EXT_INDEX_AR(A) BIT_F(A) -#define EXT_BASE_DISPLACEMENT_PRESENT(A) (((A)&0x30) > 0x10) -#define EXT_BASE_DISPLACEMENT_WORD(A) (((A)&0x30) == 0x20) -#define EXT_BASE_DISPLACEMENT_LONG(A) (((A)&0x30) == 0x30) -#define EXT_OUTER_DISPLACEMENT_PRESENT(A) (((A)&3) > 1 && ((A)&0x47) < 0x44) -#define EXT_OUTER_DISPLACEMENT_WORD(A) (((A)&3) == 2 && ((A)&0x47) < 0x44) -#define EXT_OUTER_DISPLACEMENT_LONG(A) (((A)&3) == 3 && ((A)&0x47) < 0x44) - - -/* Opcode flags */ -#define SET_OPCODE_FLAGS(x) g_opcode_type = x; -#define COMBINE_OPCODE_FLAGS(x) ((x) | g_opcode_type | DASMFLAG_SUPPORTED) - - -/* ======================================================================== */ -/* =============================== PROTOTYPES ============================= */ -/* ======================================================================== */ - -/* Read data at the PC and increment PC */ -uint32_t read_imm_8(void); -uint32_t read_imm_16(void); -uint32_t read_imm_32(void); - -/* Read data at the PC but don't imcrement the PC */ -uint32_t peek_imm_8(void); -uint32_t peek_imm_16(void); -uint32_t peek_imm_32(void); - -/* make signed integers 100% portably */ -static int make_int_8(int value); -static int make_int_16(int value); -static int make_int_32(int value); - -/* make a string of a hex value */ -static char* make_signed_hex_str_8(uint32_t val); -static char* make_signed_hex_str_16(uint32_t val); -static char* make_signed_hex_str_32(uint32_t val); - -/* make string of ea mode */ -static char* get_ea_mode_str(uint32_t instruction, uint32_t size); - -char* get_ea_mode_str_8(uint32_t instruction); -char* get_ea_mode_str_16(uint32_t instruction); -char* get_ea_mode_str_32(uint32_t instruction); - -/* make string of immediate value */ -static char* get_imm_str_s(uint32_t size); -static char* get_imm_str_u(uint32_t size); - -char* get_imm_str_s8(void); -char* get_imm_str_s16(void); -char* get_imm_str_s32(void); - -/* Stuff to build the opcode handler jump table */ -static void build_opcode_table(void); -static int valid_ea(uint32_t opcode, uint32_t mask); -static int DECL_SPEC compare_nof_true_bits(const void *aptr, const void *bptr); - -/* used to build opcode handler jump table */ -struct opcode_struct -{ - void (*opcode_handler)(void); /* handler function */ - uint32_t mask; /* mask on opcode */ - uint32_t match; /* what to match after masking */ - uint32_t ea_mask; /* what ea modes are allowed */ -}; - - - -/* ======================================================================== */ -/* ================================= DATA ================================= */ -/* ======================================================================== */ - -/* Opcode handler jump table */ -static void (*g_instruction_table[0x10000])(void); -/* Flag if disassembler initialized */ -static int g_initialized = 0; - -static char g_dasm_str[100]; /* string to hold disassembly */ -static char g_helper_str[100]; /* string to hold helpful info */ -static uint32_t g_cpu_pc; /* program counter */ -static uint32_t g_cpu_ir; /* instruction register */ -static uint32_t g_cpu_type; -static uint32_t g_opcode_type; -static const unsigned char* g_rawop; -static uint32_t g_rawbasepc; - -/* used by ops like asr, ror, addq, etc */ -static const uint32_t g_3bit_qdata_table[8] = {8, 1, 2, 3, 4, 5, 6, 7}; - -static const uint32_t g_5bit_data_table[32] = -{ - 32, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, - 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31 -}; - -static const char *const g_cc[16] = -{"t", "f", "hi", "ls", "cc", "cs", "ne", "eq", "vc", "vs", "pl", "mi", "ge", "lt", "gt", "le"}; - -static const char *const g_cpcc[64] = -{/* 000 001 010 011 100 101 110 111 */ - "f", "eq", "ogt", "oge", "olt", "ole", "ogl", "or", /* 000 */ - "un", "ueq", "ugt", "uge", "ult", "ule", "ne", "t", /* 001 */ - "sf", "seq", "gt", "ge", "lt", "le", "gl" "gle", /* 010 */ - "ngle", "ngl", "nle", "nlt", "nge", "ngt", "sne", "st", /* 011 */ - "?", "?", "?", "?", "?", "?", "?", "?", /* 100 */ - "?", "?", "?", "?", "?", "?", "?", "?", /* 101 */ - "?", "?", "?", "?", "?", "?", "?", "?", /* 110 */ - "?", "?", "?", "?", "?", "?", "?", "?" /* 111 */ -}; - -static const char *const g_mmuregs[8] = -{ - "tc", "drp", "srp", "crp", "cal", "val", "sccr", "acr" -}; - -static const char *const g_mmucond[16] = -{ - "bs", "bc", "ls", "lc", "ss", "sc", "as", "ac", - "ws", "wc", "is", "ic", "gs", "gc", "cs", "cc" -}; - -/* ======================================================================== */ -/* =========================== UTILITY FUNCTIONS ========================== */ -/* ======================================================================== */ - -#define LIMIT_CPU_TYPES(ALLOWED_CPU_TYPES) \ - if(!(g_cpu_type & ALLOWED_CPU_TYPES)) \ - { \ - if((g_cpu_ir & 0xf000) == 0xf000) \ - d68000_1111(); \ - else d68000_illegal(); \ - return; \ - } - -static uint32_t dasm_read_imm_8(uint32_t advance) -{ - uint32_t result; - result = g_rawop[g_cpu_pc + 1 - g_rawbasepc]; - g_cpu_pc += advance; - return result; -} - -static uint32_t dasm_read_imm_16(uint32_t advance) -{ - uint32_t result; - result = (g_rawop[g_cpu_pc + 0 - g_rawbasepc] << 8) | - g_rawop[g_cpu_pc + 1 - g_rawbasepc]; - g_cpu_pc += advance; - return result; -} - -static uint32_t dasm_read_imm_32(uint32_t advance) -{ - uint32_t result; - result = (g_rawop[g_cpu_pc + 0 - g_rawbasepc] << 24) | - (g_rawop[g_cpu_pc + 1 - g_rawbasepc] << 16) | - (g_rawop[g_cpu_pc + 2 - g_rawbasepc] << 8) | - g_rawop[g_cpu_pc + 3 - g_rawbasepc]; - g_cpu_pc += advance; - return result; -} - -#define read_imm_8() dasm_read_imm_8(2) -#define read_imm_16() dasm_read_imm_16(2) -#define read_imm_32() dasm_read_imm_32(4) - -#define peek_imm_8() dasm_read_imm_8(0) -#define peek_imm_16() dasm_read_imm_16(0) -#define peek_imm_32() dasm_read_imm_32(0) - -/* Fake a split interface */ -#define get_ea_mode_str_8(instruction) get_ea_mode_str(instruction, 0) -#define get_ea_mode_str_16(instruction) get_ea_mode_str(instruction, 1) -#define get_ea_mode_str_32(instruction) get_ea_mode_str(instruction, 2) - -#define get_imm_str_s8() get_imm_str_s(0) -#define get_imm_str_s16() get_imm_str_s(1) -#define get_imm_str_s32() get_imm_str_s(2) - -#define get_imm_str_u8() get_imm_str_u(0) -#define get_imm_str_u16() get_imm_str_u(1) -#define get_imm_str_u32() get_imm_str_u(2) - -static int sext_7bit_int(int value) -{ - return (value & 0x40) ? (value | 0xffffff80) : (value & 0x7f); -} - - -/* 100% portable signed int generators */ -static int make_int_8(int value) -{ - return (value & 0x80) ? value | ~0xff : value & 0xff; -} - -static int make_int_16(int value) -{ - return (value & 0x8000) ? value | ~0xffff : value & 0xffff; -} - -static int make_int_32(int value) -{ - return (value & 0x80000000) ? value | ~0xffffffff : value & 0xffffffff; -} - -/* Get string representation of hex values */ -static char* make_signed_hex_str_8(uint32_t val) +std::string m68k_disassembler::make_signed_hex_str_8(u8 val) { - static char str[20]; - - val &= 0xff; - if(val == 0x80) - sprintf(str, "-$80"); + return "-$80"; else if(val & 0x80) - sprintf(str, "-$%x", (0-val) & 0x7f); + return util::string_format("-$%x", (-val) & 0x7f); else - sprintf(str, "$%x", val & 0x7f); - - return str; + return util::string_format("$%x", val & 0x7f); } -static char* make_signed_hex_str_16(uint32_t val) +std::string m68k_disassembler::make_signed_hex_str_16(u16 val) { - static char str[20]; - - val &= 0xffff; - if(val == 0x8000) - sprintf(str, "-$8000"); + return "-$8000"; else if(val & 0x8000) - sprintf(str, "-$%x", (0-val) & 0x7fff); + return util::string_format("-$%x", (-val) & 0x7fff); else - sprintf(str, "$%x", val & 0x7fff); - - return str; + return util::string_format("$%x", val & 0x7fff); } -static char* make_signed_hex_str_32(uint32_t val) +std::string m68k_disassembler::make_signed_hex_str_32(u32 val) { - static char str[20]; - - val &= 0xffffffff; - if(val == 0x80000000) - sprintf(str, "-$80000000"); + return "-$80000000"; else if(val & 0x80000000) - sprintf(str, "-$%x", (0-val) & 0x7fffffff); + return util::string_format("-$%x", (-val) & 0x7fffffff); else - sprintf(str, "$%x", val & 0x7fffffff); - - return str; + return util::string_format("$%x", val & 0x7fffffff); } - -/* make string of immediate value */ -static char* get_imm_str_s(uint32_t size) +std::string m68k_disassembler::get_imm_str_s(u32 size) { - static char str[15]; - if(size == 0) - sprintf(str, "#%s", make_signed_hex_str_8(read_imm_8())); - else if(size == 1) - sprintf(str, "#%s", make_signed_hex_str_16(read_imm_16())); - else - sprintf(str, "#%s", make_signed_hex_str_32(read_imm_32())); - return str; + switch(size) { + case 0: return util::string_format("#%s", make_signed_hex_str_8(read_imm_8())); + case 1: return util::string_format("#%s", make_signed_hex_str_16(read_imm_16())); + case 2: return util::string_format("#%s", make_signed_hex_str_32(read_imm_32())); + default: abort(); + } } -static char* get_imm_str_u(uint32_t size) +std::string m68k_disassembler::get_imm_str_u(u32 size) { - static char str[15]; - if(size == 0) - sprintf(str, "#$%x", read_imm_8() & 0xff); - else if(size == 1) - sprintf(str, "#$%x", read_imm_16() & 0xffff); - else - sprintf(str, "#$%x", read_imm_32() & 0xffffffff); - return str; -} - -/* Make string of effective address mode */ -static char* get_ea_mode_str(uint32_t instruction, uint32_t size) -{ - static char b1[64]; - static char b2[64]; - static char* mode = b2; - uint32_t extension; - uint32_t base; - uint32_t outer; - char base_reg[4]; - char index_reg[8]; - uint32_t preindex; - uint32_t postindex; - uint32_t comma = 0; - uint32_t temp_value; - char invalid_mode = 0; - - /* Switch buffers so we don't clobber on a double-call to this function */ - mode = mode == b1 ? b2 : b1; + switch(size) { + case 0: return util::string_format("#$%x", read_imm_8()); + case 1: return util::string_format("#$%x", read_imm_16()); + case 2: return util::string_format("#$%x", read_imm_32()); + default: abort(); + } +} +std::string m68k_disassembler::get_ea_mode_str(u16 instruction, u32 size) +{ switch(instruction & 0x3f) { case 0x00: case 0x01: case 0x02: case 0x03: case 0x04: case 0x05: case 0x06: case 0x07: /* data register direct */ - sprintf(mode, "D%d", instruction&7); + return util::string_format("D%d", instruction&7); break; case 0x08: case 0x09: case 0x0a: case 0x0b: case 0x0c: case 0x0d: case 0x0e: case 0x0f: /* address register direct */ - sprintf(mode, "A%d", instruction&7); + return util::string_format("A%d", instruction&7); break; case 0x10: case 0x11: case 0x12: case 0x13: case 0x14: case 0x15: case 0x16: case 0x17: /* address register indirect */ - sprintf(mode, "(A%d)", instruction&7); + return util::string_format("(A%d)", instruction&7); break; case 0x18: case 0x19: case 0x1a: case 0x1b: case 0x1c: case 0x1d: case 0x1e: case 0x1f: /* address register indirect with postincrement */ - sprintf(mode, "(A%d)+", instruction&7); + return util::string_format("(A%d)+", instruction&7); break; case 0x20: case 0x21: case 0x22: case 0x23: case 0x24: case 0x25: case 0x26: case 0x27: /* address register indirect with predecrement */ - sprintf(mode, "-(A%d)", instruction&7); + return util::string_format("-(A%d)", instruction&7); break; case 0x28: case 0x29: case 0x2a: case 0x2b: case 0x2c: case 0x2d: case 0x2e: case 0x2f: /* address register indirect with displacement*/ - sprintf(mode, "(%s,A%d)", make_signed_hex_str_16(read_imm_16()), instruction&7); + return util::string_format("(%s,A%d)", make_signed_hex_str_16(read_imm_16()), instruction&7); break; case 0x30: case 0x31: case 0x32: case 0x33: case 0x34: case 0x35: case 0x36: case 0x37: + { /* address register indirect with index */ - extension = read_imm_16(); + u16 extension = read_imm_16(); - if((g_cpu_type & M68010_LESS) && EXT_INDEX_SCALE(extension)) - { - invalid_mode = 1; + if((m_cpu_type & M68010_LESS) && ext_index_scale(extension)) break; - } - if(EXT_FULL(extension)) + if(ext_full(extension)) { - if(g_cpu_type & M68010_LESS) - { - invalid_mode = 1; + if(m_cpu_type & M68010_LESS) break; - } - if(EXT_EFFECTIVE_ZERO(extension)) - { - strcpy(mode, "0"); - break; - } + if(ext_effective_zero(extension)) + return "0"; - base = EXT_BASE_DISPLACEMENT_PRESENT(extension) ? (EXT_BASE_DISPLACEMENT_LONG(extension) ? read_imm_32() : read_imm_16()) : 0; - outer = EXT_OUTER_DISPLACEMENT_PRESENT(extension) ? (EXT_OUTER_DISPLACEMENT_LONG(extension) ? read_imm_32() : read_imm_16()) : 0; - if(EXT_BASE_REGISTER_PRESENT(extension)) - sprintf(base_reg, "A%d", instruction&7); - else - *base_reg = 0; - if(EXT_INDEX_REGISTER_PRESENT(extension)) - { - sprintf(index_reg, "%c%d.%c", EXT_INDEX_AR(extension) ? 'A' : 'D', EXT_INDEX_REGISTER(extension), EXT_INDEX_LONG(extension) ? 'l' : 'w'); - if(EXT_INDEX_SCALE(extension)) - sprintf(index_reg+strlen(index_reg), "*%d", 1 << EXT_INDEX_SCALE(extension)); - } - else - *index_reg = 0; - preindex = (extension&7) > 0 && (extension&7) < 4; - postindex = (extension&7) > 4; + u32 base = ext_base_displacement_present(extension) ? (ext_base_displacement_long(extension) ? read_imm_32() : read_imm_16()) : 0; + u32 outer = ext_outer_displacement_present(extension) ? (ext_outer_displacement_long(extension) ? read_imm_32() : read_imm_16()) : 0; + std::string base_reg = ext_base_register_present(extension) ? util::string_format("A%d", instruction&7) : ""; + std::string index_reg = ext_index_register_present(extension) ? + util::string_format("%c%d.%c%s", ext_index_ar(extension) ? 'A' : 'D', ext_index_register(extension), ext_index_long(extension) ? 'l' : 'w', + ext_index_scale(extension) ? util::string_format("*%d", 1 << ext_index_scale(extension)) : "") + : ""; + + bool preindex = (extension&7) > 0 && (extension&7) < 4; + bool postindex = (extension&7) > 4; - strcpy(mode, "("); + std::string mode = "("; if(preindex || postindex) - strcat(mode, "["); + mode += '['; + bool comma = false; if(base) { - if (EXT_BASE_DISPLACEMENT_LONG(extension)) - { - strcat(mode, make_signed_hex_str_32(base)); - } + if(ext_base_displacement_long(extension)) + mode += make_signed_hex_str_32(base); else - { - strcat(mode, make_signed_hex_str_16(base)); - } - comma = 1; + mode += make_signed_hex_str_16(base); + comma = true; } - if(*base_reg) + if(!base_reg.empty()) { if(comma) - strcat(mode, ","); - strcat(mode, base_reg); - comma = 1; + mode += ','; + mode += base_reg; + comma = true; } if(postindex) { - strcat(mode, "]"); - comma = 1; + mode += ']'; + comma = true; } - if(*index_reg) + if(!index_reg.empty()) { if(comma) - strcat(mode, ","); - strcat(mode, index_reg); - comma = 1; + mode += ','; + mode += index_reg; + comma = true; } if(preindex) { - strcat(mode, "]"); - comma = 1; + mode += ']'; } if(outer) { if(comma) - strcat(mode, ","); - strcat(mode, make_signed_hex_str_16(outer)); + mode += ','; + mode += make_signed_hex_str_16(outer); } - strcat(mode, ")"); - break; + mode += ')'; + return mode; } - if(EXT_8BIT_DISPLACEMENT(extension) == 0) - sprintf(mode, "(A%d,%c%d.%c", instruction&7, EXT_INDEX_AR(extension) ? 'A' : 'D', EXT_INDEX_REGISTER(extension), EXT_INDEX_LONG(extension) ? 'l' : 'w'); - else - sprintf(mode, "(%s,A%d,%c%d.%c", make_signed_hex_str_8(extension), instruction&7, EXT_INDEX_AR(extension) ? 'A' : 'D', EXT_INDEX_REGISTER(extension), EXT_INDEX_LONG(extension) ? 'l' : 'w'); - if(EXT_INDEX_SCALE(extension)) - sprintf(mode+strlen(mode), "*%d", 1 << EXT_INDEX_SCALE(extension)); - strcat(mode, ")"); - break; + std::string mode = ext_8bit_displacement(extension) ? + util::string_format("(%s,A%d,%c%d.%c", make_signed_hex_str_8(extension), instruction&7, ext_index_ar(extension) ? 'A' : 'D', ext_index_register(extension), ext_index_long(extension) ? 'l' : 'w') : + util::string_format("(A%d,%c%d.%c", instruction&7, ext_index_ar(extension) ? 'A' : 'D', ext_index_register(extension), ext_index_long(extension) ? 'l' : 'w'); + if(ext_index_scale(extension)) + mode += util::string_format("*%d", 1 << ext_index_scale(extension)); + mode += ')'; + return mode; + } case 0x38: /* absolute short address */ - sprintf(mode, "$%x.w", read_imm_16()); + return util::string_format("$%x.w", read_imm_16()); break; case 0x39: /* absolute long address */ - sprintf(mode, "$%x.l", read_imm_32()); + return util::string_format("$%x.l", read_imm_32()); break; case 0x3a: + { /* program counter with displacement */ - temp_value = read_imm_16(); - sprintf(mode, "(%s,PC)", make_signed_hex_str_16(temp_value)); - sprintf(g_helper_str, "; ($%x)", (make_int_16(temp_value) + g_cpu_pc-2) & 0xffffffff); - break; + u16 temp_value = read_imm_16(); + return util::string_format("(%s,PC) ; ($%x)", make_signed_hex_str_16(temp_value), + (make_int_16(temp_value) + m_cpu_pc-2) & 0xffffffff); + } case 0x3b: + { /* program counter with index */ - extension = read_imm_16(); + u16 extension = read_imm_16(); - if((g_cpu_type & M68010_LESS) && EXT_INDEX_SCALE(extension)) - { - invalid_mode = 1; + if((m_cpu_type & M68010_LESS) && ext_index_scale(extension)) break; - } - if(EXT_FULL(extension)) + if(ext_full(extension)) { - if(g_cpu_type & M68010_LESS) - { - invalid_mode = 1; - break; - } - - if(EXT_EFFECTIVE_ZERO(extension)) - { - strcpy(mode, "0"); + if(m_cpu_type & M68010_LESS) break; - } - base = EXT_BASE_DISPLACEMENT_PRESENT(extension) ? (EXT_BASE_DISPLACEMENT_LONG(extension) ? read_imm_32() : read_imm_16()) : 0; - outer = EXT_OUTER_DISPLACEMENT_PRESENT(extension) ? (EXT_OUTER_DISPLACEMENT_LONG(extension) ? read_imm_32() : read_imm_16()) : 0; - if(EXT_BASE_REGISTER_PRESENT(extension)) - strcpy(base_reg, "PC"); - else - *base_reg = 0; - if(EXT_INDEX_REGISTER_PRESENT(extension)) - { - sprintf(index_reg, "%c%d.%c", EXT_INDEX_AR(extension) ? 'A' : 'D', EXT_INDEX_REGISTER(extension), EXT_INDEX_LONG(extension) ? 'l' : 'w'); - if(EXT_INDEX_SCALE(extension)) - sprintf(index_reg+strlen(index_reg), "*%d", 1 << EXT_INDEX_SCALE(extension)); - } - else - *index_reg = 0; - preindex = (extension&7) > 0 && (extension&7) < 4; - postindex = (extension&7) > 4; - strcpy(mode, "("); + if(ext_effective_zero(extension)) + return "0"; + + u32 base = ext_base_displacement_present(extension) ? (ext_base_displacement_long(extension) ? read_imm_32() : read_imm_16()) : 0; + u32 outer = ext_outer_displacement_present(extension) ? (ext_outer_displacement_long(extension) ? read_imm_32() : read_imm_16()) : 0; + std::string base_reg = ext_base_register_present(extension) ? "PC" : ""; + std::string index_reg = + ext_index_register_present(extension) ? + util::string_format("%c%d.%c%s", ext_index_ar(extension) ? 'A' : 'D', ext_index_register(extension), ext_index_long(extension) ? 'l' : 'w', + ext_index_scale(extension) ? + util::string_format("*%d", 1 << ext_index_scale(extension)) : "") : ""; + bool preindex = (extension&7) > 0 && (extension&7) < 4; + bool postindex = (extension&7) > 4; + + bool comma = false; + std::string mode = "("; if(preindex || postindex) - strcat(mode, "["); + mode += '['; if(base) { - strcat(mode, make_signed_hex_str_16(base)); - comma = 1; + mode += make_signed_hex_str_16(base); + comma = true; } - if(*base_reg) + if(!base_reg.empty()) { if(comma) - strcat(mode, ","); - strcat(mode, base_reg); - comma = 1; + mode += ','; + mode += base_reg; + comma = true; } if(postindex) { - strcat(mode, "]"); - comma = 1; + mode += ']'; + comma = true; } - if(*index_reg) + if(!index_reg.empty()) { if(comma) - strcat(mode, ","); - strcat(mode, index_reg); - comma = 1; + mode += ','; + mode += index_reg; + comma = true; } if(preindex) { - strcat(mode, "]"); - comma = 1; + mode += ']'; + comma = true; } if(outer) { if(comma) - strcat(mode, ","); - strcat(mode, make_signed_hex_str_16(outer)); + mode += ','; + mode += make_signed_hex_str_16(outer); } - strcat(mode, ")"); - break; + mode += ')'; + return mode; } - if(EXT_8BIT_DISPLACEMENT(extension) == 0) - sprintf(mode, "(PC,%c%d.%c", EXT_INDEX_AR(extension) ? 'A' : 'D', EXT_INDEX_REGISTER(extension), EXT_INDEX_LONG(extension) ? 'l' : 'w'); - else - sprintf(mode, "(%s,PC,%c%d.%c", make_signed_hex_str_8(extension), EXT_INDEX_AR(extension) ? 'A' : 'D', EXT_INDEX_REGISTER(extension), EXT_INDEX_LONG(extension) ? 'l' : 'w'); - if(EXT_INDEX_SCALE(extension)) - sprintf(mode+strlen(mode), "*%d", 1 << EXT_INDEX_SCALE(extension)); - strcat(mode, ")"); - break; + std::string mode = ext_8bit_displacement(extension) ? + util::string_format("(%s,PC,%c%d.%c", make_signed_hex_str_8(extension), ext_index_ar(extension) ? 'A' : 'D', ext_index_register(extension), ext_index_long(extension) ? 'l' : 'w') : + util::string_format("(PC,%c%d.%c", ext_index_ar(extension) ? 'A' : 'D', ext_index_register(extension), ext_index_long(extension) ? 'l' : 'w'); + + if(ext_index_scale(extension)) + mode += util::string_format("*%d", 1 << ext_index_scale(extension)); + mode += ')'; + return mode; + } case 0x3c: /* Immediate */ - sprintf(mode, "%s", get_imm_str_u(size)); - break; - default: - invalid_mode = 1; + return get_imm_str_u(size); } - if(invalid_mode) - sprintf(mode, "INVALID %x", instruction & 0x3f); - - return mode; + return util::string_format("INVALID %x", instruction & 0x3f); } +/* ======================================================================== */ +/* ================================= DATA ================================= */ +/* ======================================================================== */ + +/* used by ops like asr, ror, addq, etc */ +const u32 m68k_disassembler::m_3bit_qdata_table[8] = {8, 1, 2, 3, 4, 5, 6, 7}; + +const u32 m68k_disassembler::m_5bit_data_table[32] = +{ + 32, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, + 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31 +}; + +const char *const m68k_disassembler::m_cc[16] = +{ + "t", "f", "hi", "ls", "cc", "cs", "ne", "eq", "vc", "vs", "pl", "mi", "ge", "lt", "gt", "le" +}; + +const char *const m68k_disassembler::m_cpcc[64] = +{/* 000 001 010 011 100 101 110 111 */ + "f", "eq", "ogt", "oge", "olt", "ole", "ogl", "or", /* 000 */ + "un", "ueq", "ugt", "uge", "ult", "ule", "ne", "t", /* 001 */ + "sf", "seq", "gt", "ge", "lt", "le", "gl" "gle", /* 010 */ + "ngle", "ngl", "nle", "nlt", "nge", "ngt", "sne", "st", /* 011 */ + "?", "?", "?", "?", "?", "?", "?", "?", /* 100 */ + "?", "?", "?", "?", "?", "?", "?", "?", /* 101 */ + "?", "?", "?", "?", "?", "?", "?", "?", /* 110 */ + "?", "?", "?", "?", "?", "?", "?", "?" /* 111 */ +}; + +const char *const m68k_disassembler::m_mmuregs[8] = +{ + "tc", "drp", "srp", "crp", "cal", "val", "sccr", "acr" +}; + +const char *const m68k_disassembler::m_mmucond[16] = +{ + "bs", "bc", "ls", "lc", "ss", "sc", "as", "ac", + "ws", "wc", "is", "ic", "gs", "gc", "cs", "cc" +}; +std::pair m68k_disassembler::limit_cpu_types(u32 allowed) +{ + if(!(m_cpu_type & allowed)) + { + if((m_cpu_ir & 0xf000) == 0xf000) + return std::make_pair(true, d68000_1111()); + else + return std::make_pair(true, d68000_illegal()); + } + return std::make_pair(false, std::string()); +} /* ======================================================================== */ /* ========================= INSTRUCTION HANDLERS ========================= */ @@ -691,578 +372,534 @@ static char* get_ea_mode_str(uint32_t instruction, uint32_t size) * al : absolute long */ -static void d68000_illegal(void) +std::string m68k_disassembler::d68000_illegal() { - sprintf(g_dasm_str, "dc.w $%04x; ILLEGAL", g_cpu_ir); + return util::string_format("dc.w $%04x; ILLEGAL", m_cpu_ir); } -static void d68000_1010(void) +std::string m68k_disassembler::d68000_1010() { - sprintf(g_dasm_str, "dc.w $%04x; opcode 1010", g_cpu_ir); + return util::string_format("dc.w $%04x; opcode 1010", m_cpu_ir); } -static void d68000_1111(void) +std::string m68k_disassembler::d68000_1111() { - sprintf(g_dasm_str, "dc.w $%04x; opcode 1111", g_cpu_ir); + return util::string_format("dc.w $%04x; opcode 1111", m_cpu_ir); } -static void d68000_abcd_rr(void) +std::string m68k_disassembler::d68000_abcd_rr() { - sprintf(g_dasm_str, "abcd D%d, D%d", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("abcd D%d, D%d", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_abcd_mm(void) +std::string m68k_disassembler::d68000_abcd_mm() { - sprintf(g_dasm_str, "abcd -(A%d), -(A%d)", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("abcd -(A%d), -(A%d)", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_add_er_8(void) +std::string m68k_disassembler::d68000_add_er_8() { - sprintf(g_dasm_str, "add.b %s, D%d", get_ea_mode_str_8(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("add.b %s, D%d", get_ea_mode_str_8(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_add_er_16(void) +std::string m68k_disassembler::d68000_add_er_16() { - sprintf(g_dasm_str, "add.w %s, D%d", get_ea_mode_str_16(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("add.w %s, D%d", get_ea_mode_str_16(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_add_er_32(void) +std::string m68k_disassembler::d68000_add_er_32() { - sprintf(g_dasm_str, "add.l %s, D%d", get_ea_mode_str_32(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("add.l %s, D%d", get_ea_mode_str_32(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_add_re_8(void) +std::string m68k_disassembler::d68000_add_re_8() { - sprintf(g_dasm_str, "add.b D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("add.b D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_add_re_16(void) +std::string m68k_disassembler::d68000_add_re_16() { - sprintf(g_dasm_str, "add.w D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_16(g_cpu_ir)); + return util::string_format("add.w D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_add_re_32(void) +std::string m68k_disassembler::d68000_add_re_32() { - sprintf(g_dasm_str, "add.l D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("add.l D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_adda_16(void) +std::string m68k_disassembler::d68000_adda_16() { - sprintf(g_dasm_str, "adda.w %s, A%d", get_ea_mode_str_16(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("adda.w %s, A%d", get_ea_mode_str_16(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_adda_32(void) +std::string m68k_disassembler::d68000_adda_32() { - sprintf(g_dasm_str, "adda.l %s, A%d", get_ea_mode_str_32(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("adda.l %s, A%d", get_ea_mode_str_32(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_addi_8(void) +std::string m68k_disassembler::d68000_addi_8() { - char* str = get_imm_str_s8(); - sprintf(g_dasm_str, "addi.b %s, %s", str, get_ea_mode_str_8(g_cpu_ir)); + std::string str = get_imm_str_s8(); + return util::string_format("addi.b %s, %s", str, get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_addi_16(void) +std::string m68k_disassembler::d68000_addi_16() { - char* str = get_imm_str_s16(); - sprintf(g_dasm_str, "addi.w %s, %s", str, get_ea_mode_str_16(g_cpu_ir)); + std::string str = get_imm_str_s16(); + return util::string_format("addi.w %s, %s", str, get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_addi_32(void) +std::string m68k_disassembler::d68000_addi_32() { - char* str = get_imm_str_s32(); - sprintf(g_dasm_str, "addi.l %s, %s", str, get_ea_mode_str_32(g_cpu_ir)); + std::string str = get_imm_str_s32(); + return util::string_format("addi.l %s, %s", str, get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_addq_8(void) +std::string m68k_disassembler::d68000_addq_8() { - sprintf(g_dasm_str, "addq.b #%d, %s", g_3bit_qdata_table[(g_cpu_ir>>9)&7], get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("addq.b #%d, %s", m_3bit_qdata_table[(m_cpu_ir>>9)&7], get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_addq_16(void) +std::string m68k_disassembler::d68000_addq_16() { - sprintf(g_dasm_str, "addq.w #%d, %s", g_3bit_qdata_table[(g_cpu_ir>>9)&7], get_ea_mode_str_16(g_cpu_ir)); + return util::string_format("addq.w #%d, %s", m_3bit_qdata_table[(m_cpu_ir>>9)&7], get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_addq_32(void) +std::string m68k_disassembler::d68000_addq_32() { - sprintf(g_dasm_str, "addq.l #%d, %s", g_3bit_qdata_table[(g_cpu_ir>>9)&7], get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("addq.l #%d, %s", m_3bit_qdata_table[(m_cpu_ir>>9)&7], get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_addx_rr_8(void) +std::string m68k_disassembler::d68000_addx_rr_8() { - sprintf(g_dasm_str, "addx.b D%d, D%d", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("addx.b D%d, D%d", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_addx_rr_16(void) +std::string m68k_disassembler::d68000_addx_rr_16() { - sprintf(g_dasm_str, "addx.w D%d, D%d", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("addx.w D%d, D%d", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_addx_rr_32(void) +std::string m68k_disassembler::d68000_addx_rr_32() { - sprintf(g_dasm_str, "addx.l D%d, D%d", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("addx.l D%d, D%d", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_addx_mm_8(void) +std::string m68k_disassembler::d68000_addx_mm_8() { - sprintf(g_dasm_str, "addx.b -(A%d), -(A%d)", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("addx.b -(A%d), -(A%d)", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_addx_mm_16(void) +std::string m68k_disassembler::d68000_addx_mm_16() { - sprintf(g_dasm_str, "addx.w -(A%d), -(A%d)", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("addx.w -(A%d), -(A%d)", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_addx_mm_32(void) +std::string m68k_disassembler::d68000_addx_mm_32() { - sprintf(g_dasm_str, "addx.l -(A%d), -(A%d)", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("addx.l -(A%d), -(A%d)", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_and_er_8(void) +std::string m68k_disassembler::d68000_and_er_8() { - sprintf(g_dasm_str, "and.b %s, D%d", get_ea_mode_str_8(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("and.b %s, D%d", get_ea_mode_str_8(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_and_er_16(void) +std::string m68k_disassembler::d68000_and_er_16() { - sprintf(g_dasm_str, "and.w %s, D%d", get_ea_mode_str_16(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("and.w %s, D%d", get_ea_mode_str_16(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_and_er_32(void) +std::string m68k_disassembler::d68000_and_er_32() { - sprintf(g_dasm_str, "and.l %s, D%d", get_ea_mode_str_32(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("and.l %s, D%d", get_ea_mode_str_32(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_and_re_8(void) +std::string m68k_disassembler::d68000_and_re_8() { - sprintf(g_dasm_str, "and.b D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("and.b D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_and_re_16(void) +std::string m68k_disassembler::d68000_and_re_16() { - sprintf(g_dasm_str, "and.w D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_16(g_cpu_ir)); + return util::string_format("and.w D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_and_re_32(void) +std::string m68k_disassembler::d68000_and_re_32() { - sprintf(g_dasm_str, "and.l D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("and.l D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_andi_8(void) +std::string m68k_disassembler::d68000_andi_8() { - char* str = get_imm_str_u8(); - sprintf(g_dasm_str, "andi.b %s, %s", str, get_ea_mode_str_8(g_cpu_ir)); + std::string str = get_imm_str_u8(); + return util::string_format("andi.b %s, %s", str, get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_andi_16(void) +std::string m68k_disassembler::d68000_andi_16() { - char* str = get_imm_str_u16(); - sprintf(g_dasm_str, "andi.w %s, %s", str, get_ea_mode_str_16(g_cpu_ir)); + std::string str = get_imm_str_u16(); + return util::string_format("andi.w %s, %s", str, get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_andi_32(void) +std::string m68k_disassembler::d68000_andi_32() { - char* str = get_imm_str_u32(); - sprintf(g_dasm_str, "andi.l %s, %s", str, get_ea_mode_str_32(g_cpu_ir)); + std::string str = get_imm_str_u32(); + return util::string_format("andi.l %s, %s", str, get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_andi_to_ccr(void) +std::string m68k_disassembler::d68000_andi_to_ccr() { - sprintf(g_dasm_str, "andi %s, CCR", get_imm_str_u8()); + return util::string_format("andi %s, CCR", get_imm_str_u8()); } -static void d68000_andi_to_sr(void) +std::string m68k_disassembler::d68000_andi_to_sr() { - sprintf(g_dasm_str, "andi %s, SR", get_imm_str_u16()); + return util::string_format("andi %s, SR", get_imm_str_u16()); } -static void d68000_asr_s_8(void) +std::string m68k_disassembler::d68000_asr_s_8() { - sprintf(g_dasm_str, "asr.b #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("asr.b #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_asr_s_16(void) +std::string m68k_disassembler::d68000_asr_s_16() { - sprintf(g_dasm_str, "asr.w #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("asr.w #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_asr_s_32(void) +std::string m68k_disassembler::d68000_asr_s_32() { - sprintf(g_dasm_str, "asr.l #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("asr.l #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_asr_r_8(void) +std::string m68k_disassembler::d68000_asr_r_8() { - sprintf(g_dasm_str, "asr.b D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("asr.b D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_asr_r_16(void) +std::string m68k_disassembler::d68000_asr_r_16() { - sprintf(g_dasm_str, "asr.w D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("asr.w D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_asr_r_32(void) +std::string m68k_disassembler::d68000_asr_r_32() { - sprintf(g_dasm_str, "asr.l D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("asr.l D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_asr_ea(void) +std::string m68k_disassembler::d68000_asr_ea() { - sprintf(g_dasm_str, "asr.w %s", get_ea_mode_str_16(g_cpu_ir)); + return util::string_format("asr.w %s", get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_asl_s_8(void) +std::string m68k_disassembler::d68000_asl_s_8() { - sprintf(g_dasm_str, "asl.b #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("asl.b #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_asl_s_16(void) +std::string m68k_disassembler::d68000_asl_s_16() { - sprintf(g_dasm_str, "asl.w #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("asl.w #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_asl_s_32(void) +std::string m68k_disassembler::d68000_asl_s_32() { - sprintf(g_dasm_str, "asl.l #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("asl.l #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_asl_r_8(void) +std::string m68k_disassembler::d68000_asl_r_8() { - sprintf(g_dasm_str, "asl.b D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("asl.b D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_asl_r_16(void) +std::string m68k_disassembler::d68000_asl_r_16() { - sprintf(g_dasm_str, "asl.w D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("asl.w D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_asl_r_32(void) +std::string m68k_disassembler::d68000_asl_r_32() { - sprintf(g_dasm_str, "asl.l D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("asl.l D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_asl_ea(void) +std::string m68k_disassembler::d68000_asl_ea() { - sprintf(g_dasm_str, "asl.w %s", get_ea_mode_str_16(g_cpu_ir)); + return util::string_format("asl.w %s", get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_bcc_8(void) +std::string m68k_disassembler::d68000_bcc_8() { - uint32_t temp_pc = g_cpu_pc; - sprintf(g_dasm_str, "b%-2s $%x", g_cc[(g_cpu_ir>>8)&0xf], temp_pc + make_int_8(g_cpu_ir)); + u32 temp_pc = m_cpu_pc; + return util::string_format("b%-2s $%x", m_cc[(m_cpu_ir>>8)&0xf], temp_pc + make_int_8(m_cpu_ir)); } -static void d68000_bcc_16(void) +std::string m68k_disassembler::d68000_bcc_16() { - uint32_t temp_pc = g_cpu_pc; - sprintf(g_dasm_str, "b%-2s $%x", g_cc[(g_cpu_ir>>8)&0xf], temp_pc + make_int_16(read_imm_16())); + u32 temp_pc = m_cpu_pc; + return util::string_format("b%-2s $%x", m_cc[(m_cpu_ir>>8)&0xf], temp_pc + make_int_16(read_imm_16())); } -static void d68020_bcc_32(void) +std::string m68k_disassembler::d68020_bcc_32() { - uint32_t temp_pc = g_cpu_pc; - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "b%-2s $%x; (2+)", g_cc[(g_cpu_ir>>8)&0xf], temp_pc + read_imm_32()); + u32 temp_pc = m_cpu_pc; + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("b%-2s $%x; (2+)", m_cc[(m_cpu_ir>>8)&0xf], temp_pc + read_imm_32()); } -static void d68000_bchg_r(void) +std::string m68k_disassembler::d68000_bchg_r() { - sprintf(g_dasm_str, "bchg D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("bchg D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_bchg_s(void) +std::string m68k_disassembler::d68000_bchg_s() { - char* str = get_imm_str_u8(); - sprintf(g_dasm_str, "bchg %s, %s", str, get_ea_mode_str_8(g_cpu_ir)); + std::string str = get_imm_str_u8(); + return util::string_format("bchg %s, %s", str, get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_bclr_r(void) +std::string m68k_disassembler::d68000_bclr_r() { - sprintf(g_dasm_str, "bclr D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("bclr D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_bclr_s(void) +std::string m68k_disassembler::d68000_bclr_s() { - char* str = get_imm_str_u8(); - sprintf(g_dasm_str, "bclr %s, %s", str, get_ea_mode_str_8(g_cpu_ir)); + std::string str = get_imm_str_u8(); + return util::string_format("bclr %s, %s", str, get_ea_mode_str_8(m_cpu_ir)); } -static void d68010_bkpt(void) +std::string m68k_disassembler::d68010_bkpt() { - LIMIT_CPU_TYPES(M68010_PLUS); - sprintf(g_dasm_str, "bkpt #%d; (1+)", g_cpu_ir&7); + auto limit = limit_cpu_types(M68010_PLUS); + if(limit.first) + return limit.second; + return util::string_format("bkpt #%d; (1+)", m_cpu_ir&7); } -static void d68020_bfchg(void) +std::string m68k_disassembler::d68020_bfchg() { - uint32_t extension; - char offset[3]; - char width[3]; + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; - LIMIT_CPU_TYPES(M68020_PLUS); + u16 extension = read_imm_16(); - extension = read_imm_16(); + std::string offset = BIT(extension, 11) ? util::string_format("D%d", (extension>>6)&7) : util::string_format("%d", (extension>>6)&31); - if(BIT_B(extension)) - sprintf(offset, "D%d", (extension>>6)&7); - else - sprintf(offset, "%d", (extension>>6)&31); - if(BIT_5(extension)) - sprintf(width, "D%d", extension&7); - else - sprintf(width, "%d", g_5bit_data_table[extension&31]); - sprintf(g_dasm_str, "bfchg %s {%s:%s}; (2+)", get_ea_mode_str_8(g_cpu_ir), offset, width); + std::string width = BIT(extension, 5) ? util::string_format("D%d", extension&7) : util::string_format("%d", m_5bit_data_table[extension&31]); + return util::string_format("bfchg %s {%s:%s}; (2+)", get_ea_mode_str_8(m_cpu_ir), offset, width); } -static void d68020_bfclr(void) +std::string m68k_disassembler::d68020_bfclr() { - uint32_t extension; - char offset[3]; - char width[3]; + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; - LIMIT_CPU_TYPES(M68020_PLUS); + u16 extension = read_imm_16(); - extension = read_imm_16(); + std::string offset = BIT(extension, 11) ? util::string_format("D%d", (extension>>6)&7) : util::string_format("%d", (extension>>6)&31); - if(BIT_B(extension)) - sprintf(offset, "D%d", (extension>>6)&7); - else - sprintf(offset, "%d", (extension>>6)&31); - if(BIT_5(extension)) - sprintf(width, "D%d", extension&7); - else - sprintf(width, "%d", g_5bit_data_table[extension&31]); - sprintf(g_dasm_str, "bfclr %s {%s:%s}; (2+)", get_ea_mode_str_8(g_cpu_ir), offset, width); + std::string width = BIT(extension, 5) ? util::string_format("D%d", extension&7) : util::string_format("%d", m_5bit_data_table[extension&31]); + return util::string_format("bfclr %s {%s:%s}; (2+)", get_ea_mode_str_8(m_cpu_ir), offset, width); } -static void d68020_bfexts(void) +std::string m68k_disassembler::d68020_bfexts() { - uint32_t extension; - char offset[3]; - char width[3]; + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; - LIMIT_CPU_TYPES(M68020_PLUS); + u16 extension = read_imm_16(); - extension = read_imm_16(); + std::string offset = BIT(extension, 11) ? util::string_format("D%d", (extension>>6)&7) : util::string_format("%d", (extension>>6)&31); - if(BIT_B(extension)) - sprintf(offset, "D%d", (extension>>6)&7); - else - sprintf(offset, "%d", (extension>>6)&31); - if(BIT_5(extension)) - sprintf(width, "D%d", extension&7); - else - sprintf(width, "%d", g_5bit_data_table[extension&31]); - sprintf(g_dasm_str, "bfexts D%d, %s {%s:%s}; (2+)", (extension>>12)&7, get_ea_mode_str_8(g_cpu_ir), offset, width); + std::string width = BIT(extension, 5) ? util::string_format("D%d", extension&7) : util::string_format("%d", m_5bit_data_table[extension&31]); + return util::string_format("bfexts D%d, %s {%s:%s}; (2+)", (extension>>12)&7, get_ea_mode_str_8(m_cpu_ir), offset, width); } -static void d68020_bfextu(void) +std::string m68k_disassembler::d68020_bfextu() { - uint32_t extension; - char offset[3]; - char width[3]; + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; - LIMIT_CPU_TYPES(M68020_PLUS); + u16 extension = read_imm_16(); - extension = read_imm_16(); + std::string offset = BIT(extension, 11) ? util::string_format("D%d", (extension>>6)&7) : util::string_format("%d", (extension>>6)&31); - if(BIT_B(extension)) - sprintf(offset, "D%d", (extension>>6)&7); - else - sprintf(offset, "%d", (extension>>6)&31); - if(BIT_5(extension)) - sprintf(width, "D%d", extension&7); - else - sprintf(width, "%d", g_5bit_data_table[extension&31]); - sprintf(g_dasm_str, "bfextu D%d, %s {%s:%s}; (2+)", (extension>>12)&7, get_ea_mode_str_8(g_cpu_ir), offset, width); + std::string width = BIT(extension, 5) ? util::string_format("D%d", extension&7) : util::string_format("%d", m_5bit_data_table[extension&31]); + return util::string_format("bfextu D%d, %s {%s:%s}; (2+)", (extension>>12)&7, get_ea_mode_str_8(m_cpu_ir), offset, width); } -static void d68020_bfffo(void) +std::string m68k_disassembler::d68020_bfffo() { - uint32_t extension; - char offset[3]; - char width[3]; + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; - LIMIT_CPU_TYPES(M68020_PLUS); + u16 extension = read_imm_16(); - extension = read_imm_16(); + std::string offset = BIT(extension, 11) ? util::string_format("D%d", (extension>>6)&7) : util::string_format("%d", (extension>>6)&31); - if(BIT_B(extension)) - sprintf(offset, "D%d", (extension>>6)&7); - else - sprintf(offset, "%d", (extension>>6)&31); - if(BIT_5(extension)) - sprintf(width, "D%d", extension&7); - else - sprintf(width, "%d", g_5bit_data_table[extension&31]); - sprintf(g_dasm_str, "bfffo D%d, %s {%s:%s}; (2+)", (extension>>12)&7, get_ea_mode_str_8(g_cpu_ir), offset, width); + std::string width = BIT(extension, 5) ? util::string_format("D%d", extension&7) : util::string_format("%d", m_5bit_data_table[extension&31]); + return util::string_format("bfffo D%d, %s {%s:%s}; (2+)", (extension>>12)&7, get_ea_mode_str_8(m_cpu_ir), offset, width); } -static void d68020_bfins(void) +std::string m68k_disassembler::d68020_bfins() { - uint32_t extension; - char offset[3]; - char width[3]; + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; - LIMIT_CPU_TYPES(M68020_PLUS); + u16 extension = read_imm_16(); - extension = read_imm_16(); + std::string offset = BIT(extension, 11) ? util::string_format("D%d", (extension>>6)&7) : util::string_format("%d", (extension>>6)&31); - if(BIT_B(extension)) - sprintf(offset, "D%d", (extension>>6)&7); - else - sprintf(offset, "%d", (extension>>6)&31); - if(BIT_5(extension)) - sprintf(width, "D%d", extension&7); - else - sprintf(width, "%d", g_5bit_data_table[extension&31]); - sprintf(g_dasm_str, "bfins D%d, %s {%s:%s}; (2+)", (extension>>12)&7, get_ea_mode_str_8(g_cpu_ir), offset, width); + std::string width = BIT(extension, 5) ? util::string_format("D%d", extension&7) : util::string_format("%d", m_5bit_data_table[extension&31]); + return util::string_format("bfins D%d, %s {%s:%s}; (2+)", (extension>>12)&7, get_ea_mode_str_8(m_cpu_ir), offset, width); } -static void d68020_bfset(void) +std::string m68k_disassembler::d68020_bfset() { - uint32_t extension; - char offset[3]; - char width[3]; + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; - LIMIT_CPU_TYPES(M68020_PLUS); + u16 extension = read_imm_16(); - extension = read_imm_16(); + std::string offset = BIT(extension, 11) ? util::string_format("D%d", (extension>>6)&7) : util::string_format("%d", (extension>>6)&31); - if(BIT_B(extension)) - sprintf(offset, "D%d", (extension>>6)&7); - else - sprintf(offset, "%d", (extension>>6)&31); - if(BIT_5(extension)) - sprintf(width, "D%d", extension&7); - else - sprintf(width, "%d", g_5bit_data_table[extension&31]); - sprintf(g_dasm_str, "bfset %s {%s:%s}; (2+)", get_ea_mode_str_8(g_cpu_ir), offset, width); + std::string width = BIT(extension, 5) ? util::string_format("D%d", extension&7) : util::string_format("%d", m_5bit_data_table[extension&31]); + return util::string_format("bfset %s {%s:%s}; (2+)", get_ea_mode_str_8(m_cpu_ir), offset, width); } -static void d68020_bftst(void) +std::string m68k_disassembler::d68020_bftst() { - uint32_t extension; - char offset[3]; - char width[3]; + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; - LIMIT_CPU_TYPES(M68020_PLUS); + u16 extension = read_imm_16(); - extension = read_imm_16(); + std::string offset = BIT(extension, 11) ? util::string_format("D%d", (extension>>6)&7) : util::string_format("%d", (extension>>6)&31); - if(BIT_B(extension)) - sprintf(offset, "D%d", (extension>>6)&7); - else - sprintf(offset, "%d", (extension>>6)&31); - if(BIT_5(extension)) - sprintf(width, "D%d", extension&7); - else - sprintf(width, "%d", g_5bit_data_table[extension&31]); - sprintf(g_dasm_str, "bftst %s {%s:%s}; (2+)", get_ea_mode_str_8(g_cpu_ir), offset, width); + std::string width = BIT(extension, 5) ? util::string_format("D%d", extension&7) : util::string_format("%d", m_5bit_data_table[extension&31]); + return util::string_format("bftst %s {%s:%s}; (2+)", get_ea_mode_str_8(m_cpu_ir), offset, width); } -static void d68000_bra_8(void) +std::string m68k_disassembler::d68000_bra_8() { - uint32_t temp_pc = g_cpu_pc; - sprintf(g_dasm_str, "bra $%x", temp_pc + make_int_8(g_cpu_ir)); + u32 temp_pc = m_cpu_pc; + return util::string_format("bra $%x", temp_pc + make_int_8(m_cpu_ir)); } -static void d68000_bra_16(void) +std::string m68k_disassembler::d68000_bra_16() { - uint32_t temp_pc = g_cpu_pc; - sprintf(g_dasm_str, "bra $%x", temp_pc + make_int_16(read_imm_16())); + u32 temp_pc = m_cpu_pc; + return util::string_format("bra $%x", temp_pc + make_int_16(read_imm_16())); } -static void d68020_bra_32(void) +std::string m68k_disassembler::d68020_bra_32() { - uint32_t temp_pc = g_cpu_pc; - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "bra $%x; (2+)", temp_pc + read_imm_32()); + u32 temp_pc = m_cpu_pc; + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("bra $%x; (2+)", temp_pc + read_imm_32()); } -static void d68000_bset_r(void) +std::string m68k_disassembler::d68000_bset_r() { - sprintf(g_dasm_str, "bset D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("bset D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_bset_s(void) +std::string m68k_disassembler::d68000_bset_s() { - char* str = get_imm_str_u8(); - sprintf(g_dasm_str, "bset %s, %s", str, get_ea_mode_str_8(g_cpu_ir)); + std::string str = get_imm_str_u8(); + return util::string_format("bset %s, %s", str, get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_bsr_8(void) +std::string m68k_disassembler::d68000_bsr_8() { - uint32_t temp_pc = g_cpu_pc; - sprintf(g_dasm_str, "bsr $%x", temp_pc + make_int_8(g_cpu_ir)); - SET_OPCODE_FLAGS(DASMFLAG_STEP_OVER); + u32 temp_pc = m_cpu_pc; + m_flags = STEP_OVER; + return util::string_format("bsr $%x", temp_pc + make_int_8(m_cpu_ir)); } -static void d68000_bsr_16(void) +std::string m68k_disassembler::d68000_bsr_16() { - uint32_t temp_pc = g_cpu_pc; - sprintf(g_dasm_str, "bsr $%x", temp_pc + make_int_16(read_imm_16())); - SET_OPCODE_FLAGS(DASMFLAG_STEP_OVER); + u32 temp_pc = m_cpu_pc; + m_flags = STEP_OVER; + return util::string_format("bsr $%x", temp_pc + make_int_16(read_imm_16())); } -static void d68020_bsr_32(void) +std::string m68k_disassembler::d68020_bsr_32() { - uint32_t temp_pc = g_cpu_pc; - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "bsr $%x; (2+)", temp_pc + read_imm_32()); - SET_OPCODE_FLAGS(DASMFLAG_STEP_OVER); + u32 temp_pc = m_cpu_pc; + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + m_flags = STEP_OVER; + return util::string_format("bsr $%x; (2+)", temp_pc + read_imm_32()); } -static void d68000_btst_r(void) +std::string m68k_disassembler::d68000_btst_r() { - sprintf(g_dasm_str, "btst D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("btst D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_btst_s(void) +std::string m68k_disassembler::d68000_btst_s() { - char* str = get_imm_str_u8(); - sprintf(g_dasm_str, "btst %s, %s", str, get_ea_mode_str_8(g_cpu_ir)); + std::string str = get_imm_str_u8(); + return util::string_format("btst %s, %s", str, get_ea_mode_str_8(m_cpu_ir)); } -static void d68020_callm(void) +std::string m68k_disassembler::d68020_callm() { - char* str; - LIMIT_CPU_TYPES(M68020_ONLY); - str = get_imm_str_u8(); + auto limit = limit_cpu_types(M68020_ONLY); + if(limit.first) + return limit.second; + std::string str = get_imm_str_u8(); - sprintf(g_dasm_str, "callm %s, %s; (2)", str, get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("callm %s, %s; (2)", str, get_ea_mode_str_8(m_cpu_ir)); } -static void d68020_cas_8(void) +std::string m68k_disassembler::d68020_cas_8() { - uint32_t extension; - LIMIT_CPU_TYPES(M68020_PLUS); - extension = read_imm_16(); - sprintf(g_dasm_str, "cas.b D%d, D%d, %s; (2+)", extension&7, (extension>>8)&7, get_ea_mode_str_8(g_cpu_ir)); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + u16 extension = read_imm_16(); + return util::string_format("cas.b D%d, D%d, %s; (2+)", extension&7, (extension>>8)&7, get_ea_mode_str_8(m_cpu_ir)); } -static void d68020_cas_16(void) +std::string m68k_disassembler::d68020_cas_16() { - uint32_t extension; - LIMIT_CPU_TYPES(M68020_PLUS); - extension = read_imm_16(); - sprintf(g_dasm_str, "cas.w D%d, D%d, %s; (2+)", extension&7, (extension>>8)&7, get_ea_mode_str_16(g_cpu_ir)); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + u16 extension = read_imm_16(); + return util::string_format("cas.w D%d, D%d, %s; (2+)", extension&7, (extension>>8)&7, get_ea_mode_str_16(m_cpu_ir)); } -static void d68020_cas_32(void) +std::string m68k_disassembler::d68020_cas_32() { - uint32_t extension; - LIMIT_CPU_TYPES(M68020_PLUS); - extension = read_imm_16(); - sprintf(g_dasm_str, "cas.l D%d, D%d, %s; (2+)", extension&7, (extension>>8)&7, get_ea_mode_str_32(g_cpu_ir)); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + u16 extension = read_imm_16(); + return util::string_format("cas.l D%d, D%d, %s; (2+)", extension&7, (extension>>8)&7, get_ea_mode_str_32(m_cpu_ir)); } -static void d68020_cas2_16(void) +std::string m68k_disassembler::d68020_cas2_16() { /* CAS2 Dc1:Dc2,Du1:Dc2:(Rn1):(Rn2) f e d c b a 9 8 7 6 5 4 3 2 1 0 @@ -1270,495 +907,520 @@ f e d c b a 9 8 7 6 5 4 3 2 1 0 DARn2 0 0 0 Du2 0 0 0 Dc2 */ - uint32_t extension; - LIMIT_CPU_TYPES(M68020_PLUS); - extension = read_imm_32(); - sprintf(g_dasm_str, "cas2.w D%d:D%d:D%d:D%d, (%c%d):(%c%d); (2+)", + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + u32 extension = read_imm_32(); + return util::string_format("cas2.w D%d:D%d:D%d:D%d, (%c%d):(%c%d); (2+)", (extension>>16)&7, extension&7, (extension>>22)&7, (extension>>6)&7, - BIT_1F(extension) ? 'A' : 'D', (extension>>28)&7, - BIT_F(extension) ? 'A' : 'D', (extension>>12)&7); + BIT(extension, 31) ? 'A' : 'D', (extension>>28)&7, + BIT(extension, 15) ? 'A' : 'D', (extension>>12)&7); } -static void d68020_cas2_32(void) +std::string m68k_disassembler::d68020_cas2_32() { - uint32_t extension; - LIMIT_CPU_TYPES(M68020_PLUS); - extension = read_imm_32(); - sprintf(g_dasm_str, "cas2.l D%d:D%d:D%d:D%d, (%c%d):(%c%d); (2+)", + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + u32 extension = read_imm_32(); + return util::string_format("cas2.l D%d:D%d:D%d:D%d, (%c%d):(%c%d); (2+)", (extension>>16)&7, extension&7, (extension>>22)&7, (extension>>6)&7, - BIT_1F(extension) ? 'A' : 'D', (extension>>28)&7, - BIT_F(extension) ? 'A' : 'D', (extension>>12)&7); + BIT(extension, 31) ? 'A' : 'D', (extension>>28)&7, + BIT(extension, 15) ? 'A' : 'D', (extension>>12)&7); } -static void d68000_chk_16(void) +std::string m68k_disassembler::d68000_chk_16() { - sprintf(g_dasm_str, "chk.w %s, D%d", get_ea_mode_str_16(g_cpu_ir), (g_cpu_ir>>9)&7); - SET_OPCODE_FLAGS(DASMFLAG_STEP_OVER); + m_flags = STEP_OVER; + return util::string_format("chk.w %s, D%d", get_ea_mode_str_16(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68020_chk_32(void) +std::string m68k_disassembler::d68020_chk_32() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "chk.l %s, D%d; (2+)", get_ea_mode_str_32(g_cpu_ir), (g_cpu_ir>>9)&7); - SET_OPCODE_FLAGS(DASMFLAG_STEP_OVER); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + m_flags = STEP_OVER; + return util::string_format("chk.l %s, D%d; (2+)", get_ea_mode_str_32(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68020_chk2_cmp2_8(void) +std::string m68k_disassembler::d68020_chk2_cmp2_8() { - uint32_t extension; - LIMIT_CPU_TYPES(M68020_PLUS); - extension = read_imm_16(); - sprintf(g_dasm_str, "%s.b %s, %c%d; (2+)", BIT_B(extension) ? "chk2" : "cmp2", get_ea_mode_str_8(g_cpu_ir), BIT_F(extension) ? 'A' : 'D', (extension>>12)&7); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + u16 extension = read_imm_16(); + return util::string_format("%s.b %s, %c%d; (2+)", BIT(extension, 11) ? "chk2" : "cmp2", get_ea_mode_str_8(m_cpu_ir), BIT(extension, 15) ? 'A' : 'D', (extension>>12)&7); } -static void d68020_chk2_cmp2_16(void) +std::string m68k_disassembler::d68020_chk2_cmp2_16() { - uint32_t extension; - LIMIT_CPU_TYPES(M68020_PLUS); - extension = read_imm_16(); - sprintf(g_dasm_str, "%s.w %s, %c%d; (2+)", BIT_B(extension) ? "chk2" : "cmp2", get_ea_mode_str_16(g_cpu_ir), BIT_F(extension) ? 'A' : 'D', (extension>>12)&7); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + u16 extension = read_imm_16(); + return util::string_format("%s.w %s, %c%d; (2+)", BIT(extension, 11) ? "chk2" : "cmp2", get_ea_mode_str_16(m_cpu_ir), BIT(extension, 15) ? 'A' : 'D', (extension>>12)&7); } -static void d68020_chk2_cmp2_32(void) +std::string m68k_disassembler::d68020_chk2_cmp2_32() { - uint32_t extension; - LIMIT_CPU_TYPES(M68020_PLUS); - extension = read_imm_16(); - sprintf(g_dasm_str, "%s.l %s, %c%d; (2+)", BIT_B(extension) ? "chk2" : "cmp2", get_ea_mode_str_32(g_cpu_ir), BIT_F(extension) ? 'A' : 'D', (extension>>12)&7); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + u16 extension = read_imm_16(); + return util::string_format("%s.l %s, %c%d; (2+)", BIT(extension, 11) ? "chk2" : "cmp2", get_ea_mode_str_32(m_cpu_ir), BIT(extension, 15) ? 'A' : 'D', (extension>>12)&7); } -static void d68040_cinv(void) +std::string m68k_disassembler::d68040_cinv() { - LIMIT_CPU_TYPES(M68040_PLUS); + auto limit = limit_cpu_types(M68040_PLUS); + if(limit.first) + return limit.second; static const char *cachetype[4] = { "nop", "data", "inst", "both" }; - switch((g_cpu_ir>>3)&3) + switch((m_cpu_ir>>3)&3) { case 0: - sprintf(g_dasm_str, "cinv (illegal scope); (4)"); + return util::string_format("cinv (illegal scope); (4)"); break; case 1: - sprintf(g_dasm_str, "cinvl %s, (A%d); (4)", cachetype[(g_cpu_ir>>6)&3], g_cpu_ir&7); + return util::string_format("cinvl %s, (A%d); (4)", cachetype[(m_cpu_ir>>6)&3], m_cpu_ir&7); break; case 2: - sprintf(g_dasm_str, "cinvp %s, (A%d); (4)", cachetype[(g_cpu_ir>>6)&3], g_cpu_ir&7); + return util::string_format("cinvp %s, (A%d); (4)", cachetype[(m_cpu_ir>>6)&3], m_cpu_ir&7); break; - case 3: - sprintf(g_dasm_str, "cinva %s; (4)", cachetype[(g_cpu_ir>>6)&3]); + case 3: default: + return util::string_format("cinva %s; (4)", cachetype[(m_cpu_ir>>6)&3]); break; } } -static void d68000_clr_8(void) +std::string m68k_disassembler::d68000_clr_8() { - sprintf(g_dasm_str, "clr.b %s", get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("clr.b %s", get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_clr_16(void) +std::string m68k_disassembler::d68000_clr_16() { - sprintf(g_dasm_str, "clr.w %s", get_ea_mode_str_16(g_cpu_ir)); + return util::string_format("clr.w %s", get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_clr_32(void) +std::string m68k_disassembler::d68000_clr_32() { - sprintf(g_dasm_str, "clr.l %s", get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("clr.l %s", get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_cmp_8(void) +std::string m68k_disassembler::d68000_cmp_8() { - sprintf(g_dasm_str, "cmp.b %s, D%d", get_ea_mode_str_8(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("cmp.b %s, D%d", get_ea_mode_str_8(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_cmp_16(void) +std::string m68k_disassembler::d68000_cmp_16() { - sprintf(g_dasm_str, "cmp.w %s, D%d", get_ea_mode_str_16(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("cmp.w %s, D%d", get_ea_mode_str_16(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_cmp_32(void) +std::string m68k_disassembler::d68000_cmp_32() { - sprintf(g_dasm_str, "cmp.l %s, D%d", get_ea_mode_str_32(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("cmp.l %s, D%d", get_ea_mode_str_32(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_cmpa_16(void) +std::string m68k_disassembler::d68000_cmpa_16() { - sprintf(g_dasm_str, "cmpa.w %s, A%d", get_ea_mode_str_16(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("cmpa.w %s, A%d", get_ea_mode_str_16(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_cmpa_32(void) +std::string m68k_disassembler::d68000_cmpa_32() { - sprintf(g_dasm_str, "cmpa.l %s, A%d", get_ea_mode_str_32(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("cmpa.l %s, A%d", get_ea_mode_str_32(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_cmpi_8(void) +std::string m68k_disassembler::d68000_cmpi_8() { - char* str = get_imm_str_s8(); - sprintf(g_dasm_str, "cmpi.b %s, %s", str, get_ea_mode_str_8(g_cpu_ir)); + std::string str = get_imm_str_s8(); + return util::string_format("cmpi.b %s, %s", str, get_ea_mode_str_8(m_cpu_ir)); } -static void d68020_cmpi_pcdi_8(void) +std::string m68k_disassembler::d68020_cmpi_pcdi_8() { - char* str; - LIMIT_CPU_TYPES(M68010_PLUS); - str = get_imm_str_s8(); - sprintf(g_dasm_str, "cmpi.b %s, %s; (2+)", str, get_ea_mode_str_8(g_cpu_ir)); + auto limit = limit_cpu_types(M68010_PLUS); + if(limit.first) + return limit.second; + std::string str = get_imm_str_s8(); + return util::string_format("cmpi.b %s, %s; (2+)", str, get_ea_mode_str_8(m_cpu_ir)); } -static void d68020_cmpi_pcix_8(void) +std::string m68k_disassembler::d68020_cmpi_pcix_8() { - char* str; - LIMIT_CPU_TYPES(M68010_PLUS); - str = get_imm_str_s8(); - sprintf(g_dasm_str, "cmpi.b %s, %s; (2+)", str, get_ea_mode_str_8(g_cpu_ir)); + auto limit = limit_cpu_types(M68010_PLUS); + if(limit.first) + return limit.second; + std::string str = get_imm_str_s8(); + return util::string_format("cmpi.b %s, %s; (2+)", str, get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_cmpi_16(void) +std::string m68k_disassembler::d68000_cmpi_16() { - char* str; - str = get_imm_str_s16(); - sprintf(g_dasm_str, "cmpi.w %s, %s", str, get_ea_mode_str_16(g_cpu_ir)); + std::string str = get_imm_str_s16(); + return util::string_format("cmpi.w %s, %s", str, get_ea_mode_str_16(m_cpu_ir)); } -static void d68020_cmpi_pcdi_16(void) +std::string m68k_disassembler::d68020_cmpi_pcdi_16() { - char* str; - LIMIT_CPU_TYPES(M68010_PLUS); - str = get_imm_str_s16(); - sprintf(g_dasm_str, "cmpi.w %s, %s; (2+)", str, get_ea_mode_str_16(g_cpu_ir)); + auto limit = limit_cpu_types(M68010_PLUS); + if(limit.first) + return limit.second; + std::string str = get_imm_str_s16(); + return util::string_format("cmpi.w %s, %s; (2+)", str, get_ea_mode_str_16(m_cpu_ir)); } -static void d68020_cmpi_pcix_16(void) +std::string m68k_disassembler::d68020_cmpi_pcix_16() { - char* str; - LIMIT_CPU_TYPES(M68010_PLUS); - str = get_imm_str_s16(); - sprintf(g_dasm_str, "cmpi.w %s, %s; (2+)", str, get_ea_mode_str_16(g_cpu_ir)); + auto limit = limit_cpu_types(M68010_PLUS); + if(limit.first) + return limit.second; + std::string str = get_imm_str_s16(); + return util::string_format("cmpi.w %s, %s; (2+)", str, get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_cmpi_32(void) +std::string m68k_disassembler::d68000_cmpi_32() { - char* str; - str = get_imm_str_s32(); - sprintf(g_dasm_str, "cmpi.l %s, %s", str, get_ea_mode_str_32(g_cpu_ir)); + std::string str = get_imm_str_s32(); + return util::string_format("cmpi.l %s, %s", str, get_ea_mode_str_32(m_cpu_ir)); } -static void d68020_cmpi_pcdi_32(void) +std::string m68k_disassembler::d68020_cmpi_pcdi_32() { - char* str; - LIMIT_CPU_TYPES(M68010_PLUS); - str = get_imm_str_s32(); - sprintf(g_dasm_str, "cmpi.l %s, %s; (2+)", str, get_ea_mode_str_32(g_cpu_ir)); + auto limit = limit_cpu_types(M68010_PLUS); + if(limit.first) + return limit.second; + std::string str = get_imm_str_s32(); + return util::string_format("cmpi.l %s, %s; (2+)", str, get_ea_mode_str_32(m_cpu_ir)); } -static void d68020_cmpi_pcix_32(void) +std::string m68k_disassembler::d68020_cmpi_pcix_32() { - char* str; - LIMIT_CPU_TYPES(M68010_PLUS); - str = get_imm_str_s32(); - sprintf(g_dasm_str, "cmpi.l %s, %s; (2+)", str, get_ea_mode_str_32(g_cpu_ir)); + auto limit = limit_cpu_types(M68010_PLUS); + if(limit.first) + return limit.second; + std::string str = get_imm_str_s32(); + return util::string_format("cmpi.l %s, %s; (2+)", str, get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_cmpm_8(void) +std::string m68k_disassembler::d68000_cmpm_8() { - sprintf(g_dasm_str, "cmpm.b (A%d)+, (A%d)+", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("cmpm.b (A%d)+, (A%d)+", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_cmpm_16(void) +std::string m68k_disassembler::d68000_cmpm_16() { - sprintf(g_dasm_str, "cmpm.w (A%d)+, (A%d)+", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("cmpm.w (A%d)+, (A%d)+", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_cmpm_32(void) +std::string m68k_disassembler::d68000_cmpm_32() { - sprintf(g_dasm_str, "cmpm.l (A%d)+, (A%d)+", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("cmpm.l (A%d)+, (A%d)+", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68020_cpbcc_16(void) +std::string m68k_disassembler::d68020_cpbcc_16() { - uint32_t extension; - uint32_t new_pc = g_cpu_pc; - LIMIT_CPU_TYPES(M68020_PLUS); - extension = read_imm_16(); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + u32 new_pc = m_cpu_pc; + u16 extension = read_imm_16(); new_pc += make_int_16(read_imm_16()); - sprintf(g_dasm_str, "%db%-4s %s; %x (extension = %x) (2-3)", (g_cpu_ir>>9)&7, g_cpcc[g_cpu_ir&0x3f], get_imm_str_s16(), new_pc, extension); + return util::string_format("%db%-4s %s; %x (extension = %x) (2-3)", (m_cpu_ir>>9)&7, m_cpcc[m_cpu_ir&0x3f], get_imm_str_s16(), new_pc, extension); } -static void d68020_cpbcc_32(void) +std::string m68k_disassembler::d68020_cpbcc_32() { - uint32_t extension; - uint32_t new_pc = g_cpu_pc; - LIMIT_CPU_TYPES(M68020_PLUS); - extension = read_imm_16(); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + u32 new_pc = m_cpu_pc; + u16 extension = read_imm_16(); new_pc += read_imm_32(); - sprintf(g_dasm_str, "%db%-4s %s; %x (extension = %x) (2-3)", (g_cpu_ir>>9)&7, g_cpcc[g_cpu_ir&0x3f], get_imm_str_s16(), new_pc, extension); + return util::string_format("%db%-4s %s; %x (extension = %x) (2-3)", (m_cpu_ir>>9)&7, m_cpcc[m_cpu_ir&0x3f], get_imm_str_s16(), new_pc, extension); } -static void d68020_cpdbcc(void) +std::string m68k_disassembler::d68020_cpdbcc() { - uint32_t extension1; - uint32_t extension2; - uint32_t new_pc = g_cpu_pc; - LIMIT_CPU_TYPES(M68020_PLUS); - extension1 = read_imm_16(); - extension2 = read_imm_16(); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + u32 new_pc = m_cpu_pc; + u16 extension1 = read_imm_16(); + u16 extension2 = read_imm_16(); new_pc += make_int_16(read_imm_16()); - sprintf(g_dasm_str, "%ddb%-4s D%d,%s; %x (extension = %x) (2-3)", (g_cpu_ir>>9)&7, g_cpcc[extension1&0x3f], g_cpu_ir&7, get_imm_str_s16(), new_pc, extension2); + return util::string_format("%ddb%-4s D%d,%s; %x (extension = %x) (2-3)", (m_cpu_ir>>9)&7, m_cpcc[extension1&0x3f], m_cpu_ir&7, get_imm_str_s16(), new_pc, extension2); } -static void d68020_cpgen(void) +std::string m68k_disassembler::d68020_cpgen() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "%dgen %s; (2-3)", (g_cpu_ir>>9)&7, get_imm_str_u32()); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("%dgen %s; (2-3)", (m_cpu_ir>>9)&7, get_imm_str_u32()); } -static void d68020_cprestore(void) +std::string m68k_disassembler::d68020_cprestore() { - LIMIT_CPU_TYPES(M68020_PLUS); - if (((g_cpu_ir>>9)&7) == 1) + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + if (((m_cpu_ir>>9)&7) == 1) { - sprintf(g_dasm_str, "frestore %s", get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("frestore %s", get_ea_mode_str_8(m_cpu_ir)); } else { - sprintf(g_dasm_str, "%drestore %s; (2-3)", (g_cpu_ir>>9)&7, get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("%drestore %s; (2-3)", (m_cpu_ir>>9)&7, get_ea_mode_str_8(m_cpu_ir)); } } -static void d68020_cpsave(void) +std::string m68k_disassembler::d68020_cpsave() { - LIMIT_CPU_TYPES(M68020_PLUS); - if (((g_cpu_ir>>9)&7) == 1) + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + if (((m_cpu_ir>>9)&7) == 1) { - sprintf(g_dasm_str, "fsave %s", get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("fsave %s", get_ea_mode_str_8(m_cpu_ir)); } else { - sprintf(g_dasm_str, "%dsave %s; (2-3)", (g_cpu_ir>>9)&7, get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("%dsave %s; (2-3)", (m_cpu_ir>>9)&7, get_ea_mode_str_8(m_cpu_ir)); } } -static void d68020_cpscc(void) +std::string m68k_disassembler::d68020_cpscc() { - uint32_t extension1; - uint32_t extension2; - LIMIT_CPU_TYPES(M68020_PLUS); - extension1 = read_imm_16(); - extension2 = read_imm_16(); - sprintf(g_dasm_str, "%ds%-4s %s; (extension = %x) (2-3)", (g_cpu_ir>>9)&7, g_cpcc[extension1&0x3f], get_ea_mode_str_8(g_cpu_ir), extension2); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + u16 extension1 = read_imm_16(); + u16 extension2 = read_imm_16(); + return util::string_format("%ds%-4s %s; (extension = %x) (2-3)", (m_cpu_ir>>9)&7, m_cpcc[extension1&0x3f], get_ea_mode_str_8(m_cpu_ir), extension2); } -static void d68020_cptrapcc_0(void) +std::string m68k_disassembler::d68020_cptrapcc_0() { - uint32_t extension1; - uint32_t extension2; - LIMIT_CPU_TYPES(M68020_PLUS); - extension1 = read_imm_16(); - extension2 = read_imm_16(); - sprintf(g_dasm_str, "%dtrap%-4s; (extension = %x) (2-3)", (g_cpu_ir>>9)&7, g_cpcc[extension1&0x3f], extension2); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + u16 extension1 = read_imm_16(); + u16 extension2 = read_imm_16(); + return util::string_format("%dtrap%-4s; (extension = %x) (2-3)", (m_cpu_ir>>9)&7, m_cpcc[extension1&0x3f], extension2); } -static void d68020_cptrapcc_16(void) +std::string m68k_disassembler::d68020_cptrapcc_16() { - uint32_t extension1; - uint32_t extension2; - LIMIT_CPU_TYPES(M68020_PLUS); - extension1 = read_imm_16(); - extension2 = read_imm_16(); - sprintf(g_dasm_str, "%dtrap%-4s %s; (extension = %x) (2-3)", (g_cpu_ir>>9)&7, g_cpcc[extension1&0x3f], get_imm_str_u16(), extension2); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + u16 extension1 = read_imm_16(); + u16 extension2 = read_imm_16(); + return util::string_format("%dtrap%-4s %s; (extension = %x) (2-3)", (m_cpu_ir>>9)&7, m_cpcc[extension1&0x3f], get_imm_str_u16(), extension2); } -static void d68020_cptrapcc_32(void) +std::string m68k_disassembler::d68020_cptrapcc_32() { - uint32_t extension1; - uint32_t extension2; - LIMIT_CPU_TYPES(M68020_PLUS); - extension1 = read_imm_16(); - extension2 = read_imm_16(); - sprintf(g_dasm_str, "%dtrap%-4s %s; (extension = %x) (2-3)", (g_cpu_ir>>9)&7, g_cpcc[extension1&0x3f], get_imm_str_u32(), extension2); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + u16 extension1 = read_imm_16(); + u16 extension2 = read_imm_16(); + return util::string_format("%dtrap%-4s %s; (extension = %x) (2-3)", (m_cpu_ir>>9)&7, m_cpcc[extension1&0x3f], get_imm_str_u32(), extension2); } -static void d68040_cpush(void) +std::string m68k_disassembler::d68040_cpush() { + auto limit = limit_cpu_types(M68040_PLUS); + if(limit.first) + return limit.second; + static const char *cachetype[4] = { "nop", "data", "inst", "both" }; - LIMIT_CPU_TYPES(M68040_PLUS); - switch((g_cpu_ir>>3)&3) + switch((m_cpu_ir>>3)&3) { case 0: - sprintf(g_dasm_str, "cpush (illegal scope); (4)"); + return util::string_format("cpush (illegal scope); (4)"); break; case 1: - sprintf(g_dasm_str, "cpushl %s, (A%d); (4)", cachetype[(g_cpu_ir>>6)&3], g_cpu_ir&7); + return util::string_format("cpushl %s, (A%d); (4)", cachetype[(m_cpu_ir>>6)&3], m_cpu_ir&7); break; case 2: - sprintf(g_dasm_str, "cpushp %s, (A%d); (4)", cachetype[(g_cpu_ir>>6)&3], g_cpu_ir&7); + return util::string_format("cpushp %s, (A%d); (4)", cachetype[(m_cpu_ir>>6)&3], m_cpu_ir&7); break; - case 3: - sprintf(g_dasm_str, "cpusha %s; (4)", cachetype[(g_cpu_ir>>6)&3]); + case 3: default: + return util::string_format("cpusha %s; (4)", cachetype[(m_cpu_ir>>6)&3]); break; } } -static void d68000_dbra(void) +std::string m68k_disassembler::d68000_dbra() { - uint32_t temp_pc = g_cpu_pc; - sprintf(g_dasm_str, "dbra D%d, $%x", g_cpu_ir & 7, temp_pc + make_int_16(read_imm_16())); - SET_OPCODE_FLAGS(DASMFLAG_STEP_OVER); + u32 temp_pc = m_cpu_pc; + m_flags = STEP_OVER; + return util::string_format("dbra D%d, $%x", m_cpu_ir & 7, temp_pc + make_int_16(read_imm_16())); } -static void d68000_dbcc(void) +std::string m68k_disassembler::d68000_dbcc() { - uint32_t temp_pc = g_cpu_pc; - sprintf(g_dasm_str, "db%-2s D%d, $%x", g_cc[(g_cpu_ir>>8)&0xf], g_cpu_ir & 7, temp_pc + make_int_16(read_imm_16())); - SET_OPCODE_FLAGS(DASMFLAG_STEP_OVER); + u32 temp_pc = m_cpu_pc; + m_flags = STEP_OVER; + return util::string_format("db%-2s D%d, $%x", m_cc[(m_cpu_ir>>8)&0xf], m_cpu_ir & 7, temp_pc + make_int_16(read_imm_16())); } -static void d68000_divs(void) +std::string m68k_disassembler::d68000_divs() { - sprintf(g_dasm_str, "divs.w %s, D%d", get_ea_mode_str_16(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("divs.w %s, D%d", get_ea_mode_str_16(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_divu(void) +std::string m68k_disassembler::d68000_divu() { - sprintf(g_dasm_str, "divu.w %s, D%d", get_ea_mode_str_16(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("divu.w %s, D%d", get_ea_mode_str_16(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68020_divl(void) +std::string m68k_disassembler::d68020_divl() { - uint32_t extension; - LIMIT_CPU_TYPES(M68020_PLUS); - extension = read_imm_16(); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; - if(BIT_A(extension)) - sprintf(g_dasm_str, "div%c.l %s, D%d:D%d; (2+)", BIT_B(extension) ? 's' : 'u', get_ea_mode_str_32(g_cpu_ir), extension&7, (extension>>12)&7); + u16 extension = read_imm_16(); + + if(BIT(extension, 10)) + return util::string_format("div%c.l %s, D%d:D%d; (2+)", BIT(extension, 11) ? 's' : 'u', get_ea_mode_str_32(m_cpu_ir), extension&7, (extension>>12)&7); else if((extension&7) == ((extension>>12)&7)) - sprintf(g_dasm_str, "div%c.l %s, D%d; (2+)", BIT_B(extension) ? 's' : 'u', get_ea_mode_str_32(g_cpu_ir), (extension>>12)&7); + return util::string_format("div%c.l %s, D%d; (2+)", BIT(extension, 11) ? 's' : 'u', get_ea_mode_str_32(m_cpu_ir), (extension>>12)&7); else - sprintf(g_dasm_str, "div%cl.l %s, D%d:D%d; (2+)", BIT_B(extension) ? 's' : 'u', get_ea_mode_str_32(g_cpu_ir), extension&7, (extension>>12)&7); + return util::string_format("div%cl.l %s, D%d:D%d; (2+)", BIT(extension, 11) ? 's' : 'u', get_ea_mode_str_32(m_cpu_ir), extension&7, (extension>>12)&7); } -static void d68000_eor_8(void) +std::string m68k_disassembler::d68000_eor_8() { - sprintf(g_dasm_str, "eor.b D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("eor.b D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_eor_16(void) +std::string m68k_disassembler::d68000_eor_16() { - sprintf(g_dasm_str, "eor.w D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_16(g_cpu_ir)); + return util::string_format("eor.w D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_eor_32(void) +std::string m68k_disassembler::d68000_eor_32() { - sprintf(g_dasm_str, "eor.l D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("eor.l D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_eori_8(void) +std::string m68k_disassembler::d68000_eori_8() { - char* str = get_imm_str_u8(); - sprintf(g_dasm_str, "eori.b %s, %s", str, get_ea_mode_str_8(g_cpu_ir)); + std::string str = get_imm_str_u8(); + return util::string_format("eori.b %s, %s", str, get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_eori_16(void) +std::string m68k_disassembler::d68000_eori_16() { - char* str = get_imm_str_u16(); - sprintf(g_dasm_str, "eori.w %s, %s", str, get_ea_mode_str_16(g_cpu_ir)); + std::string str = get_imm_str_u16(); + return util::string_format("eori.w %s, %s", str, get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_eori_32(void) +std::string m68k_disassembler::d68000_eori_32() { - char* str = get_imm_str_u32(); - sprintf(g_dasm_str, "eori.l %s, %s", str, get_ea_mode_str_32(g_cpu_ir)); + std::string str = get_imm_str_u32(); + return util::string_format("eori.l %s, %s", str, get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_eori_to_ccr(void) +std::string m68k_disassembler::d68000_eori_to_ccr() { - sprintf(g_dasm_str, "eori %s, CCR", get_imm_str_u8()); + return util::string_format("eori %s, CCR", get_imm_str_u8()); } -static void d68000_eori_to_sr(void) +std::string m68k_disassembler::d68000_eori_to_sr() { - sprintf(g_dasm_str, "eori %s, SR", get_imm_str_u16()); + return util::string_format("eori %s, SR", get_imm_str_u16()); } -static void d68000_exg_dd(void) +std::string m68k_disassembler::d68000_exg_dd() { - sprintf(g_dasm_str, "exg D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("exg D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_exg_aa(void) +std::string m68k_disassembler::d68000_exg_aa() { - sprintf(g_dasm_str, "exg A%d, A%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("exg A%d, A%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_exg_da(void) +std::string m68k_disassembler::d68000_exg_da() { - sprintf(g_dasm_str, "exg D%d, A%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("exg D%d, A%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_ext_16(void) +std::string m68k_disassembler::d68000_ext_16() { - sprintf(g_dasm_str, "ext.w D%d", g_cpu_ir&7); + return util::string_format("ext.w D%d", m_cpu_ir&7); } -static void d68000_ext_32(void) +std::string m68k_disassembler::d68000_ext_32() { - sprintf(g_dasm_str, "ext.l D%d", g_cpu_ir&7); + return util::string_format("ext.l D%d", m_cpu_ir&7); } -static void d68020_extb_32(void) +std::string m68k_disassembler::d68020_extb_32() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "extb.l D%d; (2+)", g_cpu_ir&7); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("extb.l D%d; (2+)", m_cpu_ir&7); } -static void d68881_ftrap(void) +std::string m68k_disassembler::d68881_ftrap() { - uint16_t w2, w3; - uint32_t l2; - - LIMIT_CPU_TYPES(M68020_PLUS); - w2 = read_imm_16(); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + u16 w2 = read_imm_16(); - switch (g_cpu_ir & 0x7) + switch (m_cpu_ir & 0x7) { case 2: // word operand - w3 = read_imm_16(); - sprintf(g_dasm_str, "ftrap%s.w $%04x", g_cpcc[w2 & 0x3f], w3); - break; + return util::string_format("ftrap%s.w $%04x", m_cpcc[w2 & 0x3f], read_imm_16()); case 3: // long word operand - l2 = read_imm_32(); - sprintf(g_dasm_str, "ftrap%s.l $%08x", g_cpcc[w2 & 0x3f], l2); - break; + return util::string_format("ftrap%s.l $%08x", m_cpcc[w2 & 0x3f], read_imm_32()); case 4: // no operand - sprintf(g_dasm_str, "ftrap%s", g_cpcc[w2 & 0x3f]); - break; + return util::string_format("ftrap%s", m_cpcc[w2 & 0x3f]); } + return util::string_format("ftrap%s<%d>?", m_cpcc[w2 & 0x3f], m_cpu_ir & 7); + } -static void d68040_fpu(void) +std::string m68k_disassembler::d68040_fpu() { char float_data_format[8][3] = { ".l", ".s", ".x", ".p", ".w", ".d", ".b", ".p" }; - char mnemonic[40]; - uint32_t w2, src, dst_reg; - LIMIT_CPU_TYPES(M68020_PLUS); - w2 = read_imm_16(); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + + u16 w2 = read_imm_16(); - src = (w2 >> 10) & 0x7; - dst_reg = (w2 >> 7) & 0x7; + u16 src = (w2 >> 10) & 0x7; + u16 dst_reg = (w2 >> 7) & 0x7; // special override for FMOVECR if ((((w2 >> 13) & 0x7) == 2) && (((w2>>10)&0x7) == 7)) { - sprintf(g_dasm_str, "fmovecr #$%0x, fp%d", (w2&0x7f), dst_reg); - return; + return util::string_format("fmovecr #$%0x, fp%d", (w2&0x7f), dst_reg); } + std::string mnemonic; switch ((w2 >> 13) & 0x7) { case 0x0: @@ -1766,72 +1428,71 @@ static void d68040_fpu(void) { switch(w2 & 0x7f) { - case 0x00: sprintf(mnemonic, "fmove"); break; - case 0x01: sprintf(mnemonic, "fint"); break; - case 0x02: sprintf(mnemonic, "fsinh"); break; - case 0x03: sprintf(mnemonic, "fintrz"); break; - case 0x04: sprintf(mnemonic, "fsqrt"); break; - case 0x06: sprintf(mnemonic, "flognp1"); break; - case 0x08: sprintf(mnemonic, "fetoxm1"); break; - case 0x09: sprintf(mnemonic, "ftanh1"); break; - case 0x0a: sprintf(mnemonic, "fatan"); break; - case 0x0c: sprintf(mnemonic, "fasin"); break; - case 0x0d: sprintf(mnemonic, "fatanh"); break; - case 0x0e: sprintf(mnemonic, "fsin"); break; - case 0x0f: sprintf(mnemonic, "ftan"); break; - case 0x10: sprintf(mnemonic, "fetox"); break; - case 0x11: sprintf(mnemonic, "ftwotox"); break; - case 0x12: sprintf(mnemonic, "ftentox"); break; - case 0x14: sprintf(mnemonic, "flogn"); break; - case 0x15: sprintf(mnemonic, "flog10"); break; - case 0x16: sprintf(mnemonic, "flog2"); break; - case 0x18: sprintf(mnemonic, "fabs"); break; - case 0x19: sprintf(mnemonic, "fcosh"); break; - case 0x1a: sprintf(mnemonic, "fneg"); break; - case 0x1c: sprintf(mnemonic, "facos"); break; - case 0x1d: sprintf(mnemonic, "fcos"); break; - case 0x1e: sprintf(mnemonic, "fgetexp"); break; - case 0x1f: sprintf(mnemonic, "fgetman"); break; - case 0x20: sprintf(mnemonic, "fdiv"); break; - case 0x21: sprintf(mnemonic, "fmod"); break; - case 0x22: sprintf(mnemonic, "fadd"); break; - case 0x23: sprintf(mnemonic, "fmul"); break; - case 0x24: sprintf(mnemonic, "fsgldiv"); break; - case 0x25: sprintf(mnemonic, "frem"); break; - case 0x26: sprintf(mnemonic, "fscale"); break; - case 0x27: sprintf(mnemonic, "fsglmul"); break; - case 0x28: sprintf(mnemonic, "fsub"); break; + case 0x00: mnemonic = "fmove"; break; + case 0x01: mnemonic = "fint"; break; + case 0x02: mnemonic = "fsinh"; break; + case 0x03: mnemonic = "fintrz"; break; + case 0x04: mnemonic = "fsqrt"; break; + case 0x06: mnemonic = "flognp1"; break; + case 0x08: mnemonic = "fetoxm1"; break; + case 0x09: mnemonic = "ftanh1"; break; + case 0x0a: mnemonic = "fatan"; break; + case 0x0c: mnemonic = "fasin"; break; + case 0x0d: mnemonic = "fatanh"; break; + case 0x0e: mnemonic = "fsin"; break; + case 0x0f: mnemonic = "ftan"; break; + case 0x10: mnemonic = "fetox"; break; + case 0x11: mnemonic = "ftwotox"; break; + case 0x12: mnemonic = "ftentox"; break; + case 0x14: mnemonic = "flogn"; break; + case 0x15: mnemonic = "flog10"; break; + case 0x16: mnemonic = "flog2"; break; + case 0x18: mnemonic = "fabs"; break; + case 0x19: mnemonic = "fcosh"; break; + case 0x1a: mnemonic = "fneg"; break; + case 0x1c: mnemonic = "facos"; break; + case 0x1d: mnemonic = "fcos"; break; + case 0x1e: mnemonic = "fgetexp"; break; + case 0x1f: mnemonic = "fgetman"; break; + case 0x20: mnemonic = "fdiv"; break; + case 0x21: mnemonic = "fmod"; break; + case 0x22: mnemonic = "fadd"; break; + case 0x23: mnemonic = "fmul"; break; + case 0x24: mnemonic = "fsgldiv"; break; + case 0x25: mnemonic = "frem"; break; + case 0x26: mnemonic = "fscale"; break; + case 0x27: mnemonic = "fsglmul"; break; + case 0x28: mnemonic = "fsub"; break; case 0x30: case 0x31: case 0x32: case 0x33: case 0x34: case 0x35: case 0x36: case 0x37: - sprintf(mnemonic, "fsincos"); break; - case 0x38: sprintf(mnemonic, "fcmp"); break; - case 0x3a: sprintf(mnemonic, "ftst"); break; - case 0x41: sprintf(mnemonic, "fssqrt"); break; - case 0x45: sprintf(mnemonic, "fdsqrt"); break; - case 0x58: sprintf(mnemonic, "fsabs"); break; - case 0x5a: sprintf(mnemonic, "fsneg"); break; - case 0x5c: sprintf(mnemonic, "fdabs"); break; - case 0x5e: sprintf(mnemonic, "fdneg"); break; - case 0x60: sprintf(mnemonic, "fsdiv"); break; - case 0x62: sprintf(mnemonic, "fsadd"); break; - case 0x63: sprintf(mnemonic, "fsmul"); break; - case 0x64: sprintf(mnemonic, "fddiv"); break; - case 0x66: sprintf(mnemonic, "fdadd"); break; - case 0x67: sprintf(mnemonic, "fdmul"); break; - case 0x68: sprintf(mnemonic, "fssub"); break; - case 0x6c: sprintf(mnemonic, "fdsub"); break; - - default: sprintf(mnemonic, "FPU (?)"); break; + mnemonic = "fsincos"; break; + case 0x38: mnemonic = "fcmp"; break; + case 0x3a: mnemonic = "ftst"; break; + case 0x41: mnemonic = "fssqrt"; break; + case 0x45: mnemonic = "fdsqrt"; break; + case 0x58: mnemonic = "fsabs"; break; + case 0x5a: mnemonic = "fsneg"; break; + case 0x5c: mnemonic = "fdabs"; break; + case 0x5e: mnemonic = "fdneg"; break; + case 0x60: mnemonic = "fsdiv"; break; + case 0x62: mnemonic = "fsadd"; break; + case 0x63: mnemonic = "fsmul"; break; + case 0x64: mnemonic = "fddiv"; break; + case 0x66: mnemonic = "fdadd"; break; + case 0x67: mnemonic = "fdmul"; break; + case 0x68: mnemonic = "fssub"; break; + case 0x6c: mnemonic = "fdsub"; break; + + default: mnemonic = "FPU (?)"; break; } if (w2 & 0x4000) { - sprintf(g_dasm_str, "%s%s %s, FP%d", mnemonic, float_data_format[src], get_ea_mode_str_32(g_cpu_ir), dst_reg); + return util::string_format("%s%s %s, FP%d", mnemonic, float_data_format[src], get_ea_mode_str_32(m_cpu_ir), dst_reg); } else { - sprintf(g_dasm_str, "%s.x FP%d, FP%d", mnemonic, src, dst_reg); + return util::string_format("%s.x FP%d, FP%d", mnemonic, src, dst_reg); } - break; } case 0x3: @@ -1839,15 +1500,13 @@ static void d68040_fpu(void) switch ((w2>>10)&7) { case 3: // packed decimal w/fixed k-factor - sprintf(g_dasm_str, "fmove%s FP%d, %s {#%d}", float_data_format[(w2>>10)&7], dst_reg, get_ea_mode_str_32(g_cpu_ir), sext_7bit_int(w2&0x7f)); - break; + return util::string_format("fmove%s FP%d, %s {#%d}", float_data_format[(w2>>10)&7], dst_reg, get_ea_mode_str_32(m_cpu_ir), sext_7bit_int(w2&0x7f)); case 7: // packed decimal w/dynamic k-factor (register) - sprintf(g_dasm_str, "fmove%s FP%d, %s {D%d}", float_data_format[(w2>>10)&7], dst_reg, get_ea_mode_str_32(g_cpu_ir), (w2>>4)&7); - break; + return util::string_format("fmove%s FP%d, %s {D%d}", float_data_format[(w2>>10)&7], dst_reg, get_ea_mode_str_32(m_cpu_ir), (w2>>4)&7); default: - sprintf(g_dasm_str, "fmove%s FP%d, %s", float_data_format[(w2>>10)&7], dst_reg, get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("fmove%s FP%d, %s", float_data_format[(w2>>10)&7], dst_reg, get_ea_mode_str_32(m_cpu_ir)); break; } break; @@ -1855,264 +1514,250 @@ static void d68040_fpu(void) case 0x4: // ea to control { - sprintf(g_dasm_str, "fmovem.l %s, ", get_ea_mode_str_32(g_cpu_ir)); - if (w2 & 0x1000) strcat(g_dasm_str, "fpcr"); - if (w2 & 0x0800) strcat(g_dasm_str, "/fpsr"); - if (w2 & 0x0400) strcat(g_dasm_str, "/fpiar"); - break; + std::string dasm = util::string_format("fmovem.l %s, ", get_ea_mode_str_32(m_cpu_ir)); + if (w2 & 0x1000) return dasm + "fpcr"; + if (w2 & 0x0800) return dasm + "/fpsr"; + if (w2 & 0x0400) return dasm + "/fpiar"; + return dasm; } case 0x5: // control to ea { - strcpy(g_dasm_str, "fmovem.l "); - if (w2 & 0x1000) strcat(g_dasm_str, "fpcr"); - if (w2 & 0x0800) strcat(g_dasm_str, "/fpsr"); - if (w2 & 0x0400) strcat(g_dasm_str, "/fpiar"); - strcat(g_dasm_str, ", "); - strcat(g_dasm_str, get_ea_mode_str_32(g_cpu_ir)); - break; + std::string dasm = "fmovem.l "; + if (w2 & 0x1000) dasm += "fpcr"; + if (w2 & 0x0800) dasm += "/fpsr"; + if (w2 & 0x0400) dasm += "/fpiar"; + return dasm + ", " + get_ea_mode_str_32(m_cpu_ir); } case 0x6: // memory to FPU, list { - char temp[32]; - if ((w2>>11) & 1) // dynamic register list { - sprintf(g_dasm_str, "fmovem.x %s, D%d", get_ea_mode_str_32(g_cpu_ir), (w2>>4)&7); + return util::string_format("fmovem.x %s, D%d", get_ea_mode_str_32(m_cpu_ir), (w2>>4)&7); } else // static register list { - int i; - - sprintf(g_dasm_str, "fmovem.x %s, ", get_ea_mode_str_32(g_cpu_ir)); + std::string dasm = util::string_format("fmovem.x %s, ", get_ea_mode_str_32(m_cpu_ir)); - for (i = 0; i < 8; i++) + for (int i = 0; i < 8; i++) { if (w2 & (1<>12) & 1) // postincrement or control { - sprintf(temp, "FP%d ", 7-i); + dasm += util::string_format("FP%d ", 7-i); } else // predecrement { - sprintf(temp, "FP%d ", i); + dasm += util::string_format("FP%d ", i); } - strcat(g_dasm_str, temp); } } + return dasm; } - break; } case 0x7: // FPU to memory, list { - char temp[32]; - if ((w2>>11) & 1) // dynamic register list { - sprintf(g_dasm_str, "fmovem.x D%d, %s", (w2>>4)&7, get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("fmovem.x D%d, %s", (w2>>4)&7, get_ea_mode_str_32(m_cpu_ir)); } else // static register list { - int i; + std::string dasm = util::string_format("fmovem.x "); - sprintf(g_dasm_str, "fmovem.x "); - - for (i = 0; i < 8; i++) + for (int i = 0; i < 8; i++) { if (w2 & (1<>12) & 1) // postincrement or control { - sprintf(temp, "FP%d ", 7-i); + dasm += util::string_format("FP%d ", 7-i); } else // predecrement { - sprintf(temp, "FP%d ", i); + dasm += util::string_format("FP%d ", i); } - strcat(g_dasm_str, temp); } } - strcat(g_dasm_str, ", "); - strcat(g_dasm_str, get_ea_mode_str_32(g_cpu_ir)); + return dasm + ", " + get_ea_mode_str_32(m_cpu_ir); } - break; - } - - default: - { - sprintf(g_dasm_str, "FPU (?) "); - break; } } + return util::string_format("FPU (?) "); } -static void d68000_jmp(void) +std::string m68k_disassembler::d68000_jmp() { - sprintf(g_dasm_str, "jmp %s", get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("jmp %s", get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_jsr(void) +std::string m68k_disassembler::d68000_jsr() { - sprintf(g_dasm_str, "jsr %s", get_ea_mode_str_32(g_cpu_ir)); - SET_OPCODE_FLAGS(DASMFLAG_STEP_OVER); + m_flags = STEP_OVER; + return util::string_format("jsr %s", get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_lea(void) +std::string m68k_disassembler::d68000_lea() { - sprintf(g_dasm_str, "lea %s, A%d", get_ea_mode_str_32(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("lea %s, A%d", get_ea_mode_str_32(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_link_16(void) +std::string m68k_disassembler::d68000_link_16() { - sprintf(g_dasm_str, "link A%d, %s", g_cpu_ir&7, get_imm_str_s16()); + return util::string_format("link A%d, %s", m_cpu_ir&7, get_imm_str_s16()); } -static void d68020_link_32(void) +std::string m68k_disassembler::d68020_link_32() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "link A%d, %s; (2+)", g_cpu_ir&7, get_imm_str_s32()); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("link A%d, %s; (2+)", m_cpu_ir&7, get_imm_str_s32()); } -static void d68000_lsr_s_8(void) +std::string m68k_disassembler::d68000_lsr_s_8() { - sprintf(g_dasm_str, "lsr.b #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("lsr.b #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_lsr_s_16(void) +std::string m68k_disassembler::d68000_lsr_s_16() { - sprintf(g_dasm_str, "lsr.w #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("lsr.w #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_lsr_s_32(void) +std::string m68k_disassembler::d68000_lsr_s_32() { - sprintf(g_dasm_str, "lsr.l #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("lsr.l #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_lsr_r_8(void) +std::string m68k_disassembler::d68000_lsr_r_8() { - sprintf(g_dasm_str, "lsr.b D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("lsr.b D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_lsr_r_16(void) +std::string m68k_disassembler::d68000_lsr_r_16() { - sprintf(g_dasm_str, "lsr.w D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("lsr.w D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_lsr_r_32(void) +std::string m68k_disassembler::d68000_lsr_r_32() { - sprintf(g_dasm_str, "lsr.l D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("lsr.l D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_lsr_ea(void) +std::string m68k_disassembler::d68000_lsr_ea() { - sprintf(g_dasm_str, "lsr.w %s", get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("lsr.w %s", get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_lsl_s_8(void) +std::string m68k_disassembler::d68000_lsl_s_8() { - sprintf(g_dasm_str, "lsl.b #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("lsl.b #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_lsl_s_16(void) +std::string m68k_disassembler::d68000_lsl_s_16() { - sprintf(g_dasm_str, "lsl.w #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("lsl.w #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_lsl_s_32(void) +std::string m68k_disassembler::d68000_lsl_s_32() { - sprintf(g_dasm_str, "lsl.l #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("lsl.l #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_lsl_r_8(void) +std::string m68k_disassembler::d68000_lsl_r_8() { - sprintf(g_dasm_str, "lsl.b D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("lsl.b D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_lsl_r_16(void) +std::string m68k_disassembler::d68000_lsl_r_16() { - sprintf(g_dasm_str, "lsl.w D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("lsl.w D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_lsl_r_32(void) +std::string m68k_disassembler::d68000_lsl_r_32() { - sprintf(g_dasm_str, "lsl.l D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("lsl.l D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_lsl_ea(void) +std::string m68k_disassembler::d68000_lsl_ea() { - sprintf(g_dasm_str, "lsl.w %s", get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("lsl.w %s", get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_move_8(void) +std::string m68k_disassembler::d68000_move_8() { - char* str = get_ea_mode_str_8(g_cpu_ir); - sprintf(g_dasm_str, "move.b %s, %s", str, get_ea_mode_str_8(((g_cpu_ir>>9) & 7) | ((g_cpu_ir>>3) & 0x38))); + std::string str = get_ea_mode_str_8(m_cpu_ir); + return util::string_format("move.b %s, %s", str, get_ea_mode_str_8(((m_cpu_ir>>9) & 7) | ((m_cpu_ir>>3) & 0x38))); } -static void d68000_move_16(void) +std::string m68k_disassembler::d68000_move_16() { - char* str = get_ea_mode_str_16(g_cpu_ir); - sprintf(g_dasm_str, "move.w %s, %s", str, get_ea_mode_str_16(((g_cpu_ir>>9) & 7) | ((g_cpu_ir>>3) & 0x38))); + std::string str = get_ea_mode_str_16(m_cpu_ir); + return util::string_format("move.w %s, %s", str, get_ea_mode_str_16(((m_cpu_ir>>9) & 7) | ((m_cpu_ir>>3) & 0x38))); } -static void d68000_move_32(void) +std::string m68k_disassembler::d68000_move_32() { - char* str = get_ea_mode_str_32(g_cpu_ir); - sprintf(g_dasm_str, "move.l %s, %s", str, get_ea_mode_str_32(((g_cpu_ir>>9) & 7) | ((g_cpu_ir>>3) & 0x38))); + std::string str = get_ea_mode_str_32(m_cpu_ir); + return util::string_format("move.l %s, %s", str, get_ea_mode_str_32(((m_cpu_ir>>9) & 7) | ((m_cpu_ir>>3) & 0x38))); } -static void d68000_movea_16(void) +std::string m68k_disassembler::d68000_movea_16() { - sprintf(g_dasm_str, "movea.w %s, A%d", get_ea_mode_str_16(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("movea.w %s, A%d", get_ea_mode_str_16(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_movea_32(void) +std::string m68k_disassembler::d68000_movea_32() { - sprintf(g_dasm_str, "movea.l %s, A%d", get_ea_mode_str_32(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("movea.l %s, A%d", get_ea_mode_str_32(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_move_to_ccr(void) +std::string m68k_disassembler::d68000_move_to_ccr() { - sprintf(g_dasm_str, "move %s, CCR", get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("move %s, CCR", get_ea_mode_str_8(m_cpu_ir)); } -static void d68010_move_fr_ccr(void) +std::string m68k_disassembler::d68010_move_fr_ccr() { - LIMIT_CPU_TYPES(M68010_PLUS); - sprintf(g_dasm_str, "move CCR, %s; (1+)", get_ea_mode_str_8(g_cpu_ir)); + auto limit = limit_cpu_types(M68010_PLUS); + if(limit.first) + return limit.second; + return util::string_format("move CCR, %s; (1+)", get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_move_fr_sr(void) +std::string m68k_disassembler::d68000_move_fr_sr() { - sprintf(g_dasm_str, "move SR, %s", get_ea_mode_str_16(g_cpu_ir)); + return util::string_format("move SR, %s", get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_move_to_sr(void) +std::string m68k_disassembler::d68000_move_to_sr() { - sprintf(g_dasm_str, "move %s, SR", get_ea_mode_str_16(g_cpu_ir)); + return util::string_format("move %s, SR", get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_move_fr_usp(void) +std::string m68k_disassembler::d68000_move_fr_usp() { - sprintf(g_dasm_str, "move USP, A%d", g_cpu_ir&7); + return util::string_format("move USP, A%d", m_cpu_ir&7); } -static void d68000_move_to_usp(void) +std::string m68k_disassembler::d68000_move_to_usp() { - sprintf(g_dasm_str, "move A%d, USP", g_cpu_ir&7); + return util::string_format("move A%d, USP", m_cpu_ir&7); } -static void d68010_movec(void) +std::string m68k_disassembler::d68010_movec() { - uint32_t extension; - const char* reg_name; - const char* processor; - LIMIT_CPU_TYPES(M68010_PLUS); - extension = read_imm_16(); + auto limit = limit_cpu_types(M68010_PLUS); + if(limit.first) + return limit.second; + + std::string reg_name, processor; + u16 extension = read_imm_16(); switch(extension & 0xfff) { @@ -2153,7 +1798,7 @@ static void d68010_movec(void) processor = "4+"; break; case 0x004: - if(g_cpu_type & COLDFIRE) + if(m_cpu_type & COLDFIRE) { reg_name = "ACR0"; processor = "CF"; @@ -2165,7 +1810,7 @@ static void d68010_movec(void) } break; case 0x005: - if(g_cpu_type & COLDFIRE) + if(m_cpu_type & COLDFIRE) { reg_name = "ACR1"; processor = "CF"; @@ -2177,7 +1822,7 @@ static void d68010_movec(void) } break; case 0x006: - if(g_cpu_type & COLDFIRE) + if(m_cpu_type & COLDFIRE) { reg_name = "ACR2"; processor = "CF"; @@ -2189,7 +1834,7 @@ static void d68010_movec(void) } break; case 0x007: - if(g_cpu_type & COLDFIRE) + if(m_cpu_type & COLDFIRE) { reg_name = "ACR3"; processor = "CF"; @@ -2249,994 +1894,1026 @@ static void d68010_movec(void) processor = "?"; } - if(BIT_0(g_cpu_ir)) - sprintf(g_dasm_str, "movec %c%d, %s; (%s)", BIT_F(extension) ? 'A' : 'D', (extension>>12)&7, reg_name, processor); + if(BIT(m_cpu_ir, 0)) + return util::string_format("movec %c%d, %s; (%s)", BIT(extension, 15) ? 'A' : 'D', (extension>>12)&7, reg_name, processor); else - sprintf(g_dasm_str, "movec %s, %c%d; (%s)", reg_name, BIT_F(extension) ? 'A' : 'D', (extension>>12)&7, processor); + return util::string_format("movec %s, %c%d; (%s)", reg_name, BIT(extension, 15) ? 'A' : 'D', (extension>>12)&7, processor); } -static void d68000_movem_pd_16(void) +std::string m68k_disassembler::d68000_movem_pd_16() { - uint32_t data = read_imm_16(); - char buffer[40]; - uint32_t first; - uint32_t run_length; - uint32_t i; + u32 data = read_imm_16(); - buffer[0] = 0; - for(i=0;i<8;i++) + std::string regs; + for(int i=0;i<8;i++) { if(data&(1<<(15-i))) { - first = i; - run_length = 0; + int first = i; + int run_length = 0; while(i<7 && (data&(1<<(15-(i+1))))) { i++; run_length++; } - if(buffer[0] != 0) - strcat(buffer, "/"); - sprintf(buffer+strlen(buffer), "D%d", first); + if(!regs.empty()) + regs += '/'; + regs += util::string_format("D%d", first); if(run_length > 0) - sprintf(buffer+strlen(buffer), "-D%d", first + run_length); + regs += util::string_format("-D%d", first + run_length); } } - for(i=0;i<8;i++) + for(int i=0;i<8;i++) { if(data&(1<<(7-i))) { - first = i; - run_length = 0; + int first = i; + int run_length = 0; while(i<7 && (data&(1<<(7-(i+1))))) { i++; run_length++; } - if(buffer[0] != 0) - strcat(buffer, "/"); - sprintf(buffer+strlen(buffer), "A%d", first); + if(!regs.empty()) + regs += '/'; + regs += util::string_format("A%d", first); if(run_length > 0) - sprintf(buffer+strlen(buffer), "-A%d", first + run_length); + regs += util::string_format("-A%d", first + run_length); } } - sprintf(g_dasm_str, "movem.w %s, %s", buffer, get_ea_mode_str_16(g_cpu_ir)); + return util::string_format("movem.w %s, %s", regs, get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_movem_pd_32(void) +std::string m68k_disassembler::d68000_movem_pd_32() { - uint32_t data = read_imm_16(); - char buffer[40]; - uint32_t first; - uint32_t run_length; - uint32_t i; + u32 data = read_imm_16(); - buffer[0] = 0; - for(i=0;i<8;i++) + std::string regs; + for(int i=0;i<8;i++) { if(data&(1<<(15-i))) { - first = i; - run_length = 0; + int first = i; + int run_length = 0; while(i<7 && (data&(1<<(15-(i+1))))) { i++; run_length++; } - if(buffer[0] != 0) - strcat(buffer, "/"); - sprintf(buffer+strlen(buffer), "D%d", first); + if(!regs.empty()) + regs += '/'; + regs += util::string_format("D%d", first); if(run_length > 0) - sprintf(buffer+strlen(buffer), "-D%d", first + run_length); + regs += util::string_format("-D%d", first + run_length); } } - for(i=0;i<8;i++) + for(int i=0;i<8;i++) { if(data&(1<<(7-i))) { - first = i; - run_length = 0; + int first = i; + int run_length = 0; while(i<7 && (data&(1<<(7-(i+1))))) { i++; run_length++; } - if(buffer[0] != 0) - strcat(buffer, "/"); - sprintf(buffer+strlen(buffer), "A%d", first); + if(!regs.empty()) + regs += '/'; + regs += util::string_format("A%d", first); if(run_length > 0) - sprintf(buffer+strlen(buffer), "-A%d", first + run_length); + regs += util::string_format("-A%d", first + run_length); } } - sprintf(g_dasm_str, "movem.l %s, %s", buffer, get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("movem.l %s, %s", regs, get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_movem_er_16(void) +std::string m68k_disassembler::d68000_movem_er_16() { - uint32_t data = read_imm_16(); - char buffer[40]; - uint32_t first; - uint32_t run_length; - uint32_t i; + u32 data = read_imm_16(); - buffer[0] = 0; - for(i=0;i<8;i++) + std::string regs; + for(int i=0;i<8;i++) { if(data&(1< 0) - sprintf(buffer+strlen(buffer), "-D%d", first + run_length); + regs += util::string_format("-D%d", first + run_length); } } - for(i=0;i<8;i++) + for(int i=0;i<8;i++) { if(data&(1<<(i+8))) { - first = i; - run_length = 0; + int first = i; + int run_length = 0; while(i<7 && (data&(1<<(i+8+1)))) { i++; run_length++; } - if(buffer[0] != 0) - strcat(buffer, "/"); - sprintf(buffer+strlen(buffer), "A%d", first); + if(!regs.empty()) + regs += '/'; + regs += util::string_format("A%d", first); if(run_length > 0) - sprintf(buffer+strlen(buffer), "-A%d", first + run_length); + regs += util::string_format("-A%d", first + run_length); } } - sprintf(g_dasm_str, "movem.w %s, %s", get_ea_mode_str_16(g_cpu_ir), buffer); + return util::string_format("movem.w %s, %s", get_ea_mode_str_16(m_cpu_ir), regs); } -static void d68000_movem_er_32(void) +std::string m68k_disassembler::d68000_movem_er_32() { - uint32_t data = read_imm_16(); - char buffer[40]; - uint32_t first; - uint32_t run_length; - uint32_t i; + u32 data = read_imm_16(); - buffer[0] = 0; - for(i=0;i<8;i++) + std::string regs; + for(int i=0;i<8;i++) { if(data&(1< 0) - sprintf(buffer+strlen(buffer), "-D%d", first + run_length); + regs += util::string_format("-D%d", first + run_length); } } - for(i=0;i<8;i++) + for(int i=0;i<8;i++) { if(data&(1<<(i+8))) { - first = i; - run_length = 0; + int first = i; + int run_length = 0; while(i<7 && (data&(1<<(i+8+1)))) { i++; run_length++; } - if(buffer[0] != 0) - strcat(buffer, "/"); - sprintf(buffer+strlen(buffer), "A%d", first); + if(!regs.empty()) + regs += '/'; + regs += util::string_format("A%d", first); if(run_length > 0) - sprintf(buffer+strlen(buffer), "-A%d", first + run_length); + regs += util::string_format("-A%d", first + run_length); } } - sprintf(g_dasm_str, "movem.l %s, %s", get_ea_mode_str_32(g_cpu_ir), buffer); + return util::string_format("movem.l %s, %s", get_ea_mode_str_32(m_cpu_ir), regs); } -static void d68000_movem_re_16(void) +std::string m68k_disassembler::d68000_movem_re_16() { - uint32_t data = read_imm_16(); - char buffer[40]; - uint32_t first; - uint32_t run_length; - uint32_t i; + u32 data = read_imm_16(); - buffer[0] = 0; - for(i=0;i<8;i++) + std::string regs; + for(int i=0;i<8;i++) { if(data&(1< 0) - sprintf(buffer+strlen(buffer), "-D%d", first + run_length); + regs += util::string_format("-D%d", first + run_length); } } - for(i=0;i<8;i++) + for(int i=0;i<8;i++) { if(data&(1<<(i+8))) { - first = i; - run_length = 0; + int first = i; + int run_length = 0; while(i<7 && (data&(1<<(i+8+1)))) { i++; run_length++; } - if(buffer[0] != 0) - strcat(buffer, "/"); - sprintf(buffer+strlen(buffer), "A%d", first); + if(!regs.empty()) + regs += '/'; + regs += util::string_format("A%d", first); if(run_length > 0) - sprintf(buffer+strlen(buffer), "-A%d", first + run_length); + regs += util::string_format("-A%d", first + run_length); } } - sprintf(g_dasm_str, "movem.w %s, %s", buffer, get_ea_mode_str_16(g_cpu_ir)); + return util::string_format("movem.w %s, %s", regs, get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_movem_re_32(void) +std::string m68k_disassembler::d68000_movem_re_32() { - uint32_t data = read_imm_16(); - char buffer[40]; - uint32_t first; - uint32_t run_length; - uint32_t i; + u32 data = read_imm_16(); - buffer[0] = 0; - for(i=0;i<8;i++) + std::string regs; + for(int i=0;i<8;i++) { if(data&(1< 0) - sprintf(buffer+strlen(buffer), "-D%d", first + run_length); + regs += util::string_format("-D%d", first + run_length); } } - for(i=0;i<8;i++) + for(int i=0;i<8;i++) { if(data&(1<<(i+8))) { - first = i; - run_length = 0; + int first = i; + int run_length = 0; while(i<7 && (data&(1<<(i+8+1)))) { i++; run_length++; } - if(buffer[0] != 0) - strcat(buffer, "/"); - sprintf(buffer+strlen(buffer), "A%d", first); + if(!regs.empty()) + regs += '/'; + regs += util::string_format("A%d", first); if(run_length > 0) - sprintf(buffer+strlen(buffer), "-A%d", first + run_length); + regs += util::string_format("-A%d", first + run_length); } } - sprintf(g_dasm_str, "movem.l %s, %s", buffer, get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("movem.l %s, %s", regs, get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_movep_re_16(void) +std::string m68k_disassembler::d68000_movep_re_16() { - sprintf(g_dasm_str, "movep.w D%d, ($%x,A%d)", (g_cpu_ir>>9)&7, read_imm_16(), g_cpu_ir&7); + return util::string_format("movep.w D%d, ($%x,A%d)", (m_cpu_ir>>9)&7, read_imm_16(), m_cpu_ir&7); } -static void d68000_movep_re_32(void) +std::string m68k_disassembler::d68000_movep_re_32() { - sprintf(g_dasm_str, "movep.l D%d, ($%x,A%d)", (g_cpu_ir>>9)&7, read_imm_16(), g_cpu_ir&7); + return util::string_format("movep.l D%d, ($%x,A%d)", (m_cpu_ir>>9)&7, read_imm_16(), m_cpu_ir&7); } -static void d68000_movep_er_16(void) +std::string m68k_disassembler::d68000_movep_er_16() { - sprintf(g_dasm_str, "movep.w ($%x,A%d), D%d", read_imm_16(), g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("movep.w ($%x,A%d), D%d", read_imm_16(), m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_movep_er_32(void) +std::string m68k_disassembler::d68000_movep_er_32() { - sprintf(g_dasm_str, "movep.l ($%x,A%d), D%d", read_imm_16(), g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("movep.l ($%x,A%d), D%d", read_imm_16(), m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68010_moves_8(void) +std::string m68k_disassembler::d68010_moves_8() { - uint32_t extension; - LIMIT_CPU_TYPES(M68010_PLUS); - extension = read_imm_16(); - if(BIT_B(extension)) - sprintf(g_dasm_str, "moves.b %c%d, %s; (1+)", BIT_F(extension) ? 'A' : 'D', (extension>>12)&7, get_ea_mode_str_8(g_cpu_ir)); + auto limit = limit_cpu_types(M68010_PLUS); + if(limit.first) + return limit.second; + u16 extension = read_imm_16(); + if(BIT(extension, 11)) + return util::string_format("moves.b %c%d, %s; (1+)", BIT(extension, 15) ? 'A' : 'D', (extension>>12)&7, get_ea_mode_str_8(m_cpu_ir)); else - sprintf(g_dasm_str, "moves.b %s, %c%d; (1+)", get_ea_mode_str_8(g_cpu_ir), BIT_F(extension) ? 'A' : 'D', (extension>>12)&7); + return util::string_format("moves.b %s, %c%d; (1+)", get_ea_mode_str_8(m_cpu_ir), BIT(extension, 15) ? 'A' : 'D', (extension>>12)&7); } -static void d68010_moves_16(void) +std::string m68k_disassembler::d68010_moves_16() { - uint32_t extension; - LIMIT_CPU_TYPES(M68010_PLUS); - extension = read_imm_16(); - if(BIT_B(extension)) - sprintf(g_dasm_str, "moves.w %c%d, %s; (1+)", BIT_F(extension) ? 'A' : 'D', (extension>>12)&7, get_ea_mode_str_16(g_cpu_ir)); + auto limit = limit_cpu_types(M68010_PLUS); + if(limit.first) + return limit.second; + u16 extension = read_imm_16(); + if(BIT(extension, 11)) + return util::string_format("moves.w %c%d, %s; (1+)", BIT(extension, 15) ? 'A' : 'D', (extension>>12)&7, get_ea_mode_str_16(m_cpu_ir)); else - sprintf(g_dasm_str, "moves.w %s, %c%d; (1+)", get_ea_mode_str_16(g_cpu_ir), BIT_F(extension) ? 'A' : 'D', (extension>>12)&7); + return util::string_format("moves.w %s, %c%d; (1+)", get_ea_mode_str_16(m_cpu_ir), BIT(extension, 15) ? 'A' : 'D', (extension>>12)&7); } -static void d68010_moves_32(void) +std::string m68k_disassembler::d68010_moves_32() { - uint32_t extension; - LIMIT_CPU_TYPES(M68010_PLUS); - extension = read_imm_16(); - if(BIT_B(extension)) - sprintf(g_dasm_str, "moves.l %c%d, %s; (1+)", BIT_F(extension) ? 'A' : 'D', (extension>>12)&7, get_ea_mode_str_32(g_cpu_ir)); + auto limit = limit_cpu_types(M68010_PLUS); + if(limit.first) + return limit.second; + u16 extension = read_imm_16(); + if(BIT(extension, 11)) + return util::string_format("moves.l %c%d, %s; (1+)", BIT(extension, 15) ? 'A' : 'D', (extension>>12)&7, get_ea_mode_str_32(m_cpu_ir)); else - sprintf(g_dasm_str, "moves.l %s, %c%d; (1+)", get_ea_mode_str_32(g_cpu_ir), BIT_F(extension) ? 'A' : 'D', (extension>>12)&7); + return util::string_format("moves.l %s, %c%d; (1+)", get_ea_mode_str_32(m_cpu_ir), BIT(extension, 15) ? 'A' : 'D', (extension>>12)&7); } -static void d68000_moveq(void) +std::string m68k_disassembler::d68000_moveq() { - sprintf(g_dasm_str, "moveq #%s, D%d", make_signed_hex_str_8(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("moveq #%s, D%d", make_signed_hex_str_8(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68040_move16_pi_pi(void) +std::string m68k_disassembler::d68040_move16_pi_pi() { - LIMIT_CPU_TYPES(M68040_PLUS); - sprintf(g_dasm_str, "move16 (A%d)+, (A%d)+; (4)", g_cpu_ir&7, (read_imm_16()>>12)&7); + auto limit = limit_cpu_types(M68040_PLUS); + if(limit.first) + return limit.second; + return util::string_format("move16 (A%d)+, (A%d)+; (4)", m_cpu_ir&7, (read_imm_16()>>12)&7); } -static void d68040_move16_pi_al(void) +std::string m68k_disassembler::d68040_move16_pi_al() { - LIMIT_CPU_TYPES(M68040_PLUS); - sprintf(g_dasm_str, "move16 (A%d)+, %s; (4)", g_cpu_ir&7, get_imm_str_u32()); + auto limit = limit_cpu_types(M68040_PLUS); + if(limit.first) + return limit.second; + return util::string_format("move16 (A%d)+, %s; (4)", m_cpu_ir&7, get_imm_str_u32()); } -static void d68040_move16_al_pi(void) +std::string m68k_disassembler::d68040_move16_al_pi() { - LIMIT_CPU_TYPES(M68040_PLUS); - sprintf(g_dasm_str, "move16 %s, (A%d)+; (4)", get_imm_str_u32(), g_cpu_ir&7); + auto limit = limit_cpu_types(M68040_PLUS); + if(limit.first) + return limit.second; + return util::string_format("move16 %s, (A%d)+; (4)", get_imm_str_u32(), m_cpu_ir&7); } -static void d68040_move16_ai_al(void) +std::string m68k_disassembler::d68040_move16_ai_al() { - LIMIT_CPU_TYPES(M68040_PLUS); - sprintf(g_dasm_str, "move16 (A%d), %s; (4)", g_cpu_ir&7, get_imm_str_u32()); + auto limit = limit_cpu_types(M68040_PLUS); + if(limit.first) + return limit.second; + return util::string_format("move16 (A%d), %s; (4)", m_cpu_ir&7, get_imm_str_u32()); } -static void d68040_move16_al_ai(void) +std::string m68k_disassembler::d68040_move16_al_ai() { - LIMIT_CPU_TYPES(M68040_PLUS); - sprintf(g_dasm_str, "move16 %s, (A%d); (4)", get_imm_str_u32(), g_cpu_ir&7); + auto limit = limit_cpu_types(M68040_PLUS); + if(limit.first) + return limit.second; + return util::string_format("move16 %s, (A%d); (4)", get_imm_str_u32(), m_cpu_ir&7); } -static void d68000_muls(void) +std::string m68k_disassembler::d68000_muls() { - sprintf(g_dasm_str, "muls.w %s, D%d", get_ea_mode_str_16(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("muls.w %s, D%d", get_ea_mode_str_16(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_mulu(void) +std::string m68k_disassembler::d68000_mulu() { - sprintf(g_dasm_str, "mulu.w %s, D%d", get_ea_mode_str_16(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("mulu.w %s, D%d", get_ea_mode_str_16(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68020_mull(void) +std::string m68k_disassembler::d68020_mull() { - uint32_t extension; - LIMIT_CPU_TYPES(M68020_PLUS); - extension = read_imm_16(); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + u16 extension = read_imm_16(); - if(BIT_A(extension)) - sprintf(g_dasm_str, "mul%c.l %s, D%d-D%d; (2+)", BIT_B(extension) ? 's' : 'u', get_ea_mode_str_32(g_cpu_ir), extension&7, (extension>>12)&7); + if(BIT(extension, 10)) + return util::string_format("mul%c.l %s, D%d-D%d; (2+)", BIT(extension, 11) ? 's' : 'u', get_ea_mode_str_32(m_cpu_ir), extension&7, (extension>>12)&7); else - sprintf(g_dasm_str, "mul%c.l %s, D%d; (2+)", BIT_B(extension) ? 's' : 'u', get_ea_mode_str_32(g_cpu_ir), (extension>>12)&7); + return util::string_format("mul%c.l %s, D%d; (2+)", BIT(extension, 11) ? 's' : 'u', get_ea_mode_str_32(m_cpu_ir), (extension>>12)&7); } -static void d68000_nbcd(void) +std::string m68k_disassembler::d68000_nbcd() { - sprintf(g_dasm_str, "nbcd %s", get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("nbcd %s", get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_neg_8(void) +std::string m68k_disassembler::d68000_neg_8() { - sprintf(g_dasm_str, "neg.b %s", get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("neg.b %s", get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_neg_16(void) +std::string m68k_disassembler::d68000_neg_16() { - sprintf(g_dasm_str, "neg.w %s", get_ea_mode_str_16(g_cpu_ir)); + return util::string_format("neg.w %s", get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_neg_32(void) +std::string m68k_disassembler::d68000_neg_32() { - sprintf(g_dasm_str, "neg.l %s", get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("neg.l %s", get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_negx_8(void) +std::string m68k_disassembler::d68000_negx_8() { - sprintf(g_dasm_str, "negx.b %s", get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("negx.b %s", get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_negx_16(void) +std::string m68k_disassembler::d68000_negx_16() { - sprintf(g_dasm_str, "negx.w %s", get_ea_mode_str_16(g_cpu_ir)); + return util::string_format("negx.w %s", get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_negx_32(void) +std::string m68k_disassembler::d68000_negx_32() { - sprintf(g_dasm_str, "negx.l %s", get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("negx.l %s", get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_nop(void) +std::string m68k_disassembler::d68000_nop() { - sprintf(g_dasm_str, "nop"); + return util::string_format("nop"); } -static void d68000_not_8(void) +std::string m68k_disassembler::d68000_not_8() { - sprintf(g_dasm_str, "not.b %s", get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("not.b %s", get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_not_16(void) +std::string m68k_disassembler::d68000_not_16() { - sprintf(g_dasm_str, "not.w %s", get_ea_mode_str_16(g_cpu_ir)); + return util::string_format("not.w %s", get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_not_32(void) +std::string m68k_disassembler::d68000_not_32() { - sprintf(g_dasm_str, "not.l %s", get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("not.l %s", get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_or_er_8(void) +std::string m68k_disassembler::d68000_or_er_8() { - sprintf(g_dasm_str, "or.b %s, D%d", get_ea_mode_str_8(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("or.b %s, D%d", get_ea_mode_str_8(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_or_er_16(void) +std::string m68k_disassembler::d68000_or_er_16() { - sprintf(g_dasm_str, "or.w %s, D%d", get_ea_mode_str_16(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("or.w %s, D%d", get_ea_mode_str_16(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_or_er_32(void) +std::string m68k_disassembler::d68000_or_er_32() { - sprintf(g_dasm_str, "or.l %s, D%d", get_ea_mode_str_32(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("or.l %s, D%d", get_ea_mode_str_32(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_or_re_8(void) +std::string m68k_disassembler::d68000_or_re_8() { - sprintf(g_dasm_str, "or.b D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("or.b D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_or_re_16(void) +std::string m68k_disassembler::d68000_or_re_16() { - sprintf(g_dasm_str, "or.w D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_16(g_cpu_ir)); + return util::string_format("or.w D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_or_re_32(void) +std::string m68k_disassembler::d68000_or_re_32() { - sprintf(g_dasm_str, "or.l D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("or.l D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_ori_8(void) +std::string m68k_disassembler::d68000_ori_8() { - char* str = get_imm_str_u8(); - sprintf(g_dasm_str, "ori.b %s, %s", str, get_ea_mode_str_8(g_cpu_ir)); + std::string str = get_imm_str_u8(); + return util::string_format("ori.b %s, %s", str, get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_ori_16(void) +std::string m68k_disassembler::d68000_ori_16() { - char* str = get_imm_str_u16(); - sprintf(g_dasm_str, "ori.w %s, %s", str, get_ea_mode_str_16(g_cpu_ir)); + std::string str = get_imm_str_u16(); + return util::string_format("ori.w %s, %s", str, get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_ori_32(void) +std::string m68k_disassembler::d68000_ori_32() { - char* str = get_imm_str_u32(); - sprintf(g_dasm_str, "ori.l %s, %s", str, get_ea_mode_str_32(g_cpu_ir)); + std::string str = get_imm_str_u32(); + return util::string_format("ori.l %s, %s", str, get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_ori_to_ccr(void) +std::string m68k_disassembler::d68000_ori_to_ccr() { - sprintf(g_dasm_str, "ori %s, CCR", get_imm_str_u8()); + return util::string_format("ori %s, CCR", get_imm_str_u8()); } -static void d68000_ori_to_sr(void) +std::string m68k_disassembler::d68000_ori_to_sr() { - sprintf(g_dasm_str, "ori %s, SR", get_imm_str_u16()); + return util::string_format("ori %s, SR", get_imm_str_u16()); } -static void d68020_pack_rr(void) +std::string m68k_disassembler::d68020_pack_rr() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "pack D%d, D%d, %s; (2+)", g_cpu_ir&7, (g_cpu_ir>>9)&7, get_imm_str_u16()); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("pack D%d, D%d, %s; (2+)", m_cpu_ir&7, (m_cpu_ir>>9)&7, get_imm_str_u16()); } -static void d68020_pack_mm(void) +std::string m68k_disassembler::d68020_pack_mm() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "pack -(A%d), -(A%d), %s; (2+)", g_cpu_ir&7, (g_cpu_ir>>9)&7, get_imm_str_u16()); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("pack -(A%d), -(A%d), %s; (2+)", m_cpu_ir&7, (m_cpu_ir>>9)&7, get_imm_str_u16()); } -static void d68000_pea(void) +std::string m68k_disassembler::d68000_pea() { - sprintf(g_dasm_str, "pea %s", get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("pea %s", get_ea_mode_str_32(m_cpu_ir)); } // this is a 68040-specific form of PFLUSH -static void d68040_pflush(void) +std::string m68k_disassembler::d68040_pflush() { - LIMIT_CPU_TYPES(M68040_PLUS); + auto limit = limit_cpu_types(M68040_PLUS); + if(limit.first) + return limit.second; - if (g_cpu_ir & 0x10) + if (m_cpu_ir & 0x10) { - sprintf(g_dasm_str, "pflusha%s", (g_cpu_ir & 8) ? "" : "n"); + return util::string_format("pflusha%s", (m_cpu_ir & 8) ? "" : "n"); } else { - sprintf(g_dasm_str, "pflush%s(A%d)", (g_cpu_ir & 8) ? "" : "n", g_cpu_ir & 7); + return util::string_format("pflush%s(A%d)", (m_cpu_ir & 8) ? "" : "n", m_cpu_ir & 7); } } -static void d68000_reset(void) +std::string m68k_disassembler::d68000_reset() { - sprintf(g_dasm_str, "reset"); + return util::string_format("reset"); } -static void d68000_ror_s_8(void) +std::string m68k_disassembler::d68000_ror_s_8() { - sprintf(g_dasm_str, "ror.b #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("ror.b #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_ror_s_16(void) +std::string m68k_disassembler::d68000_ror_s_16() { - sprintf(g_dasm_str, "ror.w #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7],g_cpu_ir&7); + return util::string_format("ror.w #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7],m_cpu_ir&7); } -static void d68000_ror_s_32(void) +std::string m68k_disassembler::d68000_ror_s_32() { - sprintf(g_dasm_str, "ror.l #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("ror.l #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_ror_r_8(void) +std::string m68k_disassembler::d68000_ror_r_8() { - sprintf(g_dasm_str, "ror.b D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("ror.b D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_ror_r_16(void) +std::string m68k_disassembler::d68000_ror_r_16() { - sprintf(g_dasm_str, "ror.w D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("ror.w D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_ror_r_32(void) +std::string m68k_disassembler::d68000_ror_r_32() { - sprintf(g_dasm_str, "ror.l D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("ror.l D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_ror_ea(void) +std::string m68k_disassembler::d68000_ror_ea() { - sprintf(g_dasm_str, "ror.w %s", get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("ror.w %s", get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_rol_s_8(void) +std::string m68k_disassembler::d68000_rol_s_8() { - sprintf(g_dasm_str, "rol.b #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("rol.b #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_rol_s_16(void) +std::string m68k_disassembler::d68000_rol_s_16() { - sprintf(g_dasm_str, "rol.w #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("rol.w #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_rol_s_32(void) +std::string m68k_disassembler::d68000_rol_s_32() { - sprintf(g_dasm_str, "rol.l #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("rol.l #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_rol_r_8(void) +std::string m68k_disassembler::d68000_rol_r_8() { - sprintf(g_dasm_str, "rol.b D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("rol.b D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_rol_r_16(void) +std::string m68k_disassembler::d68000_rol_r_16() { - sprintf(g_dasm_str, "rol.w D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("rol.w D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_rol_r_32(void) +std::string m68k_disassembler::d68000_rol_r_32() { - sprintf(g_dasm_str, "rol.l D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("rol.l D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_rol_ea(void) +std::string m68k_disassembler::d68000_rol_ea() { - sprintf(g_dasm_str, "rol.w %s", get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("rol.w %s", get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_roxr_s_8(void) +std::string m68k_disassembler::d68000_roxr_s_8() { - sprintf(g_dasm_str, "roxr.b #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("roxr.b #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_roxr_s_16(void) +std::string m68k_disassembler::d68000_roxr_s_16() { - sprintf(g_dasm_str, "roxr.w #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("roxr.w #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_roxr_s_32(void) +std::string m68k_disassembler::d68000_roxr_s_32() { - sprintf(g_dasm_str, "roxr.l #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("roxr.l #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_roxr_r_8(void) +std::string m68k_disassembler::d68000_roxr_r_8() { - sprintf(g_dasm_str, "roxr.b D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("roxr.b D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_roxr_r_16(void) +std::string m68k_disassembler::d68000_roxr_r_16() { - sprintf(g_dasm_str, "roxr.w D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("roxr.w D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_roxr_r_32(void) +std::string m68k_disassembler::d68000_roxr_r_32() { - sprintf(g_dasm_str, "roxr.l D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("roxr.l D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_roxr_ea(void) +std::string m68k_disassembler::d68000_roxr_ea() { - sprintf(g_dasm_str, "roxr.w %s", get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("roxr.w %s", get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_roxl_s_8(void) +std::string m68k_disassembler::d68000_roxl_s_8() { - sprintf(g_dasm_str, "roxl.b #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("roxl.b #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_roxl_s_16(void) +std::string m68k_disassembler::d68000_roxl_s_16() { - sprintf(g_dasm_str, "roxl.w #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("roxl.w #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_roxl_s_32(void) +std::string m68k_disassembler::d68000_roxl_s_32() { - sprintf(g_dasm_str, "roxl.l #%d, D%d", g_3bit_qdata_table[(g_cpu_ir>>9)&7], g_cpu_ir&7); + return util::string_format("roxl.l #%d, D%d", m_3bit_qdata_table[(m_cpu_ir>>9)&7], m_cpu_ir&7); } -static void d68000_roxl_r_8(void) +std::string m68k_disassembler::d68000_roxl_r_8() { - sprintf(g_dasm_str, "roxl.b D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("roxl.b D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_roxl_r_16(void) +std::string m68k_disassembler::d68000_roxl_r_16() { - sprintf(g_dasm_str, "roxl.w D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("roxl.w D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_roxl_r_32(void) +std::string m68k_disassembler::d68000_roxl_r_32() { - sprintf(g_dasm_str, "roxl.l D%d, D%d", (g_cpu_ir>>9)&7, g_cpu_ir&7); + return util::string_format("roxl.l D%d, D%d", (m_cpu_ir>>9)&7, m_cpu_ir&7); } -static void d68000_roxl_ea(void) +std::string m68k_disassembler::d68000_roxl_ea() { - sprintf(g_dasm_str, "roxl.w %s", get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("roxl.w %s", get_ea_mode_str_32(m_cpu_ir)); } -static void d68010_rtd(void) +std::string m68k_disassembler::d68010_rtd() { - LIMIT_CPU_TYPES(M68010_PLUS); - sprintf(g_dasm_str, "rtd %s; (1+)", get_imm_str_s16()); - SET_OPCODE_FLAGS(DASMFLAG_STEP_OUT); + auto limit = limit_cpu_types(M68010_PLUS); + if(limit.first) + return limit.second; + m_flags = STEP_OUT; + return util::string_format("rtd %s; (1+)", get_imm_str_s16()); } -static void d68000_rte(void) +std::string m68k_disassembler::d68000_rte() { - sprintf(g_dasm_str, "rte"); - SET_OPCODE_FLAGS(DASMFLAG_STEP_OUT); + m_flags = STEP_OUT; + return util::string_format("rte"); } -static void d68020_rtm(void) +std::string m68k_disassembler::d68020_rtm() { - LIMIT_CPU_TYPES(M68020_ONLY); - sprintf(g_dasm_str, "rtm %c%d; (2+)", BIT_3(g_cpu_ir) ? 'A' : 'D', g_cpu_ir&7); - SET_OPCODE_FLAGS(DASMFLAG_STEP_OUT); + auto limit = limit_cpu_types(M68020_ONLY); + if(limit.first) + return limit.second; + m_flags = STEP_OUT; + return util::string_format("rtm %c%d; (2+)", BIT(m_cpu_ir, 3) ? 'A' : 'D', m_cpu_ir&7); } -static void d68000_rtr(void) +std::string m68k_disassembler::d68000_rtr() { - sprintf(g_dasm_str, "rtr"); - SET_OPCODE_FLAGS(DASMFLAG_STEP_OUT); + m_flags = STEP_OUT; + return util::string_format("rtr"); } -static void d68000_rts(void) +std::string m68k_disassembler::d68000_rts() { - sprintf(g_dasm_str, "rts"); - SET_OPCODE_FLAGS(DASMFLAG_STEP_OUT); + m_flags = STEP_OUT; + return util::string_format("rts"); } -static void d68000_sbcd_rr(void) +std::string m68k_disassembler::d68000_sbcd_rr() { - sprintf(g_dasm_str, "sbcd D%d, D%d", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("sbcd D%d, D%d", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_sbcd_mm(void) +std::string m68k_disassembler::d68000_sbcd_mm() { - sprintf(g_dasm_str, "sbcd -(A%d), -(A%d)", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("sbcd -(A%d), -(A%d)", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_scc(void) +std::string m68k_disassembler::d68000_scc() { - sprintf(g_dasm_str, "s%-2s %s", g_cc[(g_cpu_ir>>8)&0xf], get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("s%-2s %s", m_cc[(m_cpu_ir>>8)&0xf], get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_stop(void) +std::string m68k_disassembler::d68000_stop() { - sprintf(g_dasm_str, "stop %s", get_imm_str_s16()); + return util::string_format("stop %s", get_imm_str_s16()); } -static void d68000_sub_er_8(void) +std::string m68k_disassembler::d68000_sub_er_8() { - sprintf(g_dasm_str, "sub.b %s, D%d", get_ea_mode_str_8(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("sub.b %s, D%d", get_ea_mode_str_8(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_sub_er_16(void) +std::string m68k_disassembler::d68000_sub_er_16() { - sprintf(g_dasm_str, "sub.w %s, D%d", get_ea_mode_str_16(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("sub.w %s, D%d", get_ea_mode_str_16(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_sub_er_32(void) +std::string m68k_disassembler::d68000_sub_er_32() { - sprintf(g_dasm_str, "sub.l %s, D%d", get_ea_mode_str_32(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("sub.l %s, D%d", get_ea_mode_str_32(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_sub_re_8(void) +std::string m68k_disassembler::d68000_sub_re_8() { - sprintf(g_dasm_str, "sub.b D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("sub.b D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_sub_re_16(void) +std::string m68k_disassembler::d68000_sub_re_16() { - sprintf(g_dasm_str, "sub.w D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_16(g_cpu_ir)); + return util::string_format("sub.w D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_sub_re_32(void) +std::string m68k_disassembler::d68000_sub_re_32() { - sprintf(g_dasm_str, "sub.l D%d, %s", (g_cpu_ir>>9)&7, get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("sub.l D%d, %s", (m_cpu_ir>>9)&7, get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_suba_16(void) +std::string m68k_disassembler::d68000_suba_16() { - sprintf(g_dasm_str, "suba.w %s, A%d", get_ea_mode_str_16(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("suba.w %s, A%d", get_ea_mode_str_16(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_suba_32(void) +std::string m68k_disassembler::d68000_suba_32() { - sprintf(g_dasm_str, "suba.l %s, A%d", get_ea_mode_str_32(g_cpu_ir), (g_cpu_ir>>9)&7); + return util::string_format("suba.l %s, A%d", get_ea_mode_str_32(m_cpu_ir), (m_cpu_ir>>9)&7); } -static void d68000_subi_8(void) +std::string m68k_disassembler::d68000_subi_8() { - char* str = get_imm_str_s8(); - sprintf(g_dasm_str, "subi.b %s, %s", str, get_ea_mode_str_8(g_cpu_ir)); + std::string str = get_imm_str_s8(); + return util::string_format("subi.b %s, %s", str, get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_subi_16(void) +std::string m68k_disassembler::d68000_subi_16() { - char* str = get_imm_str_s16(); - sprintf(g_dasm_str, "subi.w %s, %s", str, get_ea_mode_str_16(g_cpu_ir)); + std::string str = get_imm_str_s16(); + return util::string_format("subi.w %s, %s", str, get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_subi_32(void) +std::string m68k_disassembler::d68000_subi_32() { - char* str = get_imm_str_s32(); - sprintf(g_dasm_str, "subi.l %s, %s", str, get_ea_mode_str_32(g_cpu_ir)); + std::string str = get_imm_str_s32(); + return util::string_format("subi.l %s, %s", str, get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_subq_8(void) +std::string m68k_disassembler::d68000_subq_8() { - sprintf(g_dasm_str, "subq.b #%d, %s", g_3bit_qdata_table[(g_cpu_ir>>9)&7], get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("subq.b #%d, %s", m_3bit_qdata_table[(m_cpu_ir>>9)&7], get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_subq_16(void) +std::string m68k_disassembler::d68000_subq_16() { - sprintf(g_dasm_str, "subq.w #%d, %s", g_3bit_qdata_table[(g_cpu_ir>>9)&7], get_ea_mode_str_16(g_cpu_ir)); + return util::string_format("subq.w #%d, %s", m_3bit_qdata_table[(m_cpu_ir>>9)&7], get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_subq_32(void) +std::string m68k_disassembler::d68000_subq_32() { - sprintf(g_dasm_str, "subq.l #%d, %s", g_3bit_qdata_table[(g_cpu_ir>>9)&7], get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("subq.l #%d, %s", m_3bit_qdata_table[(m_cpu_ir>>9)&7], get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_subx_rr_8(void) +std::string m68k_disassembler::d68000_subx_rr_8() { - sprintf(g_dasm_str, "subx.b D%d, D%d", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("subx.b D%d, D%d", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_subx_rr_16(void) +std::string m68k_disassembler::d68000_subx_rr_16() { - sprintf(g_dasm_str, "subx.w D%d, D%d", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("subx.w D%d, D%d", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_subx_rr_32(void) +std::string m68k_disassembler::d68000_subx_rr_32() { - sprintf(g_dasm_str, "subx.l D%d, D%d", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("subx.l D%d, D%d", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_subx_mm_8(void) +std::string m68k_disassembler::d68000_subx_mm_8() { - sprintf(g_dasm_str, "subx.b -(A%d), -(A%d)", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("subx.b -(A%d), -(A%d)", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_subx_mm_16(void) +std::string m68k_disassembler::d68000_subx_mm_16() { - sprintf(g_dasm_str, "subx.w -(A%d), -(A%d)", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("subx.w -(A%d), -(A%d)", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_subx_mm_32(void) +std::string m68k_disassembler::d68000_subx_mm_32() { - sprintf(g_dasm_str, "subx.l -(A%d), -(A%d)", g_cpu_ir&7, (g_cpu_ir>>9)&7); + return util::string_format("subx.l -(A%d), -(A%d)", m_cpu_ir&7, (m_cpu_ir>>9)&7); } -static void d68000_swap(void) +std::string m68k_disassembler::d68000_swap() { - sprintf(g_dasm_str, "swap D%d", g_cpu_ir&7); + return util::string_format("swap D%d", m_cpu_ir&7); } -static void d68000_tas(void) +std::string m68k_disassembler::d68000_tas() { - sprintf(g_dasm_str, "tas %s", get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("tas %s", get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_trap(void) +std::string m68k_disassembler::d68000_trap() { - sprintf(g_dasm_str, "trap #$%x", g_cpu_ir&0xf); + return util::string_format("trap #$%x", m_cpu_ir&0xf); } -static void d68020_trapcc_0(void) +std::string m68k_disassembler::d68020_trapcc_0() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "trap%-2s; (2+)", g_cc[(g_cpu_ir>>8)&0xf]); - SET_OPCODE_FLAGS(DASMFLAG_STEP_OVER); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + m_flags = STEP_OVER; + return util::string_format("trap%-2s; (2+)", m_cc[(m_cpu_ir>>8)&0xf]); } -static void d68020_trapcc_16(void) +std::string m68k_disassembler::d68020_trapcc_16() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "trap%-2s %s; (2+)", g_cc[(g_cpu_ir>>8)&0xf], get_imm_str_u16()); - SET_OPCODE_FLAGS(DASMFLAG_STEP_OVER); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + m_flags = STEP_OVER; + return util::string_format("trap%-2s %s; (2+)", m_cc[(m_cpu_ir>>8)&0xf], get_imm_str_u16()); } -static void d68020_trapcc_32(void) +std::string m68k_disassembler::d68020_trapcc_32() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "trap%-2s %s; (2+)", g_cc[(g_cpu_ir>>8)&0xf], get_imm_str_u32()); - SET_OPCODE_FLAGS(DASMFLAG_STEP_OVER); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + m_flags = STEP_OVER; + return util::string_format("trap%-2s %s; (2+)", m_cc[(m_cpu_ir>>8)&0xf], get_imm_str_u32()); } -static void d68000_trapv(void) +std::string m68k_disassembler::d68000_trapv() { - sprintf(g_dasm_str, "trapv"); - SET_OPCODE_FLAGS(DASMFLAG_STEP_OVER); + m_flags = STEP_OVER; + return util::string_format("trapv"); } -static void d68000_tst_8(void) +std::string m68k_disassembler::d68000_tst_8() { - sprintf(g_dasm_str, "tst.b %s", get_ea_mode_str_8(g_cpu_ir)); + return util::string_format("tst.b %s", get_ea_mode_str_8(m_cpu_ir)); } -static void d68020_tst_pcdi_8(void) +std::string m68k_disassembler::d68020_tst_pcdi_8() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "tst.b %s; (2+)", get_ea_mode_str_8(g_cpu_ir)); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("tst.b %s; (2+)", get_ea_mode_str_8(m_cpu_ir)); } -static void d68020_tst_pcix_8(void) +std::string m68k_disassembler::d68020_tst_pcix_8() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "tst.b %s; (2+)", get_ea_mode_str_8(g_cpu_ir)); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("tst.b %s; (2+)", get_ea_mode_str_8(m_cpu_ir)); } -static void d68020_tst_i_8(void) +std::string m68k_disassembler::d68020_tst_i_8() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "tst.b %s; (2+)", get_ea_mode_str_8(g_cpu_ir)); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("tst.b %s; (2+)", get_ea_mode_str_8(m_cpu_ir)); } -static void d68000_tst_16(void) +std::string m68k_disassembler::d68000_tst_16() { - sprintf(g_dasm_str, "tst.w %s", get_ea_mode_str_16(g_cpu_ir)); + return util::string_format("tst.w %s", get_ea_mode_str_16(m_cpu_ir)); } -static void d68020_tst_a_16(void) +std::string m68k_disassembler::d68020_tst_a_16() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "tst.w %s; (2+)", get_ea_mode_str_16(g_cpu_ir)); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("tst.w %s; (2+)", get_ea_mode_str_16(m_cpu_ir)); } -static void d68020_tst_pcdi_16(void) +std::string m68k_disassembler::d68020_tst_pcdi_16() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "tst.w %s; (2+)", get_ea_mode_str_16(g_cpu_ir)); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("tst.w %s; (2+)", get_ea_mode_str_16(m_cpu_ir)); } -static void d68020_tst_pcix_16(void) +std::string m68k_disassembler::d68020_tst_pcix_16() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "tst.w %s; (2+)", get_ea_mode_str_16(g_cpu_ir)); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("tst.w %s; (2+)", get_ea_mode_str_16(m_cpu_ir)); } -static void d68020_tst_i_16(void) +std::string m68k_disassembler::d68020_tst_i_16() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "tst.w %s; (2+)", get_ea_mode_str_16(g_cpu_ir)); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("tst.w %s; (2+)", get_ea_mode_str_16(m_cpu_ir)); } -static void d68000_tst_32(void) +std::string m68k_disassembler::d68000_tst_32() { - sprintf(g_dasm_str, "tst.l %s", get_ea_mode_str_32(g_cpu_ir)); + return util::string_format("tst.l %s", get_ea_mode_str_32(m_cpu_ir)); } -static void d68020_tst_a_32(void) +std::string m68k_disassembler::d68020_tst_a_32() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "tst.l %s; (2+)", get_ea_mode_str_32(g_cpu_ir)); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("tst.l %s; (2+)", get_ea_mode_str_32(m_cpu_ir)); } -static void d68020_tst_pcdi_32(void) +std::string m68k_disassembler::d68020_tst_pcdi_32() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "tst.l %s; (2+)", get_ea_mode_str_32(g_cpu_ir)); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("tst.l %s; (2+)", get_ea_mode_str_32(m_cpu_ir)); } -static void d68020_tst_pcix_32(void) +std::string m68k_disassembler::d68020_tst_pcix_32() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "tst.l %s; (2+)", get_ea_mode_str_32(g_cpu_ir)); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("tst.l %s; (2+)", get_ea_mode_str_32(m_cpu_ir)); } -static void d68020_tst_i_32(void) +std::string m68k_disassembler::d68020_tst_i_32() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "tst.l %s; (2+)", get_ea_mode_str_32(g_cpu_ir)); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("tst.l %s; (2+)", get_ea_mode_str_32(m_cpu_ir)); } -static void d68000_unlk(void) +std::string m68k_disassembler::d68000_unlk() { - sprintf(g_dasm_str, "unlk A%d", g_cpu_ir&7); + return util::string_format("unlk A%d", m_cpu_ir&7); } -static void d68020_unpk_rr(void) +std::string m68k_disassembler::d68020_unpk_rr() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "unpk D%d, D%d, %s; (2+)", g_cpu_ir&7, (g_cpu_ir>>9)&7, get_imm_str_u16()); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("unpk D%d, D%d, %s; (2+)", m_cpu_ir&7, (m_cpu_ir>>9)&7, get_imm_str_u16()); } -static void d68020_unpk_mm(void) +std::string m68k_disassembler::d68020_unpk_mm() { - LIMIT_CPU_TYPES(M68020_PLUS); - sprintf(g_dasm_str, "unpk -(A%d), -(A%d), %s; (2+)", g_cpu_ir&7, (g_cpu_ir>>9)&7, get_imm_str_u16()); + auto limit = limit_cpu_types(M68020_PLUS); + if(limit.first) + return limit.second; + return util::string_format("unpk -(A%d), -(A%d), %s; (2+)", m_cpu_ir&7, (m_cpu_ir>>9)&7, get_imm_str_u16()); } @@ -3249,54 +2926,48 @@ static void d68020_unpk_mm(void) // PMOVE 3: 011xxxx000000000 // PTEST: 100xxxxxxxxxxxxx // PFLUSHR: 1010000000000000 -static void d68851_p000(void) +std::string m68k_disassembler::d68851_p000() { - char* str; - uint16_t modes = read_imm_16(); + u16 modes = read_imm_16(); // do this after fetching the second PMOVE word so we properly get the 3rd if necessary - str = get_ea_mode_str_32(g_cpu_ir); + std::string str = get_ea_mode_str_32(m_cpu_ir); if ((modes & 0xfde0) == 0x2000) // PLOAD { if (modes & 0x0200) { - sprintf(g_dasm_str, "pload #%d, %s", (modes>>10)&7, str); + return util::string_format("pload #%d, %s", (modes>>10)&7, str); } else { - sprintf(g_dasm_str, "pload %s, #%d", str, (modes>>10)&7); + return util::string_format("pload %s, #%d", str, (modes>>10)&7); } - return; } if ((modes & 0xe200) == 0x2000) // PFLUSH { - sprintf(g_dasm_str, "pflushr %x, %x, %s", modes & 0x1f, (modes>>5)&0xf, str); - return; + return util::string_format("pflushr %x, %x, %s", modes & 0x1f, (modes>>5)&0xf, str); } if (modes == 0xa000) // PFLUSHR { - sprintf(g_dasm_str, "pflushr %s", str); + return util::string_format("pflushr %s", str); } if (modes == 0x2800) // PVALID (FORMAT 1) { - sprintf(g_dasm_str, "pvalid VAL, %s", str); - return; + return util::string_format("pvalid VAL, %s", str); } if ((modes & 0xfff8) == 0x2c00) // PVALID (FORMAT 2) { - sprintf(g_dasm_str, "pvalid A%d, %s", modes & 0xf, str); - return; + return util::string_format("pvalid A%d, %s", modes & 0xf, str); } if ((modes & 0xe000) == 0x8000) // PTEST { - sprintf(g_dasm_str, "ptest #%d, %s", modes & 0x1f, str); - return; + return util::string_format("ptest #%d, %s", modes & 0x1f, str); } switch ((modes>>13) & 0x7) @@ -3307,22 +2978,22 @@ static void d68851_p000(void) { if (modes & 0x0200) { - sprintf(g_dasm_str, "pmovefd %s, %s", g_mmuregs[(modes>>10)&7], str); + return util::string_format("pmovefd %s, %s", m_mmuregs[(modes>>10)&7], str); } else { - sprintf(g_dasm_str, "pmovefd %s, %s", str, g_mmuregs[(modes>>10)&7]); + return util::string_format("pmovefd %s, %s", str, m_mmuregs[(modes>>10)&7]); } } else { if (modes & 0x0200) { - sprintf(g_dasm_str, "pmove %s, %s", g_mmuregs[(modes>>10)&7], str); + return util::string_format("pmove %s, %s", m_mmuregs[(modes>>10)&7], str); } else { - sprintf(g_dasm_str, "pmove %s, %s", str, g_mmuregs[(modes>>10)&7]); + return util::string_format("pmove %s, %s", str, m_mmuregs[(modes>>10)&7]); } } break; @@ -3330,63 +3001,65 @@ static void d68851_p000(void) case 3: // MC68030 to/from status reg if (modes & 0x0200) { - sprintf(g_dasm_str, "pmove mmusr, %s", str); + return util::string_format("pmove mmusr, %s", str); } else { - sprintf(g_dasm_str, "pmove %s, mmusr", str); + return util::string_format("pmove %s, mmusr", str); } break; - default: - sprintf(g_dasm_str, "pmove [unknown form] %s", str); - break; } + return util::string_format("pmove [unknown form] %s", str); } -static void d68851_pbcc16(void) +std::string m68k_disassembler::d68851_pbcc16() { - uint32_t temp_pc = g_cpu_pc; + u32 temp_pc = m_cpu_pc; - sprintf(g_dasm_str, "pb%s %x", g_mmucond[g_cpu_ir&0xf], temp_pc + make_int_16(read_imm_16())); + return util::string_format("pb%s %x", m_mmucond[m_cpu_ir&0xf], temp_pc + make_int_16(read_imm_16())); } -static void d68851_pbcc32(void) +std::string m68k_disassembler::d68851_pbcc32() { - uint32_t temp_pc = g_cpu_pc; + u32 temp_pc = m_cpu_pc; - sprintf(g_dasm_str, "pb%s %x", g_mmucond[g_cpu_ir&0xf], temp_pc + make_int_32(read_imm_32())); + return util::string_format("pb%s %x", m_mmucond[m_cpu_ir&0xf], temp_pc + make_int_32(read_imm_32())); } -static void d68851_pdbcc(void) +std::string m68k_disassembler::d68851_pdbcc() { - uint32_t temp_pc = g_cpu_pc; + u32 temp_pc = m_cpu_pc; uint16_t modes = read_imm_16(); - sprintf(g_dasm_str, "pb%s %x", g_mmucond[modes&0xf], temp_pc + make_int_16(read_imm_16())); + return util::string_format("pb%s %x", m_mmucond[modes&0xf], temp_pc + make_int_16(read_imm_16())); } // PScc: 0000000000xxxxxx -static void d68851_p001(void) +std::string m68k_disassembler::d68851_p001() { - sprintf(g_dasm_str, "MMU 001 group"); + return util::string_format("MMU 001 group"); } // fbcc is 68040 and 68881 -static void d68040_fbcc_16() +std::string m68k_disassembler::d68040_fbcc_16() { - LIMIT_CPU_TYPES(M68030_PLUS); - uint32_t temp_pc = g_cpu_pc; + auto limit = limit_cpu_types(M68030_PLUS); + if(limit.first) + return limit.second; + u32 temp_pc = m_cpu_pc; int16_t disp = make_int_16(read_imm_16()); - sprintf(g_dasm_str, "fb%-s $%x", g_cpcc[g_cpu_ir & 0x3f], temp_pc + disp); + return util::string_format("fb%-s $%x", m_cpcc[m_cpu_ir & 0x3f], temp_pc + disp); } -static void d68040_fbcc_32() +std::string m68k_disassembler::d68040_fbcc_32() { - LIMIT_CPU_TYPES(M68030_PLUS); - uint32_t temp_pc = g_cpu_pc; - uint32_t disp = read_imm_32(); - sprintf(g_dasm_str, "fb%-s $%x", g_cpcc[g_cpu_ir & 0x3f], temp_pc + disp); + auto limit = limit_cpu_types(M68030_PLUS); + if(limit.first) + return limit.second; + u32 temp_pc = m_cpu_pc; + u32 disp = read_imm_32(); + return util::string_format("fb%-s $%x", m_cpcc[m_cpu_ir & 0x3f], temp_pc + disp); } /* ======================================================================== */ @@ -3408,325 +3081,325 @@ static void d68040_fbcc_32() 1 = pc idx */ -static const opcode_struct g_opcode_info[] = +const m68k_disassembler::opcode_struct m68k_disassembler::m_opcode_info[] = { /* opcode handler mask match ea mask */ - {d68000_1010 , 0xf000, 0xa000, 0x000}, - {d68000_1111 , 0xf000, 0xf000, 0x000}, - {d68000_abcd_rr , 0xf1f8, 0xc100, 0x000}, - {d68000_abcd_mm , 0xf1f8, 0xc108, 0x000}, - {d68000_add_er_8 , 0xf1c0, 0xd000, 0xbff}, - {d68000_add_er_16 , 0xf1c0, 0xd040, 0xfff}, - {d68000_add_er_32 , 0xf1c0, 0xd080, 0xfff}, - {d68000_add_re_8 , 0xf1c0, 0xd100, 0x3f8}, - {d68000_add_re_16 , 0xf1c0, 0xd140, 0x3f8}, - {d68000_add_re_32 , 0xf1c0, 0xd180, 0x3f8}, - {d68000_adda_16 , 0xf1c0, 0xd0c0, 0xfff}, - {d68000_adda_32 , 0xf1c0, 0xd1c0, 0xfff}, - {d68000_addi_8 , 0xffc0, 0x0600, 0xbf8}, - {d68000_addi_16 , 0xffc0, 0x0640, 0xbf8}, - {d68000_addi_32 , 0xffc0, 0x0680, 0xbf8}, - {d68000_addq_8 , 0xf1c0, 0x5000, 0xbf8}, - {d68000_addq_16 , 0xf1c0, 0x5040, 0xff8}, - {d68000_addq_32 , 0xf1c0, 0x5080, 0xff8}, - {d68000_addx_rr_8 , 0xf1f8, 0xd100, 0x000}, - {d68000_addx_rr_16 , 0xf1f8, 0xd140, 0x000}, - {d68000_addx_rr_32 , 0xf1f8, 0xd180, 0x000}, - {d68000_addx_mm_8 , 0xf1f8, 0xd108, 0x000}, - {d68000_addx_mm_16 , 0xf1f8, 0xd148, 0x000}, - {d68000_addx_mm_32 , 0xf1f8, 0xd188, 0x000}, - {d68000_and_er_8 , 0xf1c0, 0xc000, 0xbff}, - {d68000_and_er_16 , 0xf1c0, 0xc040, 0xbff}, - {d68000_and_er_32 , 0xf1c0, 0xc080, 0xbff}, - {d68000_and_re_8 , 0xf1c0, 0xc100, 0x3f8}, - {d68000_and_re_16 , 0xf1c0, 0xc140, 0x3f8}, - {d68000_and_re_32 , 0xf1c0, 0xc180, 0x3f8}, - {d68000_andi_to_ccr , 0xffff, 0x023c, 0x000}, - {d68000_andi_to_sr , 0xffff, 0x027c, 0x000}, - {d68000_andi_8 , 0xffc0, 0x0200, 0xbf8}, - {d68000_andi_16 , 0xffc0, 0x0240, 0xbf8}, - {d68000_andi_32 , 0xffc0, 0x0280, 0xbf8}, - {d68000_asr_s_8 , 0xf1f8, 0xe000, 0x000}, - {d68000_asr_s_16 , 0xf1f8, 0xe040, 0x000}, - {d68000_asr_s_32 , 0xf1f8, 0xe080, 0x000}, - {d68000_asr_r_8 , 0xf1f8, 0xe020, 0x000}, - {d68000_asr_r_16 , 0xf1f8, 0xe060, 0x000}, - {d68000_asr_r_32 , 0xf1f8, 0xe0a0, 0x000}, - {d68000_asr_ea , 0xffc0, 0xe0c0, 0x3f8}, - {d68000_asl_s_8 , 0xf1f8, 0xe100, 0x000}, - {d68000_asl_s_16 , 0xf1f8, 0xe140, 0x000}, - {d68000_asl_s_32 , 0xf1f8, 0xe180, 0x000}, - {d68000_asl_r_8 , 0xf1f8, 0xe120, 0x000}, - {d68000_asl_r_16 , 0xf1f8, 0xe160, 0x000}, - {d68000_asl_r_32 , 0xf1f8, 0xe1a0, 0x000}, - {d68000_asl_ea , 0xffc0, 0xe1c0, 0x3f8}, - {d68000_bcc_8 , 0xf000, 0x6000, 0x000}, - {d68000_bcc_16 , 0xf0ff, 0x6000, 0x000}, - {d68020_bcc_32 , 0xf0ff, 0x60ff, 0x000}, - {d68000_bchg_r , 0xf1c0, 0x0140, 0xbf8}, - {d68000_bchg_s , 0xffc0, 0x0840, 0xbf8}, - {d68000_bclr_r , 0xf1c0, 0x0180, 0xbf8}, - {d68000_bclr_s , 0xffc0, 0x0880, 0xbf8}, - {d68020_bfchg , 0xffc0, 0xeac0, 0xa78}, - {d68020_bfclr , 0xffc0, 0xecc0, 0xa78}, - {d68020_bfexts , 0xffc0, 0xebc0, 0xa7b}, - {d68020_bfextu , 0xffc0, 0xe9c0, 0xa7b}, - {d68020_bfffo , 0xffc0, 0xedc0, 0xa7b}, - {d68020_bfins , 0xffc0, 0xefc0, 0xa78}, - {d68020_bfset , 0xffc0, 0xeec0, 0xa78}, - {d68020_bftst , 0xffc0, 0xe8c0, 0xa7b}, - {d68881_ftrap , 0xfff8, 0xf278, 0x000}, - {d68010_bkpt , 0xfff8, 0x4848, 0x000}, - {d68000_bra_8 , 0xff00, 0x6000, 0x000}, - {d68000_bra_16 , 0xffff, 0x6000, 0x000}, - {d68020_bra_32 , 0xffff, 0x60ff, 0x000}, - {d68000_bset_r , 0xf1c0, 0x01c0, 0xbf8}, - {d68000_bset_s , 0xffc0, 0x08c0, 0xbf8}, - {d68000_bsr_8 , 0xff00, 0x6100, 0x000}, - {d68000_bsr_16 , 0xffff, 0x6100, 0x000}, - {d68020_bsr_32 , 0xffff, 0x61ff, 0x000}, - {d68000_btst_r , 0xf1c0, 0x0100, 0xbff}, - {d68000_btst_s , 0xffc0, 0x0800, 0xbfb}, - {d68020_callm , 0xffc0, 0x06c0, 0x27b}, - {d68020_cas_8 , 0xffc0, 0x0ac0, 0x3f8}, - {d68020_cas_16 , 0xffc0, 0x0cc0, 0x3f8}, - {d68020_cas_32 , 0xffc0, 0x0ec0, 0x3f8}, - {d68020_cas2_16 , 0xffff, 0x0cfc, 0x000}, - {d68020_cas2_32 , 0xffff, 0x0efc, 0x000}, - {d68000_chk_16 , 0xf1c0, 0x4180, 0xbff}, - {d68020_chk_32 , 0xf1c0, 0x4100, 0xbff}, - {d68020_chk2_cmp2_8 , 0xffc0, 0x00c0, 0x27b}, - {d68020_chk2_cmp2_16 , 0xffc0, 0x02c0, 0x27b}, - {d68020_chk2_cmp2_32 , 0xffc0, 0x04c0, 0x27b}, - {d68040_cinv , 0xff20, 0xf400, 0x000}, - {d68000_clr_8 , 0xffc0, 0x4200, 0xbf8}, - {d68000_clr_16 , 0xffc0, 0x4240, 0xbf8}, - {d68000_clr_32 , 0xffc0, 0x4280, 0xbf8}, - {d68000_cmp_8 , 0xf1c0, 0xb000, 0xbff}, - {d68000_cmp_16 , 0xf1c0, 0xb040, 0xfff}, - {d68000_cmp_32 , 0xf1c0, 0xb080, 0xfff}, - {d68000_cmpa_16 , 0xf1c0, 0xb0c0, 0xfff}, - {d68000_cmpa_32 , 0xf1c0, 0xb1c0, 0xfff}, - {d68000_cmpi_8 , 0xffc0, 0x0c00, 0xbf8}, - {d68020_cmpi_pcdi_8 , 0xffff, 0x0c3a, 0x000}, - {d68020_cmpi_pcix_8 , 0xffff, 0x0c3b, 0x000}, - {d68000_cmpi_16 , 0xffc0, 0x0c40, 0xbf8}, - {d68020_cmpi_pcdi_16 , 0xffff, 0x0c7a, 0x000}, - {d68020_cmpi_pcix_16 , 0xffff, 0x0c7b, 0x000}, - {d68000_cmpi_32 , 0xffc0, 0x0c80, 0xbf8}, - {d68020_cmpi_pcdi_32 , 0xffff, 0x0cba, 0x000}, - {d68020_cmpi_pcix_32 , 0xffff, 0x0cbb, 0x000}, - {d68000_cmpm_8 , 0xf1f8, 0xb108, 0x000}, - {d68000_cmpm_16 , 0xf1f8, 0xb148, 0x000}, - {d68000_cmpm_32 , 0xf1f8, 0xb188, 0x000}, - {d68020_cpbcc_16 , 0xf1c0, 0xf080, 0x000}, - {d68020_cpbcc_32 , 0xf1c0, 0xf0c0, 0x000}, - {d68020_cpdbcc , 0xf1f8, 0xf048, 0x000}, - {d68020_cpgen , 0xf1c0, 0xf000, 0x000}, - {d68020_cprestore , 0xf1c0, 0xf140, 0x37f}, - {d68020_cpsave , 0xf1c0, 0xf100, 0x2f8}, - {d68020_cpscc , 0xf1c0, 0xf040, 0xbf8}, - {d68020_cptrapcc_0 , 0xf1ff, 0xf07c, 0x000}, - {d68020_cptrapcc_16 , 0xf1ff, 0xf07a, 0x000}, - {d68020_cptrapcc_32 , 0xf1ff, 0xf07b, 0x000}, - {d68040_cpush , 0xff20, 0xf420, 0x000}, - {d68000_dbcc , 0xf0f8, 0x50c8, 0x000}, - {d68000_dbra , 0xfff8, 0x51c8, 0x000}, - {d68000_divs , 0xf1c0, 0x81c0, 0xbff}, - {d68000_divu , 0xf1c0, 0x80c0, 0xbff}, - {d68020_divl , 0xffc0, 0x4c40, 0xbff}, - {d68000_eor_8 , 0xf1c0, 0xb100, 0xbf8}, - {d68000_eor_16 , 0xf1c0, 0xb140, 0xbf8}, - {d68000_eor_32 , 0xf1c0, 0xb180, 0xbf8}, - {d68000_eori_to_ccr , 0xffff, 0x0a3c, 0x000}, - {d68000_eori_to_sr , 0xffff, 0x0a7c, 0x000}, - {d68000_eori_8 , 0xffc0, 0x0a00, 0xbf8}, - {d68000_eori_16 , 0xffc0, 0x0a40, 0xbf8}, - {d68000_eori_32 , 0xffc0, 0x0a80, 0xbf8}, - {d68000_exg_dd , 0xf1f8, 0xc140, 0x000}, - {d68000_exg_aa , 0xf1f8, 0xc148, 0x000}, - {d68000_exg_da , 0xf1f8, 0xc188, 0x000}, - {d68020_extb_32 , 0xfff8, 0x49c0, 0x000}, - {d68000_ext_16 , 0xfff8, 0x4880, 0x000}, - {d68000_ext_32 , 0xfff8, 0x48c0, 0x000}, - {d68040_fpu , 0xffc0, 0xf200, 0x000}, - {d68000_illegal , 0xffff, 0x4afc, 0x000}, - {d68000_jmp , 0xffc0, 0x4ec0, 0x27b}, - {d68000_jsr , 0xffc0, 0x4e80, 0x27b}, - {d68000_lea , 0xf1c0, 0x41c0, 0x27b}, - {d68000_link_16 , 0xfff8, 0x4e50, 0x000}, - {d68020_link_32 , 0xfff8, 0x4808, 0x000}, - {d68000_lsr_s_8 , 0xf1f8, 0xe008, 0x000}, - {d68000_lsr_s_16 , 0xf1f8, 0xe048, 0x000}, - {d68000_lsr_s_32 , 0xf1f8, 0xe088, 0x000}, - {d68000_lsr_r_8 , 0xf1f8, 0xe028, 0x000}, - {d68000_lsr_r_16 , 0xf1f8, 0xe068, 0x000}, - {d68000_lsr_r_32 , 0xf1f8, 0xe0a8, 0x000}, - {d68000_lsr_ea , 0xffc0, 0xe2c0, 0x3f8}, - {d68000_lsl_s_8 , 0xf1f8, 0xe108, 0x000}, - {d68000_lsl_s_16 , 0xf1f8, 0xe148, 0x000}, - {d68000_lsl_s_32 , 0xf1f8, 0xe188, 0x000}, - {d68000_lsl_r_8 , 0xf1f8, 0xe128, 0x000}, - {d68000_lsl_r_16 , 0xf1f8, 0xe168, 0x000}, - {d68000_lsl_r_32 , 0xf1f8, 0xe1a8, 0x000}, - {d68000_lsl_ea , 0xffc0, 0xe3c0, 0x3f8}, - {d68000_move_8 , 0xf000, 0x1000, 0xbff}, - {d68000_move_16 , 0xf000, 0x3000, 0xfff}, - {d68000_move_32 , 0xf000, 0x2000, 0xfff}, - {d68000_movea_16 , 0xf1c0, 0x3040, 0xfff}, - {d68000_movea_32 , 0xf1c0, 0x2040, 0xfff}, - {d68000_move_to_ccr , 0xffc0, 0x44c0, 0xbff}, - {d68010_move_fr_ccr , 0xffc0, 0x42c0, 0xbf8}, - {d68000_move_to_sr , 0xffc0, 0x46c0, 0xbff}, - {d68000_move_fr_sr , 0xffc0, 0x40c0, 0xbf8}, - {d68000_move_to_usp , 0xfff8, 0x4e60, 0x000}, - {d68000_move_fr_usp , 0xfff8, 0x4e68, 0x000}, - {d68010_movec , 0xfffe, 0x4e7a, 0x000}, - {d68000_movem_pd_16 , 0xfff8, 0x48a0, 0x000}, - {d68000_movem_pd_32 , 0xfff8, 0x48e0, 0x000}, - {d68000_movem_re_16 , 0xffc0, 0x4880, 0x2f8}, - {d68000_movem_re_32 , 0xffc0, 0x48c0, 0x2f8}, - {d68000_movem_er_16 , 0xffc0, 0x4c80, 0x37b}, - {d68000_movem_er_32 , 0xffc0, 0x4cc0, 0x37b}, - {d68000_movep_er_16 , 0xf1f8, 0x0108, 0x000}, - {d68000_movep_er_32 , 0xf1f8, 0x0148, 0x000}, - {d68000_movep_re_16 , 0xf1f8, 0x0188, 0x000}, - {d68000_movep_re_32 , 0xf1f8, 0x01c8, 0x000}, - {d68010_moves_8 , 0xffc0, 0x0e00, 0x3f8}, - {d68010_moves_16 , 0xffc0, 0x0e40, 0x3f8}, - {d68010_moves_32 , 0xffc0, 0x0e80, 0x3f8}, - {d68000_moveq , 0xf100, 0x7000, 0x000}, - {d68040_move16_pi_pi , 0xfff8, 0xf620, 0x000}, - {d68040_move16_pi_al , 0xfff8, 0xf600, 0x000}, - {d68040_move16_al_pi , 0xfff8, 0xf608, 0x000}, - {d68040_move16_ai_al , 0xfff8, 0xf610, 0x000}, - {d68040_move16_al_ai , 0xfff8, 0xf618, 0x000}, - {d68000_muls , 0xf1c0, 0xc1c0, 0xbff}, - {d68000_mulu , 0xf1c0, 0xc0c0, 0xbff}, - {d68020_mull , 0xffc0, 0x4c00, 0xbff}, - {d68000_nbcd , 0xffc0, 0x4800, 0xbf8}, - {d68000_neg_8 , 0xffc0, 0x4400, 0xbf8}, - {d68000_neg_16 , 0xffc0, 0x4440, 0xbf8}, - {d68000_neg_32 , 0xffc0, 0x4480, 0xbf8}, - {d68000_negx_8 , 0xffc0, 0x4000, 0xbf8}, - {d68000_negx_16 , 0xffc0, 0x4040, 0xbf8}, - {d68000_negx_32 , 0xffc0, 0x4080, 0xbf8}, - {d68000_nop , 0xffff, 0x4e71, 0x000}, - {d68000_not_8 , 0xffc0, 0x4600, 0xbf8}, - {d68000_not_16 , 0xffc0, 0x4640, 0xbf8}, - {d68000_not_32 , 0xffc0, 0x4680, 0xbf8}, - {d68000_or_er_8 , 0xf1c0, 0x8000, 0xbff}, - {d68000_or_er_16 , 0xf1c0, 0x8040, 0xbff}, - {d68000_or_er_32 , 0xf1c0, 0x8080, 0xbff}, - {d68000_or_re_8 , 0xf1c0, 0x8100, 0x3f8}, - {d68000_or_re_16 , 0xf1c0, 0x8140, 0x3f8}, - {d68000_or_re_32 , 0xf1c0, 0x8180, 0x3f8}, - {d68000_ori_to_ccr , 0xffff, 0x003c, 0x000}, - {d68000_ori_to_sr , 0xffff, 0x007c, 0x000}, - {d68000_ori_8 , 0xffc0, 0x0000, 0xbf8}, - {d68000_ori_16 , 0xffc0, 0x0040, 0xbf8}, - {d68000_ori_32 , 0xffc0, 0x0080, 0xbf8}, - {d68020_pack_rr , 0xf1f8, 0x8140, 0x000}, - {d68020_pack_mm , 0xf1f8, 0x8148, 0x000}, - {d68000_pea , 0xffc0, 0x4840, 0x27b}, - {d68040_pflush , 0xffe0, 0xf500, 0x000}, - {d68000_reset , 0xffff, 0x4e70, 0x000}, - {d68000_ror_s_8 , 0xf1f8, 0xe018, 0x000}, - {d68000_ror_s_16 , 0xf1f8, 0xe058, 0x000}, - {d68000_ror_s_32 , 0xf1f8, 0xe098, 0x000}, - {d68000_ror_r_8 , 0xf1f8, 0xe038, 0x000}, - {d68000_ror_r_16 , 0xf1f8, 0xe078, 0x000}, - {d68000_ror_r_32 , 0xf1f8, 0xe0b8, 0x000}, - {d68000_ror_ea , 0xffc0, 0xe6c0, 0x3f8}, - {d68000_rol_s_8 , 0xf1f8, 0xe118, 0x000}, - {d68000_rol_s_16 , 0xf1f8, 0xe158, 0x000}, - {d68000_rol_s_32 , 0xf1f8, 0xe198, 0x000}, - {d68000_rol_r_8 , 0xf1f8, 0xe138, 0x000}, - {d68000_rol_r_16 , 0xf1f8, 0xe178, 0x000}, - {d68000_rol_r_32 , 0xf1f8, 0xe1b8, 0x000}, - {d68000_rol_ea , 0xffc0, 0xe7c0, 0x3f8}, - {d68000_roxr_s_8 , 0xf1f8, 0xe010, 0x000}, - {d68000_roxr_s_16 , 0xf1f8, 0xe050, 0x000}, - {d68000_roxr_s_32 , 0xf1f8, 0xe090, 0x000}, - {d68000_roxr_r_8 , 0xf1f8, 0xe030, 0x000}, - {d68000_roxr_r_16 , 0xf1f8, 0xe070, 0x000}, - {d68000_roxr_r_32 , 0xf1f8, 0xe0b0, 0x000}, - {d68000_roxr_ea , 0xffc0, 0xe4c0, 0x3f8}, - {d68000_roxl_s_8 , 0xf1f8, 0xe110, 0x000}, - {d68000_roxl_s_16 , 0xf1f8, 0xe150, 0x000}, - {d68000_roxl_s_32 , 0xf1f8, 0xe190, 0x000}, - {d68000_roxl_r_8 , 0xf1f8, 0xe130, 0x000}, - {d68000_roxl_r_16 , 0xf1f8, 0xe170, 0x000}, - {d68000_roxl_r_32 , 0xf1f8, 0xe1b0, 0x000}, - {d68000_roxl_ea , 0xffc0, 0xe5c0, 0x3f8}, - {d68010_rtd , 0xffff, 0x4e74, 0x000}, - {d68000_rte , 0xffff, 0x4e73, 0x000}, - {d68020_rtm , 0xfff0, 0x06c0, 0x000}, - {d68000_rtr , 0xffff, 0x4e77, 0x000}, - {d68000_rts , 0xffff, 0x4e75, 0x000}, - {d68000_sbcd_rr , 0xf1f8, 0x8100, 0x000}, - {d68000_sbcd_mm , 0xf1f8, 0x8108, 0x000}, - {d68000_scc , 0xf0c0, 0x50c0, 0xbf8}, - {d68000_stop , 0xffff, 0x4e72, 0x000}, - {d68000_sub_er_8 , 0xf1c0, 0x9000, 0xbff}, - {d68000_sub_er_16 , 0xf1c0, 0x9040, 0xfff}, - {d68000_sub_er_32 , 0xf1c0, 0x9080, 0xfff}, - {d68000_sub_re_8 , 0xf1c0, 0x9100, 0x3f8}, - {d68000_sub_re_16 , 0xf1c0, 0x9140, 0x3f8}, - {d68000_sub_re_32 , 0xf1c0, 0x9180, 0x3f8}, - {d68000_suba_16 , 0xf1c0, 0x90c0, 0xfff}, - {d68000_suba_32 , 0xf1c0, 0x91c0, 0xfff}, - {d68000_subi_8 , 0xffc0, 0x0400, 0xbf8}, - {d68000_subi_16 , 0xffc0, 0x0440, 0xbf8}, - {d68000_subi_32 , 0xffc0, 0x0480, 0xbf8}, - {d68000_subq_8 , 0xf1c0, 0x5100, 0xbf8}, - {d68000_subq_16 , 0xf1c0, 0x5140, 0xff8}, - {d68000_subq_32 , 0xf1c0, 0x5180, 0xff8}, - {d68000_subx_rr_8 , 0xf1f8, 0x9100, 0x000}, - {d68000_subx_rr_16 , 0xf1f8, 0x9140, 0x000}, - {d68000_subx_rr_32 , 0xf1f8, 0x9180, 0x000}, - {d68000_subx_mm_8 , 0xf1f8, 0x9108, 0x000}, - {d68000_subx_mm_16 , 0xf1f8, 0x9148, 0x000}, - {d68000_subx_mm_32 , 0xf1f8, 0x9188, 0x000}, - {d68000_swap , 0xfff8, 0x4840, 0x000}, - {d68000_tas , 0xffc0, 0x4ac0, 0xbf8}, - {d68000_trap , 0xfff0, 0x4e40, 0x000}, - {d68020_trapcc_0 , 0xf0ff, 0x50fc, 0x000}, - {d68020_trapcc_16 , 0xf0ff, 0x50fa, 0x000}, - {d68020_trapcc_32 , 0xf0ff, 0x50fb, 0x000}, - {d68000_trapv , 0xffff, 0x4e76, 0x000}, - {d68000_tst_8 , 0xffc0, 0x4a00, 0xbf8}, - {d68020_tst_pcdi_8 , 0xffff, 0x4a3a, 0x000}, - {d68020_tst_pcix_8 , 0xffff, 0x4a3b, 0x000}, - {d68020_tst_i_8 , 0xffff, 0x4a3c, 0x000}, - {d68000_tst_16 , 0xffc0, 0x4a40, 0xbf8}, - {d68020_tst_a_16 , 0xfff8, 0x4a48, 0x000}, - {d68020_tst_pcdi_16 , 0xffff, 0x4a7a, 0x000}, - {d68020_tst_pcix_16 , 0xffff, 0x4a7b, 0x000}, - {d68020_tst_i_16 , 0xffff, 0x4a7c, 0x000}, - {d68000_tst_32 , 0xffc0, 0x4a80, 0xbf8}, - {d68020_tst_a_32 , 0xfff8, 0x4a88, 0x000}, - {d68020_tst_pcdi_32 , 0xffff, 0x4aba, 0x000}, - {d68020_tst_pcix_32 , 0xffff, 0x4abb, 0x000}, - {d68020_tst_i_32 , 0xffff, 0x4abc, 0x000}, - {d68000_unlk , 0xfff8, 0x4e58, 0x000}, - {d68020_unpk_rr , 0xf1f8, 0x8180, 0x000}, - {d68020_unpk_mm , 0xf1f8, 0x8188, 0x000}, - {d68851_p000 , 0xffc0, 0xf000, 0x000}, - {d68851_pbcc16 , 0xffc0, 0xf080, 0x000}, - {d68851_pbcc32 , 0xffc0, 0xf0c0, 0x000}, - {d68851_pdbcc , 0xfff8, 0xf048, 0x000}, - {d68851_p001 , 0xffc0, 0xf040, 0x000}, - {d68040_fbcc_16 , 0xffc0, 0xf280, 0x000}, - {d68040_fbcc_32 , 0xffc0, 0xf2c0, 0x000}, + {&m68k_disassembler::d68000_1010 , 0xf000, 0xa000, 0x000}, + {&m68k_disassembler::d68000_1111 , 0xf000, 0xf000, 0x000}, + {&m68k_disassembler::d68000_abcd_rr , 0xf1f8, 0xc100, 0x000}, + {&m68k_disassembler::d68000_abcd_mm , 0xf1f8, 0xc108, 0x000}, + {&m68k_disassembler::d68000_add_er_8 , 0xf1c0, 0xd000, 0xbff}, + {&m68k_disassembler::d68000_add_er_16 , 0xf1c0, 0xd040, 0xfff}, + {&m68k_disassembler::d68000_add_er_32 , 0xf1c0, 0xd080, 0xfff}, + {&m68k_disassembler::d68000_add_re_8 , 0xf1c0, 0xd100, 0x3f8}, + {&m68k_disassembler::d68000_add_re_16 , 0xf1c0, 0xd140, 0x3f8}, + {&m68k_disassembler::d68000_add_re_32 , 0xf1c0, 0xd180, 0x3f8}, + {&m68k_disassembler::d68000_adda_16 , 0xf1c0, 0xd0c0, 0xfff}, + {&m68k_disassembler::d68000_adda_32 , 0xf1c0, 0xd1c0, 0xfff}, + {&m68k_disassembler::d68000_addi_8 , 0xffc0, 0x0600, 0xbf8}, + {&m68k_disassembler::d68000_addi_16 , 0xffc0, 0x0640, 0xbf8}, + {&m68k_disassembler::d68000_addi_32 , 0xffc0, 0x0680, 0xbf8}, + {&m68k_disassembler::d68000_addq_8 , 0xf1c0, 0x5000, 0xbf8}, + {&m68k_disassembler::d68000_addq_16 , 0xf1c0, 0x5040, 0xff8}, + {&m68k_disassembler::d68000_addq_32 , 0xf1c0, 0x5080, 0xff8}, + {&m68k_disassembler::d68000_addx_rr_8 , 0xf1f8, 0xd100, 0x000}, + {&m68k_disassembler::d68000_addx_rr_16 , 0xf1f8, 0xd140, 0x000}, + {&m68k_disassembler::d68000_addx_rr_32 , 0xf1f8, 0xd180, 0x000}, + {&m68k_disassembler::d68000_addx_mm_8 , 0xf1f8, 0xd108, 0x000}, + {&m68k_disassembler::d68000_addx_mm_16 , 0xf1f8, 0xd148, 0x000}, + {&m68k_disassembler::d68000_addx_mm_32 , 0xf1f8, 0xd188, 0x000}, + {&m68k_disassembler::d68000_and_er_8 , 0xf1c0, 0xc000, 0xbff}, + {&m68k_disassembler::d68000_and_er_16 , 0xf1c0, 0xc040, 0xbff}, + {&m68k_disassembler::d68000_and_er_32 , 0xf1c0, 0xc080, 0xbff}, + {&m68k_disassembler::d68000_and_re_8 , 0xf1c0, 0xc100, 0x3f8}, + {&m68k_disassembler::d68000_and_re_16 , 0xf1c0, 0xc140, 0x3f8}, + {&m68k_disassembler::d68000_and_re_32 , 0xf1c0, 0xc180, 0x3f8}, + {&m68k_disassembler::d68000_andi_to_ccr , 0xffff, 0x023c, 0x000}, + {&m68k_disassembler::d68000_andi_to_sr , 0xffff, 0x027c, 0x000}, + {&m68k_disassembler::d68000_andi_8 , 0xffc0, 0x0200, 0xbf8}, + {&m68k_disassembler::d68000_andi_16 , 0xffc0, 0x0240, 0xbf8}, + {&m68k_disassembler::d68000_andi_32 , 0xffc0, 0x0280, 0xbf8}, + {&m68k_disassembler::d68000_asr_s_8 , 0xf1f8, 0xe000, 0x000}, + {&m68k_disassembler::d68000_asr_s_16 , 0xf1f8, 0xe040, 0x000}, + {&m68k_disassembler::d68000_asr_s_32 , 0xf1f8, 0xe080, 0x000}, + {&m68k_disassembler::d68000_asr_r_8 , 0xf1f8, 0xe020, 0x000}, + {&m68k_disassembler::d68000_asr_r_16 , 0xf1f8, 0xe060, 0x000}, + {&m68k_disassembler::d68000_asr_r_32 , 0xf1f8, 0xe0a0, 0x000}, + {&m68k_disassembler::d68000_asr_ea , 0xffc0, 0xe0c0, 0x3f8}, + {&m68k_disassembler::d68000_asl_s_8 , 0xf1f8, 0xe100, 0x000}, + {&m68k_disassembler::d68000_asl_s_16 , 0xf1f8, 0xe140, 0x000}, + {&m68k_disassembler::d68000_asl_s_32 , 0xf1f8, 0xe180, 0x000}, + {&m68k_disassembler::d68000_asl_r_8 , 0xf1f8, 0xe120, 0x000}, + {&m68k_disassembler::d68000_asl_r_16 , 0xf1f8, 0xe160, 0x000}, + {&m68k_disassembler::d68000_asl_r_32 , 0xf1f8, 0xe1a0, 0x000}, + {&m68k_disassembler::d68000_asl_ea , 0xffc0, 0xe1c0, 0x3f8}, + {&m68k_disassembler::d68000_bcc_8 , 0xf000, 0x6000, 0x000}, + {&m68k_disassembler::d68000_bcc_16 , 0xf0ff, 0x6000, 0x000}, + {&m68k_disassembler::d68020_bcc_32 , 0xf0ff, 0x60ff, 0x000}, + {&m68k_disassembler::d68000_bchg_r , 0xf1c0, 0x0140, 0xbf8}, + {&m68k_disassembler::d68000_bchg_s , 0xffc0, 0x0840, 0xbf8}, + {&m68k_disassembler::d68000_bclr_r , 0xf1c0, 0x0180, 0xbf8}, + {&m68k_disassembler::d68000_bclr_s , 0xffc0, 0x0880, 0xbf8}, + {&m68k_disassembler::d68020_bfchg , 0xffc0, 0xeac0, 0xa78}, + {&m68k_disassembler::d68020_bfclr , 0xffc0, 0xecc0, 0xa78}, + {&m68k_disassembler::d68020_bfexts , 0xffc0, 0xebc0, 0xa7b}, + {&m68k_disassembler::d68020_bfextu , 0xffc0, 0xe9c0, 0xa7b}, + {&m68k_disassembler::d68020_bfffo , 0xffc0, 0xedc0, 0xa7b}, + {&m68k_disassembler::d68020_bfins , 0xffc0, 0xefc0, 0xa78}, + {&m68k_disassembler::d68020_bfset , 0xffc0, 0xeec0, 0xa78}, + {&m68k_disassembler::d68020_bftst , 0xffc0, 0xe8c0, 0xa7b}, + {&m68k_disassembler::d68881_ftrap , 0xfff8, 0xf278, 0x000}, + {&m68k_disassembler::d68010_bkpt , 0xfff8, 0x4848, 0x000}, + {&m68k_disassembler::d68000_bra_8 , 0xff00, 0x6000, 0x000}, + {&m68k_disassembler::d68000_bra_16 , 0xffff, 0x6000, 0x000}, + {&m68k_disassembler::d68020_bra_32 , 0xffff, 0x60ff, 0x000}, + {&m68k_disassembler::d68000_bset_r , 0xf1c0, 0x01c0, 0xbf8}, + {&m68k_disassembler::d68000_bset_s , 0xffc0, 0x08c0, 0xbf8}, + {&m68k_disassembler::d68000_bsr_8 , 0xff00, 0x6100, 0x000}, + {&m68k_disassembler::d68000_bsr_16 , 0xffff, 0x6100, 0x000}, + {&m68k_disassembler::d68020_bsr_32 , 0xffff, 0x61ff, 0x000}, + {&m68k_disassembler::d68000_btst_r , 0xf1c0, 0x0100, 0xbff}, + {&m68k_disassembler::d68000_btst_s , 0xffc0, 0x0800, 0xbfb}, + {&m68k_disassembler::d68020_callm , 0xffc0, 0x06c0, 0x27b}, + {&m68k_disassembler::d68020_cas_8 , 0xffc0, 0x0ac0, 0x3f8}, + {&m68k_disassembler::d68020_cas_16 , 0xffc0, 0x0cc0, 0x3f8}, + {&m68k_disassembler::d68020_cas_32 , 0xffc0, 0x0ec0, 0x3f8}, + {&m68k_disassembler::d68020_cas2_16 , 0xffff, 0x0cfc, 0x000}, + {&m68k_disassembler::d68020_cas2_32 , 0xffff, 0x0efc, 0x000}, + {&m68k_disassembler::d68000_chk_16 , 0xf1c0, 0x4180, 0xbff}, + {&m68k_disassembler::d68020_chk_32 , 0xf1c0, 0x4100, 0xbff}, + {&m68k_disassembler::d68020_chk2_cmp2_8 , 0xffc0, 0x00c0, 0x27b}, + {&m68k_disassembler::d68020_chk2_cmp2_16 , 0xffc0, 0x02c0, 0x27b}, + {&m68k_disassembler::d68020_chk2_cmp2_32 , 0xffc0, 0x04c0, 0x27b}, + {&m68k_disassembler::d68040_cinv , 0xff20, 0xf400, 0x000}, + {&m68k_disassembler::d68000_clr_8 , 0xffc0, 0x4200, 0xbf8}, + {&m68k_disassembler::d68000_clr_16 , 0xffc0, 0x4240, 0xbf8}, + {&m68k_disassembler::d68000_clr_32 , 0xffc0, 0x4280, 0xbf8}, + {&m68k_disassembler::d68000_cmp_8 , 0xf1c0, 0xb000, 0xbff}, + {&m68k_disassembler::d68000_cmp_16 , 0xf1c0, 0xb040, 0xfff}, + {&m68k_disassembler::d68000_cmp_32 , 0xf1c0, 0xb080, 0xfff}, + {&m68k_disassembler::d68000_cmpa_16 , 0xf1c0, 0xb0c0, 0xfff}, + {&m68k_disassembler::d68000_cmpa_32 , 0xf1c0, 0xb1c0, 0xfff}, + {&m68k_disassembler::d68000_cmpi_8 , 0xffc0, 0x0c00, 0xbf8}, + {&m68k_disassembler::d68020_cmpi_pcdi_8 , 0xffff, 0x0c3a, 0x000}, + {&m68k_disassembler::d68020_cmpi_pcix_8 , 0xffff, 0x0c3b, 0x000}, + {&m68k_disassembler::d68000_cmpi_16 , 0xffc0, 0x0c40, 0xbf8}, + {&m68k_disassembler::d68020_cmpi_pcdi_16 , 0xffff, 0x0c7a, 0x000}, + {&m68k_disassembler::d68020_cmpi_pcix_16 , 0xffff, 0x0c7b, 0x000}, + {&m68k_disassembler::d68000_cmpi_32 , 0xffc0, 0x0c80, 0xbf8}, + {&m68k_disassembler::d68020_cmpi_pcdi_32 , 0xffff, 0x0cba, 0x000}, + {&m68k_disassembler::d68020_cmpi_pcix_32 , 0xffff, 0x0cbb, 0x000}, + {&m68k_disassembler::d68000_cmpm_8 , 0xf1f8, 0xb108, 0x000}, + {&m68k_disassembler::d68000_cmpm_16 , 0xf1f8, 0xb148, 0x000}, + {&m68k_disassembler::d68000_cmpm_32 , 0xf1f8, 0xb188, 0x000}, + {&m68k_disassembler::d68020_cpbcc_16 , 0xf1c0, 0xf080, 0x000}, + {&m68k_disassembler::d68020_cpbcc_32 , 0xf1c0, 0xf0c0, 0x000}, + {&m68k_disassembler::d68020_cpdbcc , 0xf1f8, 0xf048, 0x000}, + {&m68k_disassembler::d68020_cpgen , 0xf1c0, 0xf000, 0x000}, + {&m68k_disassembler::d68020_cprestore , 0xf1c0, 0xf140, 0x37f}, + {&m68k_disassembler::d68020_cpsave , 0xf1c0, 0xf100, 0x2f8}, + {&m68k_disassembler::d68020_cpscc , 0xf1c0, 0xf040, 0xbf8}, + {&m68k_disassembler::d68020_cptrapcc_0 , 0xf1ff, 0xf07c, 0x000}, + {&m68k_disassembler::d68020_cptrapcc_16 , 0xf1ff, 0xf07a, 0x000}, + {&m68k_disassembler::d68020_cptrapcc_32 , 0xf1ff, 0xf07b, 0x000}, + {&m68k_disassembler::d68040_cpush , 0xff20, 0xf420, 0x000}, + {&m68k_disassembler::d68000_dbcc , 0xf0f8, 0x50c8, 0x000}, + {&m68k_disassembler::d68000_dbra , 0xfff8, 0x51c8, 0x000}, + {&m68k_disassembler::d68000_divs , 0xf1c0, 0x81c0, 0xbff}, + {&m68k_disassembler::d68000_divu , 0xf1c0, 0x80c0, 0xbff}, + {&m68k_disassembler::d68020_divl , 0xffc0, 0x4c40, 0xbff}, + {&m68k_disassembler::d68000_eor_8 , 0xf1c0, 0xb100, 0xbf8}, + {&m68k_disassembler::d68000_eor_16 , 0xf1c0, 0xb140, 0xbf8}, + {&m68k_disassembler::d68000_eor_32 , 0xf1c0, 0xb180, 0xbf8}, + {&m68k_disassembler::d68000_eori_to_ccr , 0xffff, 0x0a3c, 0x000}, + {&m68k_disassembler::d68000_eori_to_sr , 0xffff, 0x0a7c, 0x000}, + {&m68k_disassembler::d68000_eori_8 , 0xffc0, 0x0a00, 0xbf8}, + {&m68k_disassembler::d68000_eori_16 , 0xffc0, 0x0a40, 0xbf8}, + {&m68k_disassembler::d68000_eori_32 , 0xffc0, 0x0a80, 0xbf8}, + {&m68k_disassembler::d68000_exg_dd , 0xf1f8, 0xc140, 0x000}, + {&m68k_disassembler::d68000_exg_aa , 0xf1f8, 0xc148, 0x000}, + {&m68k_disassembler::d68000_exg_da , 0xf1f8, 0xc188, 0x000}, + {&m68k_disassembler::d68020_extb_32 , 0xfff8, 0x49c0, 0x000}, + {&m68k_disassembler::d68000_ext_16 , 0xfff8, 0x4880, 0x000}, + {&m68k_disassembler::d68000_ext_32 , 0xfff8, 0x48c0, 0x000}, + {&m68k_disassembler::d68040_fpu , 0xffc0, 0xf200, 0x000}, + {&m68k_disassembler::d68000_illegal , 0xffff, 0x4afc, 0x000}, + {&m68k_disassembler::d68000_jmp , 0xffc0, 0x4ec0, 0x27b}, + {&m68k_disassembler::d68000_jsr , 0xffc0, 0x4e80, 0x27b}, + {&m68k_disassembler::d68000_lea , 0xf1c0, 0x41c0, 0x27b}, + {&m68k_disassembler::d68000_link_16 , 0xfff8, 0x4e50, 0x000}, + {&m68k_disassembler::d68020_link_32 , 0xfff8, 0x4808, 0x000}, + {&m68k_disassembler::d68000_lsr_s_8 , 0xf1f8, 0xe008, 0x000}, + {&m68k_disassembler::d68000_lsr_s_16 , 0xf1f8, 0xe048, 0x000}, + {&m68k_disassembler::d68000_lsr_s_32 , 0xf1f8, 0xe088, 0x000}, + {&m68k_disassembler::d68000_lsr_r_8 , 0xf1f8, 0xe028, 0x000}, + {&m68k_disassembler::d68000_lsr_r_16 , 0xf1f8, 0xe068, 0x000}, + {&m68k_disassembler::d68000_lsr_r_32 , 0xf1f8, 0xe0a8, 0x000}, + {&m68k_disassembler::d68000_lsr_ea , 0xffc0, 0xe2c0, 0x3f8}, + {&m68k_disassembler::d68000_lsl_s_8 , 0xf1f8, 0xe108, 0x000}, + {&m68k_disassembler::d68000_lsl_s_16 , 0xf1f8, 0xe148, 0x000}, + {&m68k_disassembler::d68000_lsl_s_32 , 0xf1f8, 0xe188, 0x000}, + {&m68k_disassembler::d68000_lsl_r_8 , 0xf1f8, 0xe128, 0x000}, + {&m68k_disassembler::d68000_lsl_r_16 , 0xf1f8, 0xe168, 0x000}, + {&m68k_disassembler::d68000_lsl_r_32 , 0xf1f8, 0xe1a8, 0x000}, + {&m68k_disassembler::d68000_lsl_ea , 0xffc0, 0xe3c0, 0x3f8}, + {&m68k_disassembler::d68000_move_8 , 0xf000, 0x1000, 0xbff}, + {&m68k_disassembler::d68000_move_16 , 0xf000, 0x3000, 0xfff}, + {&m68k_disassembler::d68000_move_32 , 0xf000, 0x2000, 0xfff}, + {&m68k_disassembler::d68000_movea_16 , 0xf1c0, 0x3040, 0xfff}, + {&m68k_disassembler::d68000_movea_32 , 0xf1c0, 0x2040, 0xfff}, + {&m68k_disassembler::d68000_move_to_ccr , 0xffc0, 0x44c0, 0xbff}, + {&m68k_disassembler::d68010_move_fr_ccr , 0xffc0, 0x42c0, 0xbf8}, + {&m68k_disassembler::d68000_move_to_sr , 0xffc0, 0x46c0, 0xbff}, + {&m68k_disassembler::d68000_move_fr_sr , 0xffc0, 0x40c0, 0xbf8}, + {&m68k_disassembler::d68000_move_to_usp , 0xfff8, 0x4e60, 0x000}, + {&m68k_disassembler::d68000_move_fr_usp , 0xfff8, 0x4e68, 0x000}, + {&m68k_disassembler::d68010_movec , 0xfffe, 0x4e7a, 0x000}, + {&m68k_disassembler::d68000_movem_pd_16 , 0xfff8, 0x48a0, 0x000}, + {&m68k_disassembler::d68000_movem_pd_32 , 0xfff8, 0x48e0, 0x000}, + {&m68k_disassembler::d68000_movem_re_16 , 0xffc0, 0x4880, 0x2f8}, + {&m68k_disassembler::d68000_movem_re_32 , 0xffc0, 0x48c0, 0x2f8}, + {&m68k_disassembler::d68000_movem_er_16 , 0xffc0, 0x4c80, 0x37b}, + {&m68k_disassembler::d68000_movem_er_32 , 0xffc0, 0x4cc0, 0x37b}, + {&m68k_disassembler::d68000_movep_er_16 , 0xf1f8, 0x0108, 0x000}, + {&m68k_disassembler::d68000_movep_er_32 , 0xf1f8, 0x0148, 0x000}, + {&m68k_disassembler::d68000_movep_re_16 , 0xf1f8, 0x0188, 0x000}, + {&m68k_disassembler::d68000_movep_re_32 , 0xf1f8, 0x01c8, 0x000}, + {&m68k_disassembler::d68010_moves_8 , 0xffc0, 0x0e00, 0x3f8}, + {&m68k_disassembler::d68010_moves_16 , 0xffc0, 0x0e40, 0x3f8}, + {&m68k_disassembler::d68010_moves_32 , 0xffc0, 0x0e80, 0x3f8}, + {&m68k_disassembler::d68000_moveq , 0xf100, 0x7000, 0x000}, + {&m68k_disassembler::d68040_move16_pi_pi , 0xfff8, 0xf620, 0x000}, + {&m68k_disassembler::d68040_move16_pi_al , 0xfff8, 0xf600, 0x000}, + {&m68k_disassembler::d68040_move16_al_pi , 0xfff8, 0xf608, 0x000}, + {&m68k_disassembler::d68040_move16_ai_al , 0xfff8, 0xf610, 0x000}, + {&m68k_disassembler::d68040_move16_al_ai , 0xfff8, 0xf618, 0x000}, + {&m68k_disassembler::d68000_muls , 0xf1c0, 0xc1c0, 0xbff}, + {&m68k_disassembler::d68000_mulu , 0xf1c0, 0xc0c0, 0xbff}, + {&m68k_disassembler::d68020_mull , 0xffc0, 0x4c00, 0xbff}, + {&m68k_disassembler::d68000_nbcd , 0xffc0, 0x4800, 0xbf8}, + {&m68k_disassembler::d68000_neg_8 , 0xffc0, 0x4400, 0xbf8}, + {&m68k_disassembler::d68000_neg_16 , 0xffc0, 0x4440, 0xbf8}, + {&m68k_disassembler::d68000_neg_32 , 0xffc0, 0x4480, 0xbf8}, + {&m68k_disassembler::d68000_negx_8 , 0xffc0, 0x4000, 0xbf8}, + {&m68k_disassembler::d68000_negx_16 , 0xffc0, 0x4040, 0xbf8}, + {&m68k_disassembler::d68000_negx_32 , 0xffc0, 0x4080, 0xbf8}, + {&m68k_disassembler::d68000_nop , 0xffff, 0x4e71, 0x000}, + {&m68k_disassembler::d68000_not_8 , 0xffc0, 0x4600, 0xbf8}, + {&m68k_disassembler::d68000_not_16 , 0xffc0, 0x4640, 0xbf8}, + {&m68k_disassembler::d68000_not_32 , 0xffc0, 0x4680, 0xbf8}, + {&m68k_disassembler::d68000_or_er_8 , 0xf1c0, 0x8000, 0xbff}, + {&m68k_disassembler::d68000_or_er_16 , 0xf1c0, 0x8040, 0xbff}, + {&m68k_disassembler::d68000_or_er_32 , 0xf1c0, 0x8080, 0xbff}, + {&m68k_disassembler::d68000_or_re_8 , 0xf1c0, 0x8100, 0x3f8}, + {&m68k_disassembler::d68000_or_re_16 , 0xf1c0, 0x8140, 0x3f8}, + {&m68k_disassembler::d68000_or_re_32 , 0xf1c0, 0x8180, 0x3f8}, + {&m68k_disassembler::d68000_ori_to_ccr , 0xffff, 0x003c, 0x000}, + {&m68k_disassembler::d68000_ori_to_sr , 0xffff, 0x007c, 0x000}, + {&m68k_disassembler::d68000_ori_8 , 0xffc0, 0x0000, 0xbf8}, + {&m68k_disassembler::d68000_ori_16 , 0xffc0, 0x0040, 0xbf8}, + {&m68k_disassembler::d68000_ori_32 , 0xffc0, 0x0080, 0xbf8}, + {&m68k_disassembler::d68020_pack_rr , 0xf1f8, 0x8140, 0x000}, + {&m68k_disassembler::d68020_pack_mm , 0xf1f8, 0x8148, 0x000}, + {&m68k_disassembler::d68000_pea , 0xffc0, 0x4840, 0x27b}, + {&m68k_disassembler::d68040_pflush , 0xffe0, 0xf500, 0x000}, + {&m68k_disassembler::d68000_reset , 0xffff, 0x4e70, 0x000}, + {&m68k_disassembler::d68000_ror_s_8 , 0xf1f8, 0xe018, 0x000}, + {&m68k_disassembler::d68000_ror_s_16 , 0xf1f8, 0xe058, 0x000}, + {&m68k_disassembler::d68000_ror_s_32 , 0xf1f8, 0xe098, 0x000}, + {&m68k_disassembler::d68000_ror_r_8 , 0xf1f8, 0xe038, 0x000}, + {&m68k_disassembler::d68000_ror_r_16 , 0xf1f8, 0xe078, 0x000}, + {&m68k_disassembler::d68000_ror_r_32 , 0xf1f8, 0xe0b8, 0x000}, + {&m68k_disassembler::d68000_ror_ea , 0xffc0, 0xe6c0, 0x3f8}, + {&m68k_disassembler::d68000_rol_s_8 , 0xf1f8, 0xe118, 0x000}, + {&m68k_disassembler::d68000_rol_s_16 , 0xf1f8, 0xe158, 0x000}, + {&m68k_disassembler::d68000_rol_s_32 , 0xf1f8, 0xe198, 0x000}, + {&m68k_disassembler::d68000_rol_r_8 , 0xf1f8, 0xe138, 0x000}, + {&m68k_disassembler::d68000_rol_r_16 , 0xf1f8, 0xe178, 0x000}, + {&m68k_disassembler::d68000_rol_r_32 , 0xf1f8, 0xe1b8, 0x000}, + {&m68k_disassembler::d68000_rol_ea , 0xffc0, 0xe7c0, 0x3f8}, + {&m68k_disassembler::d68000_roxr_s_8 , 0xf1f8, 0xe010, 0x000}, + {&m68k_disassembler::d68000_roxr_s_16 , 0xf1f8, 0xe050, 0x000}, + {&m68k_disassembler::d68000_roxr_s_32 , 0xf1f8, 0xe090, 0x000}, + {&m68k_disassembler::d68000_roxr_r_8 , 0xf1f8, 0xe030, 0x000}, + {&m68k_disassembler::d68000_roxr_r_16 , 0xf1f8, 0xe070, 0x000}, + {&m68k_disassembler::d68000_roxr_r_32 , 0xf1f8, 0xe0b0, 0x000}, + {&m68k_disassembler::d68000_roxr_ea , 0xffc0, 0xe4c0, 0x3f8}, + {&m68k_disassembler::d68000_roxl_s_8 , 0xf1f8, 0xe110, 0x000}, + {&m68k_disassembler::d68000_roxl_s_16 , 0xf1f8, 0xe150, 0x000}, + {&m68k_disassembler::d68000_roxl_s_32 , 0xf1f8, 0xe190, 0x000}, + {&m68k_disassembler::d68000_roxl_r_8 , 0xf1f8, 0xe130, 0x000}, + {&m68k_disassembler::d68000_roxl_r_16 , 0xf1f8, 0xe170, 0x000}, + {&m68k_disassembler::d68000_roxl_r_32 , 0xf1f8, 0xe1b0, 0x000}, + {&m68k_disassembler::d68000_roxl_ea , 0xffc0, 0xe5c0, 0x3f8}, + {&m68k_disassembler::d68010_rtd , 0xffff, 0x4e74, 0x000}, + {&m68k_disassembler::d68000_rte , 0xffff, 0x4e73, 0x000}, + {&m68k_disassembler::d68020_rtm , 0xfff0, 0x06c0, 0x000}, + {&m68k_disassembler::d68000_rtr , 0xffff, 0x4e77, 0x000}, + {&m68k_disassembler::d68000_rts , 0xffff, 0x4e75, 0x000}, + {&m68k_disassembler::d68000_sbcd_rr , 0xf1f8, 0x8100, 0x000}, + {&m68k_disassembler::d68000_sbcd_mm , 0xf1f8, 0x8108, 0x000}, + {&m68k_disassembler::d68000_scc , 0xf0c0, 0x50c0, 0xbf8}, + {&m68k_disassembler::d68000_stop , 0xffff, 0x4e72, 0x000}, + {&m68k_disassembler::d68000_sub_er_8 , 0xf1c0, 0x9000, 0xbff}, + {&m68k_disassembler::d68000_sub_er_16 , 0xf1c0, 0x9040, 0xfff}, + {&m68k_disassembler::d68000_sub_er_32 , 0xf1c0, 0x9080, 0xfff}, + {&m68k_disassembler::d68000_sub_re_8 , 0xf1c0, 0x9100, 0x3f8}, + {&m68k_disassembler::d68000_sub_re_16 , 0xf1c0, 0x9140, 0x3f8}, + {&m68k_disassembler::d68000_sub_re_32 , 0xf1c0, 0x9180, 0x3f8}, + {&m68k_disassembler::d68000_suba_16 , 0xf1c0, 0x90c0, 0xfff}, + {&m68k_disassembler::d68000_suba_32 , 0xf1c0, 0x91c0, 0xfff}, + {&m68k_disassembler::d68000_subi_8 , 0xffc0, 0x0400, 0xbf8}, + {&m68k_disassembler::d68000_subi_16 , 0xffc0, 0x0440, 0xbf8}, + {&m68k_disassembler::d68000_subi_32 , 0xffc0, 0x0480, 0xbf8}, + {&m68k_disassembler::d68000_subq_8 , 0xf1c0, 0x5100, 0xbf8}, + {&m68k_disassembler::d68000_subq_16 , 0xf1c0, 0x5140, 0xff8}, + {&m68k_disassembler::d68000_subq_32 , 0xf1c0, 0x5180, 0xff8}, + {&m68k_disassembler::d68000_subx_rr_8 , 0xf1f8, 0x9100, 0x000}, + {&m68k_disassembler::d68000_subx_rr_16 , 0xf1f8, 0x9140, 0x000}, + {&m68k_disassembler::d68000_subx_rr_32 , 0xf1f8, 0x9180, 0x000}, + {&m68k_disassembler::d68000_subx_mm_8 , 0xf1f8, 0x9108, 0x000}, + {&m68k_disassembler::d68000_subx_mm_16 , 0xf1f8, 0x9148, 0x000}, + {&m68k_disassembler::d68000_subx_mm_32 , 0xf1f8, 0x9188, 0x000}, + {&m68k_disassembler::d68000_swap , 0xfff8, 0x4840, 0x000}, + {&m68k_disassembler::d68000_tas , 0xffc0, 0x4ac0, 0xbf8}, + {&m68k_disassembler::d68000_trap , 0xfff0, 0x4e40, 0x000}, + {&m68k_disassembler::d68020_trapcc_0 , 0xf0ff, 0x50fc, 0x000}, + {&m68k_disassembler::d68020_trapcc_16 , 0xf0ff, 0x50fa, 0x000}, + {&m68k_disassembler::d68020_trapcc_32 , 0xf0ff, 0x50fb, 0x000}, + {&m68k_disassembler::d68000_trapv , 0xffff, 0x4e76, 0x000}, + {&m68k_disassembler::d68000_tst_8 , 0xffc0, 0x4a00, 0xbf8}, + {&m68k_disassembler::d68020_tst_pcdi_8 , 0xffff, 0x4a3a, 0x000}, + {&m68k_disassembler::d68020_tst_pcix_8 , 0xffff, 0x4a3b, 0x000}, + {&m68k_disassembler::d68020_tst_i_8 , 0xffff, 0x4a3c, 0x000}, + {&m68k_disassembler::d68000_tst_16 , 0xffc0, 0x4a40, 0xbf8}, + {&m68k_disassembler::d68020_tst_a_16 , 0xfff8, 0x4a48, 0x000}, + {&m68k_disassembler::d68020_tst_pcdi_16 , 0xffff, 0x4a7a, 0x000}, + {&m68k_disassembler::d68020_tst_pcix_16 , 0xffff, 0x4a7b, 0x000}, + {&m68k_disassembler::d68020_tst_i_16 , 0xffff, 0x4a7c, 0x000}, + {&m68k_disassembler::d68000_tst_32 , 0xffc0, 0x4a80, 0xbf8}, + {&m68k_disassembler::d68020_tst_a_32 , 0xfff8, 0x4a88, 0x000}, + {&m68k_disassembler::d68020_tst_pcdi_32 , 0xffff, 0x4aba, 0x000}, + {&m68k_disassembler::d68020_tst_pcix_32 , 0xffff, 0x4abb, 0x000}, + {&m68k_disassembler::d68020_tst_i_32 , 0xffff, 0x4abc, 0x000}, + {&m68k_disassembler::d68000_unlk , 0xfff8, 0x4e58, 0x000}, + {&m68k_disassembler::d68020_unpk_rr , 0xf1f8, 0x8180, 0x000}, + {&m68k_disassembler::d68020_unpk_mm , 0xf1f8, 0x8188, 0x000}, + {&m68k_disassembler::d68851_p000 , 0xffc0, 0xf000, 0x000}, + {&m68k_disassembler::d68851_pbcc16 , 0xffc0, 0xf080, 0x000}, + {&m68k_disassembler::d68851_pbcc32 , 0xffc0, 0xf0c0, 0x000}, + {&m68k_disassembler::d68851_pdbcc , 0xfff8, 0xf048, 0x000}, + {&m68k_disassembler::d68851_p001 , 0xffc0, 0xf040, 0x000}, + {&m68k_disassembler::d68040_fbcc_16 , 0xffc0, 0xf280, 0x000}, + {&m68k_disassembler::d68040_fbcc_32 , 0xffc0, 0xf2c0, 0x000}, {nullptr, 0, 0, 0} }; /* Check if opcode is using a valid ea mode */ -static int valid_ea(uint32_t opcode, uint32_t mask) +bool m68k_disassembler::valid_ea(u32 opcode, u32 mask) { if(mask == 0) - return 1; + return true; switch(opcode & 0x3f) { @@ -3762,15 +3435,14 @@ static int valid_ea(uint32_t opcode, uint32_t mask) case 0x3c: return (mask & 0x004) != 0; } - return 0; - + return false; } /* Used by qsort */ -static int DECL_SPEC compare_nof_true_bits(const void *aptr, const void *bptr) +bool m68k_disassembler::compare_nof_true_bits(const opcode_struct *aptr, const opcode_struct *bptr) { - uint32_t a = ((const opcode_struct*)aptr)->mask; - uint32_t b = ((const opcode_struct*)bptr)->mask; + u32 a = aptr->mask; + u32 b = bptr->mask; a = ((a & 0xAAAA) >> 1) + (a & 0x5555); a = ((a & 0xCCCC) >> 2) + (a & 0x3333); @@ -3782,39 +3454,35 @@ static int DECL_SPEC compare_nof_true_bits(const void *aptr, const void *bptr) b = ((b & 0xF0F0) >> 4) + (b & 0x0F0F); b = ((b & 0xFF00) >> 8) + (b & 0x00FF); - return b - a; /* reversed to get greatest to least sorting */ + return b > a; /* reversed to get greatest to least sorting */ } /* build the opcode handler jump table */ -static void build_opcode_table(void) +void m68k_disassembler::build_opcode_table() { - uint32_t i; - uint32_t opcode; - opcode_struct* ostruct; - opcode_struct opcode_info[ARRAY_LENGTH(g_opcode_info)]; + std::vector opcode_info; + for(unsigned int i=0; m_opcode_info[i].handler; i++) + opcode_info.push_back(m_opcode_info + i); + std::sort(opcode_info.begin(), opcode_info.end(), compare_nof_true_bits); - memcpy(opcode_info, g_opcode_info, sizeof(g_opcode_info)); - qsort((void *)opcode_info, ARRAY_LENGTH(opcode_info)-1, sizeof(opcode_info[0]), compare_nof_true_bits); - - for(i=0;i<0x10000;i++) + for(u32 opcode = 0; opcode != 0x10000; opcode++) { - g_instruction_table[i] = d68000_illegal; /* default to illegal */ - opcode = i; + m_instruction_table[opcode] = &m68k_disassembler::d68000_illegal; /* default to illegal */ /* search through opcode info for a match */ - for(ostruct = opcode_info;ostruct->opcode_handler != nullptr;ostruct++) + for(const opcode_struct *ostruct : opcode_info) { /* match opcode mask and allowed ea modes */ if((opcode & ostruct->mask) == ostruct->match) { /* Handle destination ea for move instructions */ - if((ostruct->opcode_handler == d68000_move_8 || - ostruct->opcode_handler == d68000_move_16 || - ostruct->opcode_handler == d68000_move_32) && - !valid_ea(((opcode>>9)&7) | ((opcode>>3)&0x38), 0xbf8)) - continue; + if((ostruct->handler == &m68k_disassembler::d68000_move_8 || + ostruct->handler == &m68k_disassembler::d68000_move_16 || + ostruct->handler == &m68k_disassembler::d68000_move_32) && + !valid_ea(((opcode>>9)&7) | ((opcode>>3)&0x38), 0xbf8)) + continue; if(valid_ea(opcode, ostruct->ea_mask)) { - g_instruction_table[i] = ostruct->opcode_handler; + m_instruction_table[opcode] = ostruct->handler; break; } } @@ -3828,330 +3496,22 @@ static void build_opcode_table(void) /* ================================= API ================================== */ /* ======================================================================== */ -/* Disasemble one instruction at pc and store in str_buff */ -static unsigned int m68k_disassemble(std::ostream &stream, unsigned int pc, unsigned int cpu_type) +m68k_disassembler::m68k_disassembler(u32 type) : m_cpu_type(type) { - if(!g_initialized) - { - build_opcode_table(); - g_initialized = 1; - } - switch(cpu_type) - { - case M68K_CPU_TYPE_68000: - g_cpu_type = TYPE_68000; - break; - case M68K_CPU_TYPE_68008: - g_cpu_type = TYPE_68008; - break; - case M68K_CPU_TYPE_68010: - g_cpu_type = TYPE_68010; - break; - case M68K_CPU_TYPE_68EC020: - case M68K_CPU_TYPE_68020: - g_cpu_type = TYPE_68020; - break; - case M68K_CPU_TYPE_68EC030: - case M68K_CPU_TYPE_68030: - g_cpu_type = TYPE_68030; - break; - case M68K_CPU_TYPE_68040: - case M68K_CPU_TYPE_68EC040: - case M68K_CPU_TYPE_68LC040: - g_cpu_type = TYPE_68040; - break; - case M68K_CPU_TYPE_FSCPU32: - g_cpu_type = TYPE_68340; - break; - case M68K_CPU_TYPE_COLDFIRE: - g_cpu_type = TYPE_COLDFIRE; - break; - default: - return 0; - } - - g_cpu_pc = pc; - g_helper_str[0] = 0; - g_cpu_ir = read_imm_16(); - g_opcode_type = 0; - g_instruction_table[g_cpu_ir](); - util::stream_format(stream, "%s%s", g_dasm_str, g_helper_str); - return COMBINE_OPCODE_FLAGS(g_cpu_pc - pc); + build_opcode_table(); } -#ifdef UNUSED_FUNCTION -char* m68ki_disassemble_quick(unsigned int pc, unsigned int cpu_type) +u32 m68k_disassembler::opcode_alignment() const { - static char buff[100]; - buff[0] = 0; - m68k_disassemble(buff, pc, cpu_type); - return buff; + return 2; } -#endif -unsigned int m68k_disassemble_raw(std::ostream &stream, unsigned int pc, const unsigned char* opdata, const unsigned char* argdata, unsigned int cpu_type) +offs_t m68k_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - unsigned int result; - - g_rawop = opdata; - g_rawbasepc = pc; - result = m68k_disassemble(stream, pc, cpu_type); - g_rawop = nullptr; - return result; + m_cpu_pc = pc; + m_buffer = &opcodes; + m_cpu_ir = read_imm_16(); + m_flags = 0; + stream << (this->*m_instruction_table[m_cpu_ir])(); + return (m_cpu_pc - pc) | m_flags | SUPPORTED; } - -#ifdef UNUSED_FUNCTION -/* Check if the instruction is a valid one */ -unsigned int m68k_is_valid_instruction(unsigned int instruction, unsigned int cpu_type) -{ - if(!g_initialized) - { - build_opcode_table(); - g_initialized = 1; - } - - instruction &= 0xffff; - if(g_instruction_table[instruction] == d68000_illegal) - return 0; - - switch(cpu_type) - { - case M68K_CPU_TYPE_68000: - case M68K_CPU_TYPE_68008: - if(g_instruction_table[instruction] == d68010_bkpt) - return 0; - if(g_instruction_table[instruction] == d68010_move_fr_ccr) - return 0; - if(g_instruction_table[instruction] == d68010_movec) - return 0; - if(g_instruction_table[instruction] == d68010_moves_8) - return 0; - if(g_instruction_table[instruction] == d68010_moves_16) - return 0; - if(g_instruction_table[instruction] == d68010_moves_32) - return 0; - if(g_instruction_table[instruction] == d68010_rtd) - return 0; - case M68K_CPU_TYPE_68010: - if(g_instruction_table[instruction] == d68020_bcc_32) - return 0; - if(g_instruction_table[instruction] == d68020_bfchg) - return 0; - if(g_instruction_table[instruction] == d68020_bfclr) - return 0; - if(g_instruction_table[instruction] == d68020_bfexts) - return 0; - if(g_instruction_table[instruction] == d68020_bfextu) - return 0; - if(g_instruction_table[instruction] == d68020_bfffo) - return 0; - if(g_instruction_table[instruction] == d68020_bfins) - return 0; - if(g_instruction_table[instruction] == d68020_bfset) - return 0; - if(g_instruction_table[instruction] == d68020_bftst) - return 0; - if(g_instruction_table[instruction] == d68020_bra_32) - return 0; - if(g_instruction_table[instruction] == d68020_bsr_32) - return 0; - if(g_instruction_table[instruction] == d68020_callm) - return 0; - if(g_instruction_table[instruction] == d68020_cas_8) - return 0; - if(g_instruction_table[instruction] == d68020_cas_16) - return 0; - if(g_instruction_table[instruction] == d68020_cas_32) - return 0; - if(g_instruction_table[instruction] == d68020_cas2_16) - return 0; - if(g_instruction_table[instruction] == d68020_cas2_32) - return 0; - if(g_instruction_table[instruction] == d68020_chk_32) - return 0; - if(g_instruction_table[instruction] == d68020_chk2_cmp2_8) - return 0; - if(g_instruction_table[instruction] == d68020_chk2_cmp2_16) - return 0; - if(g_instruction_table[instruction] == d68020_chk2_cmp2_32) - return 0; - if(g_instruction_table[instruction] == d68020_cmpi_pcdi_8) - return 0; - if(g_instruction_table[instruction] == d68020_cmpi_pcix_8) - return 0; - if(g_instruction_table[instruction] == d68020_cmpi_pcdi_16) - return 0; - if(g_instruction_table[instruction] == d68020_cmpi_pcix_16) - return 0; - if(g_instruction_table[instruction] == d68020_cmpi_pcdi_32) - return 0; - if(g_instruction_table[instruction] == d68020_cmpi_pcix_32) - return 0; - if(g_instruction_table[instruction] == d68020_cpbcc_16) - return 0; - if(g_instruction_table[instruction] == d68020_cpbcc_32) - return 0; - if(g_instruction_table[instruction] == d68020_cpdbcc) - return 0; - if(g_instruction_table[instruction] == d68020_cpgen) - return 0; - if(g_instruction_table[instruction] == d68020_cprestore) - return 0; - if(g_instruction_table[instruction] == d68020_cpsave) - return 0; - if(g_instruction_table[instruction] == d68020_cpscc) - return 0; - if(g_instruction_table[instruction] == d68020_cptrapcc_0) - return 0; - if(g_instruction_table[instruction] == d68020_cptrapcc_16) - return 0; - if(g_instruction_table[instruction] == d68020_cptrapcc_32) - return 0; - if(g_instruction_table[instruction] == d68020_divl) - return 0; - if(g_instruction_table[instruction] == d68020_extb_32) - return 0; - if(g_instruction_table[instruction] == d68020_link_32) - return 0; - if(g_instruction_table[instruction] == d68020_mull) - return 0; - if(g_instruction_table[instruction] == d68020_pack_rr) - return 0; - if(g_instruction_table[instruction] == d68020_pack_mm) - return 0; - if(g_instruction_table[instruction] == d68020_rtm) - return 0; - if(g_instruction_table[instruction] == d68020_trapcc_0) - return 0; - if(g_instruction_table[instruction] == d68020_trapcc_16) - return 0; - if(g_instruction_table[instruction] == d68020_trapcc_32) - return 0; - if(g_instruction_table[instruction] == d68020_tst_pcdi_8) - return 0; - if(g_instruction_table[instruction] == d68020_tst_pcix_8) - return 0; - if(g_instruction_table[instruction] == d68020_tst_i_8) - return 0; - if(g_instruction_table[instruction] == d68020_tst_a_16) - return 0; - if(g_instruction_table[instruction] == d68020_tst_pcdi_16) - return 0; - if(g_instruction_table[instruction] == d68020_tst_pcix_16) - return 0; - if(g_instruction_table[instruction] == d68020_tst_i_16) - return 0; - if(g_instruction_table[instruction] == d68020_tst_a_32) - return 0; - if(g_instruction_table[instruction] == d68020_tst_pcdi_32) - return 0; - if(g_instruction_table[instruction] == d68020_tst_pcix_32) - return 0; - if(g_instruction_table[instruction] == d68020_tst_i_32) - return 0; - if(g_instruction_table[instruction] == d68020_unpk_rr) - return 0; - if(g_instruction_table[instruction] == d68020_unpk_mm) - return 0; - if(g_instruction_table[instruction] == d68040_fbcc_16) - return 0; - if(g_instruction_table[instruction] == d68040_fbcc_32) - return 0; - case M68K_CPU_TYPE_68EC020: - case M68K_CPU_TYPE_68020: - case M68K_CPU_TYPE_68030: - case M68K_CPU_TYPE_68EC030: - case M68K_CPU_TYPE_FSCPU32: - case M68K_CPU_TYPE_COLDFIRE: - if(g_instruction_table[instruction] == d68040_cinv) - return 0; - if(g_instruction_table[instruction] == d68040_cpush) - return 0; - if(g_instruction_table[instruction] == d68040_move16_pi_pi) - return 0; - if(g_instruction_table[instruction] == d68040_move16_pi_al) - return 0; - if(g_instruction_table[instruction] == d68040_move16_al_pi) - return 0; - if(g_instruction_table[instruction] == d68040_move16_ai_al) - return 0; - if(g_instruction_table[instruction] == d68040_move16_al_ai) - return 0; - case M68K_CPU_TYPE_68040: - case M68K_CPU_TYPE_68EC040: - case M68K_CPU_TYPE_68LC040: - if(g_instruction_table[instruction] == d68020_cpbcc_16) - return 0; - if(g_instruction_table[instruction] == d68020_cpbcc_32) - return 0; - if(g_instruction_table[instruction] == d68020_cpdbcc) - return 0; - if(g_instruction_table[instruction] == d68020_cpgen) - return 0; - if(g_instruction_table[instruction] == d68020_cprestore) - return 0; - if(g_instruction_table[instruction] == d68020_cpsave) - return 0; - if(g_instruction_table[instruction] == d68020_cpscc) - return 0; - if(g_instruction_table[instruction] == d68020_cptrapcc_0) - return 0; - if(g_instruction_table[instruction] == d68020_cptrapcc_16) - return 0; - if(g_instruction_table[instruction] == d68020_cptrapcc_32) - return 0; - if(g_instruction_table[instruction] == d68040_pflush) - return 0; - } - if(cpu_type != M68K_CPU_TYPE_68020 && cpu_type != M68K_CPU_TYPE_68EC020 && - (g_instruction_table[instruction] == d68020_callm || - g_instruction_table[instruction] == d68020_rtm)) - return 0; - - return 1; -} -#endif - -CPU_DISASSEMBLE( m68000 ) -{ - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_68000); -} - -CPU_DISASSEMBLE( m68008 ) -{ - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_68008); -} - -CPU_DISASSEMBLE( m68010 ) -{ - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_68010); -} - -CPU_DISASSEMBLE( m68020 ) -{ - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_68020); -} - -CPU_DISASSEMBLE( m68030 ) -{ - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_68030); -} - -CPU_DISASSEMBLE( m68040 ) -{ - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_68040); -} - -CPU_DISASSEMBLE( m68340 ) -{ - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_FSCPU32); -} - -CPU_DISASSEMBLE( coldfire ) -{ - return m68k_disassemble_raw(stream, pc, oprom, opram, M68K_CPU_TYPE_COLDFIRE); -} - -/* ======================================================================== */ -/* ============================== END OF FILE ============================= */ -/* ======================================================================== */ diff --git a/src/devices/cpu/m68000/m68kdasm.h b/src/devices/cpu/m68000/m68kdasm.h new file mode 100644 index 00000000000..43dfd144980 --- /dev/null +++ b/src/devices/cpu/m68000/m68kdasm.h @@ -0,0 +1,454 @@ +// license:BSD-3-Clause +// copyright-holders:Karl Stenerud +/* ======================================================================== */ +/* ========================= LICENSING & COPYRIGHT ======================== */ +/* ======================================================================== */ +/* + * MUSASHI + * Version 3.32 + * + * A portable Motorola M680x0 processor emulation engine. + * Copyright Karl Stenerud. All rights reserved. + * + */ + +#ifndef MAME_CPU_M68000_M68KDASM_H +#define MAME_CPU_M68000_M68KDASM_H + +#pragma once + +class m68k_disassembler : public util::disasm_interface +{ +public: + enum { + TYPE_68000 = 1, + TYPE_68008 = 2, + TYPE_68010 = 4, + TYPE_68020 = 8, + TYPE_68030 = 16, + TYPE_68040 = 32, + TYPE_68340 = 64, // (CPU32) + TYPE_COLDFIRE = 128, + }; + + m68k_disassembler(u32 type); + virtual ~m68k_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +protected: + enum { + M68000_ONLY = (TYPE_68000 | TYPE_68008), + M68010_ONLY = TYPE_68010, + M68010_LESS = (TYPE_68000 | TYPE_68008 | TYPE_68010), + M68010_PLUS = (TYPE_68010 | TYPE_68020 | TYPE_68030 | TYPE_68040 | TYPE_68340 | TYPE_COLDFIRE), + M68020_ONLY = (TYPE_68020 | TYPE_68340), + M68020_LESS = (TYPE_68010 | TYPE_68020 | TYPE_68340), + M68020_PLUS = (TYPE_68020 | TYPE_68030 | TYPE_68040 | TYPE_68340 | TYPE_COLDFIRE), + + M68030_ONLY = TYPE_68030, + M68030_LESS = (TYPE_68010 | TYPE_68020 | TYPE_68030 | TYPE_68340 ), + M68030_PLUS = (TYPE_68030 | TYPE_68040), + M68040_PLUS = TYPE_68040, + + COLDFIRE = TYPE_COLDFIRE + }; + + typedef std::string (m68k_disassembler::*opcode_handler)(); + + struct opcode_struct { + opcode_handler handler; /* handler function */ + u32 mask; /* mask on opcode */ + u32 match; /* what to match after masking */ + u32 ea_mask; /* what ea modes are allowed */ + }; + + /* Extension word formats */ + static inline u32 ext_8bit_displacement(u32 A) { return ((A)&0xff); } + static inline u32 ext_full(u32 A) { return BIT(A, 8); } + static inline u32 ext_effective_zero(u32 A) { return (((A)&0xe4) == 0xc4 || ((A)&0xe2) == 0xc0); } + static inline u32 ext_base_register_present(u32 A) { return (!BIT(A, 7)); } + static inline u32 ext_index_register_present(u32 A) { return (!BIT(A, 6)); } + static inline u32 ext_index_register(u32 A) { return (((A)>>12)&7); } + static inline u32 ext_index_scale(u32 A) { return (((A)>>9)&3); } + static inline u32 ext_index_long(u32 A) { return BIT(A, 11); } + static inline u32 ext_index_ar(u32 A) { return BIT(A, 15); } + static inline u32 ext_base_displacement_present(u32 A) { return (((A)&0x30) > 0x10); } + static inline u32 ext_base_displacement_word(u32 A) { return (((A)&0x30) == 0x20); } + static inline u32 ext_base_displacement_long(u32 A) { return (((A)&0x30) == 0x30); } + static inline u32 ext_outer_displacement_present(u32 A) { return (((A)&3) > 1 && ((A)&0x47) < 0x44); } + static inline u32 ext_outer_displacement_word(u32 A) { return (((A)&3) == 2 && ((A)&0x47) < 0x44); } + static inline u32 ext_outer_displacement_long(u32 A) { return (((A)&3) == 3 && ((A)&0x47) < 0x44); } + + static inline s32 sext_7bit_int(u32 value) { return (value & 0x40) ? (value | 0xffffff80) : (value & 0x7f); } + static inline s32 make_int_8(u8 value) { return s8(value); } + static inline s32 make_int_16(u16 value) { return s16(value); } + static inline s32 make_int_32(u32 value) { return s32(value); } + + static std::string make_signed_hex_str_8(u8 val); + static std::string make_signed_hex_str_16(u16 val); + static std::string make_signed_hex_str_32(u32 val); + + inline u32 read_imm_8 (u32 advance) { u32 result = m_buffer->r8 (m_cpu_pc + 1); m_cpu_pc += advance; return result; } + inline u32 read_imm_16(u32 advance) { u32 result = m_buffer->r16(m_cpu_pc); m_cpu_pc += advance; return result; } + inline u32 read_imm_32(u32 advance) { u32 result = m_buffer->r32(m_cpu_pc); m_cpu_pc += advance; return result; } + + inline u32 read_imm_8 () { return read_imm_8 (2); } // 2 to keep alignement + inline u32 read_imm_16() { return read_imm_16(2); } + inline u32 read_imm_32() { return read_imm_32(4); } + + inline u32 peek_imm_8 () { return read_imm_8 (0); } + inline u32 peek_imm_16() { return read_imm_16(0); } + inline u32 peek_imm_32() { return read_imm_32(0); } + + std::string get_imm_str_s(u32 size); + inline std::string get_imm_str_s8 () { return get_imm_str_s(0); } + inline std::string get_imm_str_s16() { return get_imm_str_s(1); } + inline std::string get_imm_str_s32() { return get_imm_str_s(2); } + + std::string get_imm_str_u(u32 size); + inline std::string get_imm_str_u8 () { return get_imm_str_u(0); } + inline std::string get_imm_str_u16() { return get_imm_str_u(1); } + inline std::string get_imm_str_u32() { return get_imm_str_u(2); } + + std::string get_ea_mode_str(u16 instruction, u32 size); + inline std::string get_ea_mode_str_8 (u16 instruction) { return get_ea_mode_str(instruction, 0); } + inline std::string get_ea_mode_str_16(u16 instruction) { return get_ea_mode_str(instruction, 1); } + inline std::string get_ea_mode_str_32(u16 instruction) { return get_ea_mode_str(instruction, 2); } + + inline std::pair limit_cpu_types(u32 allowed); + + std::string d68000_illegal(); + std::string d68000_1010(); + std::string d68000_1111(); + std::string d68000_abcd_rr(); + std::string d68000_abcd_mm(); + std::string d68000_add_er_8(); + std::string d68000_add_er_16(); + std::string d68000_add_er_32(); + std::string d68000_add_re_8(); + std::string d68000_add_re_16(); + std::string d68000_add_re_32(); + std::string d68000_adda_16(); + std::string d68000_adda_32(); + std::string d68000_addi_8(); + std::string d68000_addi_16(); + std::string d68000_addi_32(); + std::string d68000_addq_8(); + std::string d68000_addq_16(); + std::string d68000_addq_32(); + std::string d68000_addx_rr_8(); + std::string d68000_addx_rr_16(); + std::string d68000_addx_rr_32(); + std::string d68000_addx_mm_8(); + std::string d68000_addx_mm_16(); + std::string d68000_addx_mm_32(); + std::string d68000_and_er_8(); + std::string d68000_and_er_16(); + std::string d68000_and_er_32(); + std::string d68000_and_re_8(); + std::string d68000_and_re_16(); + std::string d68000_and_re_32(); + std::string d68000_andi_8(); + std::string d68000_andi_16(); + std::string d68000_andi_32(); + std::string d68000_andi_to_ccr(); + std::string d68000_andi_to_sr(); + std::string d68000_asr_s_8(); + std::string d68000_asr_s_16(); + std::string d68000_asr_s_32(); + std::string d68000_asr_r_8(); + std::string d68000_asr_r_16(); + std::string d68000_asr_r_32(); + std::string d68000_asr_ea(); + std::string d68000_asl_s_8(); + std::string d68000_asl_s_16(); + std::string d68000_asl_s_32(); + std::string d68000_asl_r_8(); + std::string d68000_asl_r_16(); + std::string d68000_asl_r_32(); + std::string d68000_asl_ea(); + std::string d68000_bcc_8(); + std::string d68000_bcc_16(); + std::string d68020_bcc_32(); + std::string d68000_bchg_r(); + std::string d68000_bchg_s(); + std::string d68000_bclr_r(); + std::string d68000_bclr_s(); + std::string d68010_bkpt(); + std::string d68020_bfchg(); + std::string d68020_bfclr(); + std::string d68020_bfexts(); + std::string d68020_bfextu(); + std::string d68020_bfffo(); + std::string d68020_bfins(); + std::string d68020_bfset(); + std::string d68020_bftst(); + std::string d68000_bra_8(); + std::string d68000_bra_16(); + std::string d68020_bra_32(); + std::string d68000_bset_r(); + std::string d68000_bset_s(); + std::string d68000_bsr_8(); + std::string d68000_bsr_16(); + std::string d68020_bsr_32(); + std::string d68000_btst_r(); + std::string d68000_btst_s(); + std::string d68020_callm(); + std::string d68020_cas_8(); + std::string d68020_cas_16(); + std::string d68020_cas_32(); + std::string d68020_cas2_16(); + std::string d68020_cas2_32(); + std::string d68000_chk_16(); + std::string d68020_chk_32(); + std::string d68020_chk2_cmp2_8(); + std::string d68020_chk2_cmp2_16(); + std::string d68020_chk2_cmp2_32(); + std::string d68040_cinv(); + std::string d68000_clr_8(); + std::string d68000_clr_16(); + std::string d68000_clr_32(); + std::string d68000_cmp_8(); + std::string d68000_cmp_16(); + std::string d68000_cmp_32(); + std::string d68000_cmpa_16(); + std::string d68000_cmpa_32(); + std::string d68000_cmpi_8(); + std::string d68020_cmpi_pcdi_8(); + std::string d68020_cmpi_pcix_8(); + std::string d68000_cmpi_16(); + std::string d68020_cmpi_pcdi_16(); + std::string d68020_cmpi_pcix_16(); + std::string d68000_cmpi_32(); + std::string d68020_cmpi_pcdi_32(); + std::string d68020_cmpi_pcix_32(); + std::string d68000_cmpm_8(); + std::string d68000_cmpm_16(); + std::string d68000_cmpm_32(); + std::string d68020_cpbcc_16(); + std::string d68020_cpbcc_32(); + std::string d68020_cpdbcc(); + std::string d68020_cpgen(); + std::string d68020_cprestore(); + std::string d68020_cpsave(); + std::string d68020_cpscc(); + std::string d68020_cptrapcc_0(); + std::string d68020_cptrapcc_16(); + std::string d68020_cptrapcc_32(); + std::string d68040_cpush(); + std::string d68000_dbra(); + std::string d68000_dbcc(); + std::string d68000_divs(); + std::string d68000_divu(); + std::string d68020_divl(); + std::string d68000_eor_8(); + std::string d68000_eor_16(); + std::string d68000_eor_32(); + std::string d68000_eori_8(); + std::string d68000_eori_16(); + std::string d68000_eori_32(); + std::string d68000_eori_to_ccr(); + std::string d68000_eori_to_sr(); + std::string d68000_exg_dd(); + std::string d68000_exg_aa(); + std::string d68000_exg_da(); + std::string d68000_ext_16(); + std::string d68000_ext_32(); + std::string d68020_extb_32(); + std::string d68881_ftrap(); + std::string d68040_fpu(); + std::string d68000_jmp(); + std::string d68000_jsr(); + std::string d68000_lea(); + std::string d68000_link_16(); + std::string d68020_link_32(); + std::string d68000_lsr_s_8(); + std::string d68000_lsr_s_16(); + std::string d68000_lsr_s_32(); + std::string d68000_lsr_r_8(); + std::string d68000_lsr_r_16(); + std::string d68000_lsr_r_32(); + std::string d68000_lsr_ea(); + std::string d68000_lsl_s_8(); + std::string d68000_lsl_s_16(); + std::string d68000_lsl_s_32(); + std::string d68000_lsl_r_8(); + std::string d68000_lsl_r_16(); + std::string d68000_lsl_r_32(); + std::string d68000_lsl_ea(); + std::string d68000_move_8(); + std::string d68000_move_16(); + std::string d68000_move_32(); + std::string d68000_movea_16(); + std::string d68000_movea_32(); + std::string d68000_move_to_ccr(); + std::string d68010_move_fr_ccr(); + std::string d68000_move_fr_sr(); + std::string d68000_move_to_sr(); + std::string d68000_move_fr_usp(); + std::string d68000_move_to_usp(); + std::string d68010_movec(); + std::string d68000_movem_pd_16(); + std::string d68000_movem_pd_32(); + std::string d68000_movem_er_16(); + std::string d68000_movem_er_32(); + std::string d68000_movem_re_16(); + std::string d68000_movem_re_32(); + std::string d68000_movep_re_16(); + std::string d68000_movep_re_32(); + std::string d68000_movep_er_16(); + std::string d68000_movep_er_32(); + std::string d68010_moves_8(); + std::string d68010_moves_16(); + std::string d68010_moves_32(); + std::string d68000_moveq(); + std::string d68040_move16_pi_pi(); + std::string d68040_move16_pi_al(); + std::string d68040_move16_al_pi(); + std::string d68040_move16_ai_al(); + std::string d68040_move16_al_ai(); + std::string d68000_muls(); + std::string d68000_mulu(); + std::string d68020_mull(); + std::string d68000_nbcd(); + std::string d68000_neg_8(); + std::string d68000_neg_16(); + std::string d68000_neg_32(); + std::string d68000_negx_8(); + std::string d68000_negx_16(); + std::string d68000_negx_32(); + std::string d68000_nop(); + std::string d68000_not_8(); + std::string d68000_not_16(); + std::string d68000_not_32(); + std::string d68000_or_er_8(); + std::string d68000_or_er_16(); + std::string d68000_or_er_32(); + std::string d68000_or_re_8(); + std::string d68000_or_re_16(); + std::string d68000_or_re_32(); + std::string d68000_ori_8(); + std::string d68000_ori_16(); + std::string d68000_ori_32(); + std::string d68000_ori_to_ccr(); + std::string d68000_ori_to_sr(); + std::string d68020_pack_rr(); + std::string d68020_pack_mm(); + std::string d68000_pea(); + std::string d68040_pflush(); + std::string d68000_reset(); + std::string d68000_ror_s_8(); + std::string d68000_ror_s_16(); + std::string d68000_ror_s_32(); + std::string d68000_ror_r_8(); + std::string d68000_ror_r_16(); + std::string d68000_ror_r_32(); + std::string d68000_ror_ea(); + std::string d68000_rol_s_8(); + std::string d68000_rol_s_16(); + std::string d68000_rol_s_32(); + std::string d68000_rol_r_8(); + std::string d68000_rol_r_16(); + std::string d68000_rol_r_32(); + std::string d68000_rol_ea(); + std::string d68000_roxr_s_8(); + std::string d68000_roxr_s_16(); + std::string d68000_roxr_s_32(); + std::string d68000_roxr_r_8(); + std::string d68000_roxr_r_16(); + std::string d68000_roxr_r_32(); + std::string d68000_roxr_ea(); + std::string d68000_roxl_s_8(); + std::string d68000_roxl_s_16(); + std::string d68000_roxl_s_32(); + std::string d68000_roxl_r_8(); + std::string d68000_roxl_r_16(); + std::string d68000_roxl_r_32(); + std::string d68000_roxl_ea(); + std::string d68010_rtd(); + std::string d68000_rte(); + std::string d68020_rtm(); + std::string d68000_rtr(); + std::string d68000_rts(); + std::string d68000_sbcd_rr(); + std::string d68000_sbcd_mm(); + std::string d68000_scc(); + std::string d68000_stop(); + std::string d68000_sub_er_8(); + std::string d68000_sub_er_16(); + std::string d68000_sub_er_32(); + std::string d68000_sub_re_8(); + std::string d68000_sub_re_16(); + std::string d68000_sub_re_32(); + std::string d68000_suba_16(); + std::string d68000_suba_32(); + std::string d68000_subi_8(); + std::string d68000_subi_16(); + std::string d68000_subi_32(); + std::string d68000_subq_8(); + std::string d68000_subq_16(); + std::string d68000_subq_32(); + std::string d68000_subx_rr_8(); + std::string d68000_subx_rr_16(); + std::string d68000_subx_rr_32(); + std::string d68000_subx_mm_8(); + std::string d68000_subx_mm_16(); + std::string d68000_subx_mm_32(); + std::string d68000_swap(); + std::string d68000_tas(); + std::string d68000_trap(); + std::string d68020_trapcc_0(); + std::string d68020_trapcc_16(); + std::string d68020_trapcc_32(); + std::string d68000_trapv(); + std::string d68000_tst_8(); + std::string d68020_tst_pcdi_8(); + std::string d68020_tst_pcix_8(); + std::string d68020_tst_i_8(); + std::string d68000_tst_16(); + std::string d68020_tst_a_16(); + std::string d68020_tst_pcdi_16(); + std::string d68020_tst_pcix_16(); + std::string d68020_tst_i_16(); + std::string d68000_tst_32(); + std::string d68020_tst_a_32(); + std::string d68020_tst_pcdi_32(); + std::string d68020_tst_pcix_32(); + std::string d68020_tst_i_32(); + std::string d68000_unlk(); + std::string d68020_unpk_rr(); + std::string d68020_unpk_mm(); + std::string d68851_p000(); + std::string d68851_pbcc16(); + std::string d68851_pbcc32(); + std::string d68851_pdbcc(); + std::string d68851_p001(); + std::string d68040_fbcc_16(); + std::string d68040_fbcc_32(); + + static bool valid_ea(u32 opcode, u32 mask); + static bool compare_nof_true_bits(const opcode_struct *aptr, const opcode_struct *bptr); + void build_opcode_table(); + + + /* used by ops like asr, ror, addq, etc */ + static const u32 m_3bit_qdata_table[8]; + static const u32 m_5bit_data_table[32]; + + static const char *const m_cc[16]; + static const char *const m_cpcc[64]; + static const char *const m_mmuregs[8]; + static const char *const m_mmucond[16]; + + static const opcode_struct m_opcode_info[]; + opcode_handler m_instruction_table[0x10000]; + + const data_buffer *m_buffer; + u32 m_cpu_type, m_cpu_pc, m_flags; + u16 m_cpu_ir; +}; + + +#endif diff --git a/src/devices/cpu/m6805/6805dasm.cpp b/src/devices/cpu/m6805/6805dasm.cpp index e8cca5bf4e3..3f6b2fbb14b 100644 --- a/src/devices/cpu/m6805/6805dasm.cpp +++ b/src/devices/cpu/m6805/6805dasm.cpp @@ -5,56 +5,21 @@ * * Note: this is not the good and proper way to disassemble anything, but it works * + * Secondary note: it actually stopped being not nice a while ago + * * I'm afraid to put my name on it, but I feel obligated: * This code written by Aaron Giles (agiles@sirius.com) for the MAME project * */ #include "emu.h" -#include "m6805.h" - -#include "debugger.h" - -namespace { - -enum class md { - INH, // inherent - BTR, // bit test and relative - BIT, // bit set/clear - REL, // relative - IMM, // immediate - DIR, // direct address - EXT, // extended address - IDX, // indexed - IX1, // indexed + byte offset - IX2 // indexed + word offset -}; - -enum class lvl { - HMOS, - CMOS, - HC -}; - -enum class op_names { - adca, adda, anda, asl, asla, aslx, asr, asra, - asrx, bcc, bclr, bcs, beq, bhcc, bhcs, bhi, - bih, bil, bit, bls, bmc, bmi, bms, bne, - bpl, bra, brclr, brn, brset, bset, bsr, clc, - cli, clr, clra, clrx, cmpa, com, coma, comx, - cpx, dec, deca, decx, eora, ill, inc, inca, - incx, jmp, jsr, lda, ldx, lsr, lsra, lsrx, - mul, neg, nega, negx, nop, ora, rol, rola, - rolx, ror, rora, rorx, rsp, rti, rts, sbca, - sec, sei, sta, stop, stx, suba, swi, tax, - tst, tsta, tstx, txa, wait -}; +#include "6805dasm.h" #define OP(name, mode) { op_names::name, #name, md::mode, lvl::HMOS } #define OPC(name, mode) { op_names::name, #name, md::mode, lvl::CMOS } #define OPHC(name, mode) { op_names::name, #name, md::mode, lvl::HC } #define ILLEGAL { op_names::ill, nullptr, md::INH, lvl::HMOS } -struct { op_names op; char const *name; md mode; lvl level; } const disasm[0x100] = { +const m6805_base_disassembler::info m6805_base_disassembler::disasm[0x100] = { OP (brset,BTR), OP (brclr,BTR), OP (brset,BTR), OP (brclr,BTR), // 00 OP (brset,BTR), OP (brclr,BTR), OP (brset,BTR), OP (brclr,BTR), OP (brset,BTR), OP (brclr,BTR), OP (brset,BTR), OP (brclr,BTR), @@ -121,43 +86,35 @@ struct { op_names op; char const *name; md mode; lvl level; } const disasm[0x100 OP (jmp, IDX), OP (jsr, IDX), OP (ldx, IDX), OP (stx, IDX) }; +m6805_base_disassembler::m6805_base_disassembler(lvl level, std::pair const symbols[], std::size_t symbol_count) : m_level(level), m_symbols(symbols), m_symbol_count(symbol_count) +{ +} + +u32 m6805_base_disassembler::opcode_alignment() const +{ + return 1; +} -template -void format_address( - std::ostream& stream, - T address, - std::pair const symbols[], - std::size_t symbol_count) +template std::string m6805_base_disassembler::address(T offset) const { - auto const symbol= std::lower_bound( - &symbols[0], - &symbols[symbol_count], - address, - [] (auto const &sym, u16 addr) { return sym.first < addr; }); - if ((symbol_count != (symbol - symbols)) && (symbol->first == address)) - stream << symbol->second; + auto const symbol = std::lower_bound(m_symbols, + m_symbols + m_symbol_count, + offset, + [] (auto const &sym, u16 addr) { return sym.first < addr; }); + if ((m_symbol_count != (symbol - m_symbols)) && (symbol->first == offset)) + return symbol->second; else - util::stream_format(stream, "$%0*X", 2 * sizeof(T), address); + return util::string_format("$%0*X", 2 * sizeof(T), offset); } - -offs_t disassemble( - cpu_device *device, - std::ostream &stream, - offs_t pc, - const u8 *oprom, - const u8 *opram, - int options, - lvl level, - std::pair const symbols[], - std::size_t symbol_count) +offs_t m6805_base_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - u8 const code = oprom[0]; + u8 const code = opcodes.r8(pc); - if (!disasm[code].name || (disasm[code].level > level)) + if (!disasm[code].name || (disasm[code].level > m_level)) { util::stream_format(stream, "%-6s$%02X", "fcb", code); - return 1 | DASMFLAG_SUPPORTED; + return 1 | SUPPORTED; } else { @@ -166,11 +123,11 @@ offs_t disassemble( { case op_names::bsr: case op_names::jsr: - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case op_names::rts: case op_names::rti: - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; default: flags = 0; @@ -178,55 +135,46 @@ offs_t disassemble( util::stream_format(stream, "%-6s", disasm[code].name); - int bit; - u16 ea; switch (disasm[code].mode) { case md::INH: // inherent - return 1 | flags | DASMFLAG_SUPPORTED; + return 1 | flags | SUPPORTED; case md::BTR: // bit test and relative branch - bit = (code >> 1) & 7; - util::stream_format(stream, "%d,", bit); - format_address(stream, opram[1], symbols, symbol_count); - util::stream_format(stream, ",$%03X", pc + 3 + s8(opram[2])); - return 3 | flags | DASMFLAG_SUPPORTED; + util::stream_format(stream, "%d, %s, $%03X", (code >> 1) & 7, address(params.r8(pc+1)), pc + 3 + s8(params.r8(pc+2))); + return 3 | flags | SUPPORTED; case md::BIT: // bit test - bit = (code >> 1) & 7; - util::stream_format(stream, "%d,", bit); - format_address(stream, opram[1], symbols, symbol_count); - return 2 | flags | DASMFLAG_SUPPORTED; + util::stream_format(stream, "%d, %s", (code >> 1) & 7, address(params.r8(pc+1))); + return 2 | flags | SUPPORTED; case md::REL: // relative - util::stream_format(stream, "$%03X", pc + 2 + s8(opram[1])); - return 2 | flags | DASMFLAG_SUPPORTED; + util::stream_format(stream, "$%03X", pc + 2 + s8(params.r8(pc+1))); + return 2 | flags | SUPPORTED; case md::IMM: // immediate - util::stream_format(stream, "#$%02X", opram[1]); - return 2 | flags | DASMFLAG_SUPPORTED; + util::stream_format(stream, "#$%02X", params.r8(pc+1)); + return 2 | flags | SUPPORTED; case md::DIR: // direct (zero page address) - format_address(stream, opram[1], symbols, symbol_count); - return 2 | flags | DASMFLAG_SUPPORTED; + util::stream_format(stream, "%s", address(params.r8(pc+1))); + return 2 | flags | SUPPORTED; case md::EXT: // extended (16 bit address) - ea = (opram[1] << 8) + opram[2]; - format_address(stream, ea, symbols, symbol_count); - return 3 | flags | DASMFLAG_SUPPORTED; + util::stream_format(stream, "%s", address(params.r16(pc+1))); + return 3 | flags | SUPPORTED; case md::IDX: // indexed util::stream_format(stream, "(x)"); - return 1 | flags | DASMFLAG_SUPPORTED; + return 1 | flags | SUPPORTED; case md::IX1: // indexed + byte (zero page) - util::stream_format(stream, "(x+$%02X)", opram[1]); - return 2 | flags | DASMFLAG_SUPPORTED; + util::stream_format(stream, "(x+$%02X)", params.r8(pc+1)); + return 2 | flags | SUPPORTED; case md::IX2: // indexed + word (16 bit address) - ea = (opram[1] << 8) + opram[2]; - util::stream_format(stream, "(x+$%04X)", ea); - return 3 | flags | DASMFLAG_SUPPORTED; + util::stream_format(stream, "(x+$%04X)", params.r16(pc+1)); + return 3 | flags | SUPPORTED; } // if we fall off the switch statement something is very wrong @@ -234,48 +182,22 @@ offs_t disassemble( } } -} // anonymous namespace - +m6805_disassembler::m6805_disassembler() : m6805_base_disassembler(lvl::HMOS) +{ +} -offs_t CPU_DISASSEMBLE_NAME(m6805)( - cpu_device *device, - std::ostream &stream, - offs_t pc, - const u8 *oprom, - const u8 *opram, - int options, - std::pair const symbols[], - std::size_t symbol_count) +m6805_disassembler::m6805_disassembler(std::pair const symbols[], std::size_t symbol_count) : m6805_base_disassembler(lvl::HMOS, symbols, symbol_count) { - return disassemble(device, stream, pc, oprom, opram, options, lvl::HMOS, symbols, symbol_count); } -offs_t CPU_DISASSEMBLE_NAME(m146805)( - cpu_device *device, - std::ostream &stream, - offs_t pc, - const u8 *oprom, - const u8 *opram, - int options, - std::pair const symbols[], - std::size_t symbol_count) +m146805_disassembler::m146805_disassembler() : m6805_base_disassembler(lvl::CMOS) { - return disassemble(device, stream, pc, oprom, opram, options, lvl::CMOS, symbols, symbol_count); } -offs_t CPU_DISASSEMBLE_NAME(m68hc05)( - cpu_device *device, - std::ostream &stream, - offs_t pc, - const u8 *oprom, - const u8 *opram, - int options, - std::pair const symbols[], - std::size_t symbol_count) +m68hc05_disassembler::m68hc05_disassembler() : m6805_base_disassembler(lvl::HC) { - return disassemble(device, stream, pc, oprom, opram, options, lvl::HC, symbols, symbol_count); } -CPU_DISASSEMBLE(m6805) { return CPU_DISASSEMBLE_NAME(m6805) (device, stream, pc, oprom, opram, options, nullptr, 0); } -CPU_DISASSEMBLE(m146805) { return CPU_DISASSEMBLE_NAME(m146805)(device, stream, pc, oprom, opram, options, nullptr, 0); } -CPU_DISASSEMBLE(m68hc05) { return CPU_DISASSEMBLE_NAME(m68hc05)(device, stream, pc, oprom, opram, options, nullptr, 0); } +m68hc05_disassembler::m68hc05_disassembler(std::pair const symbols[], std::size_t symbol_count) : m6805_base_disassembler(lvl::HC, symbols, symbol_count) +{ +} diff --git a/src/devices/cpu/m6805/6805dasm.h b/src/devices/cpu/m6805/6805dasm.h new file mode 100644 index 00000000000..95a03afb61c --- /dev/null +++ b/src/devices/cpu/m6805/6805dasm.h @@ -0,0 +1,100 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert, Aaron Giles, Vas Crabb + +// 6805 disassembler interface + +#ifndef MAME_CPU_M6805_6805DASM_H +#define MAME_CPU_M6805_6805DASM_H + +#pragma once + +class m6805_base_disassembler : public util::disasm_interface +{ +public: + enum class lvl { + HMOS, + CMOS, + HC + }; + + m6805_base_disassembler(lvl level, std::pair const symbols[], std::size_t symbol_count); + + m6805_base_disassembler(lvl level) : m6805_base_disassembler(level, nullptr, 0) {} + + virtual ~m6805_base_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum class md { + INH, // inherent + BTR, // bit test and relative + BIT, // bit set/clear + REL, // relative + IMM, // immediate + DIR, // direct address + EXT, // extended address + IDX, // indexed + IX1, // indexed + byte offset + IX2 // indexed + word offset + }; + + enum class op_names { + adca, adda, anda, asl, asla, aslx, asr, asra, + asrx, bcc, bclr, bcs, beq, bhcc, bhcs, bhi, + bih, bil, bit, bls, bmc, bmi, bms, bne, + bpl, bra, brclr, brn, brset, bset, bsr, clc, + cli, clr, clra, clrx, cmpa, com, coma, comx, + cpx, dec, deca, decx, eora, ill, inc, inca, + incx, jmp, jsr, lda, ldx, lsr, lsra, lsrx, + mul, neg, nega, negx, nop, ora, rol, rola, + rolx, ror, rora, rorx, rsp, rti, rts, sbca, + sec, sei, sta, stop, stx, suba, swi, tax, + tst, tsta, tstx, txa, wait + }; + + struct info { + op_names op; + char const *name; + md mode; + lvl level; + }; + + static const info disasm[0x100]; + + lvl m_level; + std::pair const *m_symbols; + std::size_t m_symbol_count; + + template std::string address(T offset) const; +}; + +class m6805_disassembler : public m6805_base_disassembler +{ +public: + m6805_disassembler(); + m6805_disassembler(std::pair const symbols[], std::size_t symbol_count); + template m6805_disassembler(std::pair const (&symbols)[N]) : m6805_disassembler(symbols, N) {} + + virtual ~m6805_disassembler() = default; +}; + +class m146805_disassembler : public m6805_base_disassembler +{ +public: + m146805_disassembler(); + virtual ~m146805_disassembler() = default; +}; + +class m68hc05_disassembler : public m6805_base_disassembler +{ +public: + m68hc05_disassembler(); + m68hc05_disassembler(std::pair const symbols[], std::size_t symbol_count); + template m68hc05_disassembler(std::pair const (&symbols)[N]) : m68hc05_disassembler(symbols, N) {} + virtual ~m68hc05_disassembler() = default; +}; + + +#endif diff --git a/src/devices/cpu/m6805/m6805.cpp b/src/devices/cpu/m6805/m6805.cpp index eb80246e368..48f93719e7a 100644 --- a/src/devices/cpu/m6805/m6805.cpp +++ b/src/devices/cpu/m6805/m6805.cpp @@ -35,6 +35,7 @@ #include "emu.h" #include "m6805.h" #include "m6805defs.h" +#include "6805dasm.h" #include "debugger.h" @@ -409,35 +410,13 @@ void m6805_base_device::interrupt() //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t m6805_base_device::disasm_min_opcode_bytes() const -{ - return 1; -} - - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t m6805_base_device::disasm_max_opcode_bytes() const -{ - return 3; -} - - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t m6805_base_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *m6805_base_device::create_disassembler() { - return CPU_DISASSEMBLE_NAME(m6805)(this, stream, pc, oprom, opram, options); + return new m6805_disassembler; } diff --git a/src/devices/cpu/m6805/m6805.h b/src/devices/cpu/m6805/m6805.h index fb8fc97dee3..9ffe035a730 100644 --- a/src/devices/cpu/m6805/m6805.h +++ b/src/devices/cpu/m6805/m6805.h @@ -119,9 +119,7 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // device_state_interface overrides virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; @@ -362,8 +360,4 @@ protected: #define HD63705_INT_ADCONV 0x07 #define HD63705_INT_NMI 0x08 -CPU_DISASSEMBLE( m6805 ); -CPU_DISASSEMBLE( m146805 ); -CPU_DISASSEMBLE( m68hc05 ); - #endif // MAME_CPU_M6805_M6805_H diff --git a/src/devices/cpu/m6805/m6805defs.h b/src/devices/cpu/m6805/m6805defs.h index 670beda2683..1e5d8c6e7fb 100644 --- a/src/devices/cpu/m6805/m6805defs.h +++ b/src/devices/cpu/m6805/m6805defs.h @@ -116,73 +116,4 @@ inline void m6805_base_device::skipbyte() { rdop_arg(PC++); } /* Macros for branch instructions */ #define BRANCH(f) do { u8 t; immbyte(t); if (bool(f) == bool(C)) PC += SIGNED(t); } while (false) -offs_t CPU_DISASSEMBLE_NAME(m146805)( - cpu_device *device, - std::ostream &stream, - offs_t pc, - const u8 *oprom, - const u8 *opram, - int options, - std::pair const symbols[], - std::size_t symbol_count); - -offs_t CPU_DISASSEMBLE_NAME(m68hc05)( - cpu_device *device, - std::ostream &stream, - offs_t pc, - const u8 *oprom, - const u8 *opram, - int options, - std::pair const symbols[], - std::size_t symbol_count); - -offs_t CPU_DISASSEMBLE_NAME(m6805)( - cpu_device *device, - std::ostream &stream, - offs_t pc, - const u8 *oprom, - const u8 *opram, - int options, - std::pair const symbols[], - std::size_t symbol_count); - -template -inline offs_t CPU_DISASSEMBLE_NAME(m6805)( - cpu_device *device, - std::ostream &stream, - offs_t pc, - const u8 *oprom, - const u8 *opram, - int options, - std::pair const (&symbols)[N]) -{ - return CPU_DISASSEMBLE_NAME(m6805)(device, stream, pc, oprom, opram, options, symbols, N); -} - -template -inline offs_t CPU_DISASSEMBLE_NAME(m146805)( - cpu_device *device, - std::ostream &stream, - offs_t pc, - const u8 *oprom, - const u8 *opram, - int options, - std::pair const (&symbols)[N]) -{ - return CPU_DISASSEMBLE_NAME(m146805)(device, stream, pc, oprom, opram, options, symbols, N); -} - -template -inline offs_t CPU_DISASSEMBLE_NAME(m68hc05)( - cpu_device *device, - std::ostream &stream, - offs_t pc, - const u8 *oprom, - const u8 *opram, - int options, - std::pair const (&symbols)[N]) -{ - return CPU_DISASSEMBLE_NAME(m68hc05)(device, stream, pc, oprom, opram, options, symbols, N); -} - #endif // MAME_CPU_M6805_M6805DEFS_H diff --git a/src/devices/cpu/m6805/m68705.cpp b/src/devices/cpu/m6805/m68705.cpp index ba4dae3a39f..08e40e41d9a 100644 --- a/src/devices/cpu/m6805/m68705.cpp +++ b/src/devices/cpu/m6805/m68705.cpp @@ -3,6 +3,7 @@ #include "emu.h" #include "m68705.h" #include "m6805defs.h" +#include "6805dasm.h" /**************************************************************************** * Configurable logging @@ -697,14 +698,9 @@ void m68705p_device::device_start() state_add(M68705_MOR, "MOR", get_user_rom()[0x0784]).mask(0xff); } -offs_t m68705p_device::disasm_disassemble( - std::ostream &stream, - offs_t pc, - const uint8_t *oprom, - const uint8_t *opram, - uint32_t options) +util::disasm_interface *m68705p_device::create_disassembler() { - return CPU_DISASSEMBLE_NAME(m6805)(this, stream, pc, oprom, opram, options, m68705p_syms); + return new m6805_disassembler(m68705p_syms); } @@ -776,14 +772,9 @@ void m68705u_device::device_start() // TODO: MISC register } -offs_t m68705u_device::disasm_disassemble( - std::ostream &stream, - offs_t pc, - const uint8_t *oprom, - const uint8_t *opram, - uint32_t options) +util::disasm_interface *m68705u_device::create_disassembler() { - return CPU_DISASSEMBLE_NAME(m6805)(this, stream, pc, oprom, opram, options, m68705u_syms); + return new m6805_disassembler(m68705u_syms); } @@ -834,17 +825,11 @@ void m68705r_device::device_start() // TODO: ADC } -offs_t m68705r_device::disasm_disassemble( - std::ostream &stream, - offs_t pc, - const uint8_t *oprom, - const uint8_t *opram, - uint32_t options) +util::disasm_interface *m68705r_device::create_disassembler() { - return CPU_DISASSEMBLE_NAME(m6805)(this, stream, pc, oprom, opram, options, m68705r_syms); + return new m6805_disassembler(m68705r_syms); } - /**************************************************************************** * M68705P3 device ****************************************************************************/ diff --git a/src/devices/cpu/m6805/m68705.h b/src/devices/cpu/m6805/m68705.h index aaa2f88d693..08701917b47 100644 --- a/src/devices/cpu/m6805/m68705.h +++ b/src/devices/cpu/m6805/m68705.h @@ -202,12 +202,7 @@ protected: virtual void device_start() override; - virtual offs_t disasm_disassemble( - std::ostream &stream, - offs_t pc, - const uint8_t *oprom, - const uint8_t *opram, - uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; }; @@ -240,12 +235,7 @@ protected: virtual void device_start() override; - virtual offs_t disasm_disassemble( - std::ostream &stream, - offs_t pc, - const uint8_t *oprom, - const uint8_t *opram, - uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; }; @@ -268,12 +258,7 @@ protected: virtual void device_start() override; - virtual offs_t disasm_disassemble( - std::ostream &stream, - offs_t pc, - const uint8_t *oprom, - const uint8_t *opram, - uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; }; diff --git a/src/devices/cpu/m6805/m68hc05.cpp b/src/devices/cpu/m6805/m68hc05.cpp index 90575e98ab2..24580270a9c 100644 --- a/src/devices/cpu/m6805/m68hc05.cpp +++ b/src/devices/cpu/m6805/m68hc05.cpp @@ -18,6 +18,7 @@ certain value. #include "emu.h" #include "m68hc05.h" #include "m6805defs.h" +#include "6805dasm.h" /**************************************************************************** @@ -541,15 +542,9 @@ u64 m68hc05_device::execute_cycles_to_clocks(u64 cycles) const return cycles * 2; } - -offs_t m68hc05_device::disasm_disassemble( - std::ostream &stream, - offs_t pc, - const u8 *oprom, - const u8 *opram, - u32 options) +util::disasm_interface *m68hc05_device::create_disassembler() { - return CPU_DISASSEMBLE_NAME(m68hc05)(this, stream, pc, oprom, opram, options); + return new m68hc05_disassembler; } @@ -777,14 +772,9 @@ void m68hc05c4_device::device_start() } -offs_t m68hc05c4_device::disasm_disassemble( - std::ostream &stream, - offs_t pc, - const u8 *oprom, - const u8 *opram, - u32 options) +util::disasm_interface *m68hc05c4_device::create_disassembler() { - return CPU_DISASSEMBLE_NAME(m68hc05)(this, stream, pc, oprom, opram, options, m68hc05c4_syms); + return new m68hc05_disassembler(m68hc05c4_syms); } @@ -845,15 +835,10 @@ void m68hc05c8_device::device_start() } -offs_t m68hc05c8_device::disasm_disassemble( - std::ostream &stream, - offs_t pc, - const u8 *oprom, - const u8 *opram, - u32 options) +util::disasm_interface *m68hc05c8_device::create_disassembler() { // same I/O registers as MC68HC05C4 - return CPU_DISASSEMBLE_NAME(m68hc05)(this, stream, pc, oprom, opram, options, m68hc05c4_syms); + return new m68hc05_disassembler(m68hc05c4_syms); } @@ -937,12 +922,7 @@ void m68hc705c8a_device::device_reset() } -offs_t m68hc705c8a_device::disasm_disassemble( - std::ostream &stream, - offs_t pc, - const u8 *oprom, - const u8 *opram, - u32 options) +util::disasm_interface *m68hc705c8a_device::create_disassembler() { - return CPU_DISASSEMBLE_NAME(m68hc05)(this, stream, pc, oprom, opram, options, m68hc705c8a_syms); + return new m68hc05_disassembler(m68hc705c8a_syms); } diff --git a/src/devices/cpu/m6805/m68hc05.h b/src/devices/cpu/m6805/m68hc05.h index db61afc8b60..355a675d803 100644 --- a/src/devices/cpu/m6805/m68hc05.h +++ b/src/devices/cpu/m6805/m68hc05.h @@ -138,12 +138,7 @@ protected: virtual u64 execute_clocks_to_cycles(u64 clocks) const override; virtual u64 execute_cycles_to_clocks(u64 cycles) const override; - virtual offs_t disasm_disassemble( - std::ostream &stream, - offs_t pc, - const u8 *oprom, - const uint8_t *opram, - u32 options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void interrupt() override; virtual bool test_il() override; @@ -229,12 +224,7 @@ protected: virtual void device_start() override; - virtual offs_t disasm_disassemble( - std::ostream &stream, - offs_t pc, - const u8 *oprom, - const u8 *opram, - u32 options) override; + virtual util::disasm_interface *create_disassembler() override; }; @@ -250,12 +240,7 @@ protected: virtual void device_start() override; - virtual offs_t disasm_disassemble( - std::ostream &stream, - offs_t pc, - const u8 *oprom, - const u8 *opram, - u32 options) override; + virtual util::disasm_interface *create_disassembler() override; }; @@ -274,12 +259,7 @@ protected: virtual void device_start() override; virtual void device_reset() override; - virtual offs_t disasm_disassemble( - std::ostream &stream, - offs_t pc, - const u8 *oprom, - const u8 *opram, - u32 options) override; + virtual util::disasm_interface *create_disassembler() override; }; diff --git a/src/devices/cpu/m6809/6x09dasm.cpp b/src/devices/cpu/m6809/6x09dasm.cpp index 1b07fb3c92b..3df936df070 100644 --- a/src/devices/cpu/m6809/6x09dasm.cpp +++ b/src/devices/cpu/m6809/6x09dasm.cpp @@ -27,118 +27,41 @@ *****************************************************************************/ #include "emu.h" -#include "debugger.h" +#include "6x09dasm.h" -enum m6x09_addressing_mode -{ - INH, // Inherent - PSHS, PSHU, // Push - PULS, PULU, // Pull - DIR, // Direct - DIR_IM, // Direct in memory (6309 only) - IND, // Indexed - REL, // Relative (8 bit) - LREL, // Long relative (16 bit) - EXT, // Extended - IMM, // Immediate - IMM_RR, // Register-to-register - IMM_BW, // Bitwise operations (6309 only) - IMM_TFM, // Transfer from memory (6309 only) - PG1, // Switch to page 1 opcodes - PG2 // Switch to page 2 opcodes -}; -// General, or 6309 only? -enum m6x09_instruction_level -{ - M6x09_GENERAL, - HD6309_EXCLUSIVE -}; +const char *const m6x09_base_disassembler::m6x09_regs[5] = { "X", "Y", "U", "S", "PC" }; -// Opcode structure -class opcodeinfo -{ -public: - constexpr opcodeinfo(uint16_t opcode, uint8_t length, const char *name, m6x09_addressing_mode mode, m6x09_instruction_level level, unsigned flags = 0) - : m_opcode(opcode), m_length(length), m_mode(mode), m_level(level), m_flags(flags), m_name(name) - { - } +const char *const m6x09_base_disassembler::m6x09_btwregs[5] = { "CC", "A", "B", "inv" }; - uint16_t opcode() const { return m_opcode; } - uint8_t length() const { return m_length; } - m6x09_addressing_mode mode() const { return m_mode; } - m6x09_instruction_level level() const { return m_level; } - unsigned flags() const { return m_flags; } - const char *name() const { return m_name; } - -private: - uint16_t m_opcode; // 8-bit opcode value - uint8_t m_length; // Opcode length in bytes - m6x09_addressing_mode m_mode : 6; // Addressing mode - m6x09_instruction_level m_level : 2; // General, or 6309 only? - unsigned m_flags; // Disassembly flags - const char * m_name; // Opcode name -}; -static const char *const m6x09_regs[5] = { "X", "Y", "U", "S", "PC" }; - -static const char *const m6x09_btwregs[5] = { "CC", "A", "B", "inv" }; - -static const char *const hd6309_tfmregs[16] = { - "D", "X", "Y", "U", "S", "inv", "inv", "inv", +const char *const m6x09_base_disassembler::hd6309_tfmregs[16] = { + "D", "X", "Y", "U", "S", "inv", "inv", "inv", "inv", "inv", "inv", "inv", "inv", "inv", "inv", "inv" }; -static const char *const tfm_s[] = { "%s+,%s+", "%s-,%s-", "%s+,%s", "%s,%s+" }; +const char *const m6x09_base_disassembler::tfm_s[] = { "%s+,%s+", "%s-,%s-", "%s+,%s", "%s,%s+" }; //************************************************************************** // BASE CLASS //************************************************************************** -// ======================> m6x09_disassembler_base - -// base class for M6809/HD6309/Konami disassemblers -namespace +u32 m6x09_base_disassembler::opcode_alignment() const { - class m6x09_disassembler_base - { - public: - m6x09_disassembler_base(const opcodeinfo *opcodes, size_t opcode_count, m6x09_instruction_level level) - : m_opcodes(opcodes, opcode_count), m_level(level) - { - } - - offs_t disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram); - - protected: - virtual void indirect(std::ostream &stream, uint8_t pb, const uint8_t *opram, int &p) = 0; - virtual void register_register(std::ostream &stream, uint8_t pb) = 0; - - private: - util::contiguous_sequence_wrapper m_opcodes; - m6x09_instruction_level m_level; - - const opcodeinfo *fetch_opcode(const uint8_t *oprom, int &p); - - void assert_hd6309_exclusive() - { - if (m_level < HD6309_EXCLUSIVE) - throw false; - } - }; + return 1; } //------------------------------------------------- // fetch_opcode //------------------------------------------------- -const opcodeinfo *m6x09_disassembler_base::fetch_opcode(const uint8_t *oprom, int &p) +const m6x09_base_disassembler::opcodeinfo *m6x09_base_disassembler::fetch_opcode(const data_buffer &opcodes, offs_t &p) { uint16_t page = 0; const opcodeinfo *op = nullptr; while(!op) { // retrieve the opcode - uint16_t opcode = page | oprom[p++]; + uint16_t opcode = page | opcodes.r8(p++); // perform the lookup auto iter = std::find_if( @@ -179,29 +102,28 @@ const opcodeinfo *m6x09_disassembler_base::fetch_opcode(const uint8_t *oprom, in // disassemble - core of the disassembler //------------------------------------------------- -offs_t m6x09_disassembler_base::disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram) +offs_t m6x09_base_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { uint8_t pb; unsigned int ea; int offset; - int p = 0; + offs_t p = pc; // look up the opcode - const opcodeinfo *op = fetch_opcode(oprom, p); + const opcodeinfo *op = fetch_opcode(opcodes, p); if (!op) { stream << "Illegal Opcode"; - return p | DASMFLAG_SUPPORTED; + return (p - pc) | SUPPORTED; } // how many operands do we have? - int numoperands = (p == 1) + int numoperands = (p - pc == 1) ? op->length() - 1 : op->length() - 2; - const uint8_t *operandarray = &opram[p]; + offs_t ppc = p; p += numoperands; - pc += p; // output the base instruction name util::stream_format(stream, "%-6s", op->name()); @@ -214,7 +136,7 @@ offs_t m6x09_disassembler_base::disassemble(std::ostream &stream, offs_t pc, con case PSHS: case PSHU: - pb = operandarray[0]; + pb = params.r8(ppc); if (pb & 0x80) util::stream_format(stream, "PC"); if (pb & 0x40) @@ -235,7 +157,7 @@ offs_t m6x09_disassembler_base::disassemble(std::ostream &stream, offs_t pc, con case PULS: case PULU: - pb = operandarray[0]; + pb = params.r8(ppc); if (pb & 0x01) util::stream_format(stream, "CC"); if (pb & 0x02) @@ -255,23 +177,23 @@ offs_t m6x09_disassembler_base::disassemble(std::ostream &stream, offs_t pc, con break; case DIR: - ea = operandarray[0]; + ea = params.r8(ppc); util::stream_format(stream, "$%02X", ea); break; case DIR_IM: assert_hd6309_exclusive(); - util::stream_format(stream, "#$%02X;", operandarray[0]); - util::stream_format(stream, "$%02X", operandarray[1]); + util::stream_format(stream, "#$%02X;", params.r8(ppc)); + util::stream_format(stream, "$%02X", params.r8(ppc + 1)); break; case REL: - offset = (int8_t)operandarray[0]; + offset = (int8_t)params.r8(ppc); util::stream_format(stream, "$%04X", (pc + offset) & 0xffff); break; case LREL: - offset = (int16_t)((operandarray[0] << 8) + operandarray[1]); + offset = (int16_t)params.r16(ppc); util::stream_format(stream, "$%04X", (pc + offset) & 0xffff); break; @@ -279,13 +201,13 @@ offs_t m6x09_disassembler_base::disassemble(std::ostream &stream, offs_t pc, con if (numoperands == 3) { assert_hd6309_exclusive(); - pb = operandarray[0]; - ea = (operandarray[1] << 8) + operandarray[2]; + pb = params.r8(ppc); + ea = params.r16(ppc+1); util::stream_format(stream, "#$%02X,$%04X", pb, ea); } else if (numoperands == 2) { - ea = (operandarray[0] << 8) + operandarray[1]; + ea = params.r16(ppc); util::stream_format(stream, "$%04X", ea); } break; @@ -294,52 +216,52 @@ offs_t m6x09_disassembler_base::disassemble(std::ostream &stream, offs_t pc, con if (numoperands == 2) { assert_hd6309_exclusive(); - util::stream_format(stream, "#$%02X;", operandarray[0]); - pb = operandarray[1]; + util::stream_format(stream, "#$%02X;", params.r8(ppc)); + pb = params.r8(ppc+1); } else { - pb = operandarray[0]; + pb = params.r8(ppc); } - indirect(stream, pb, opram, p); + indirect(stream, pb, params, p); break; case IMM: if (numoperands == 4) { - ea = (operandarray[0] << 24) + (operandarray[1] << 16) + (operandarray[2] << 8) + operandarray[3]; + ea = params.r32(ppc); util::stream_format(stream, "#$%08X", ea); } else if (numoperands == 2) { - ea = (operandarray[0] << 8) + operandarray[1]; + ea = params.r16(ppc); util::stream_format(stream, "#$%04X", ea); } else if (numoperands == 1) { - ea = operandarray[0]; + ea = params.r8(ppc); util::stream_format(stream, "#$%02X", ea); } break; case IMM_RR: - pb = operandarray[0]; + pb = params.r8(ppc); register_register(stream, pb); break; case IMM_BW: - pb = operandarray[0]; + pb = params.r8(ppc); util::stream_format(stream, "%s,", m6x09_btwregs[((pb & 0xc0) >> 6)]); util::stream_format(stream, "%d,", (pb & 0x38) >> 3); util::stream_format(stream, "%d,", (pb & 0x07)); - util::stream_format(stream, "$%02X", operandarray[1]); + util::stream_format(stream, "$%02X", params.r8(ppc+1)); break; case IMM_TFM: - pb = operandarray[0]; + pb = params.r8(ppc); util::stream_format(stream, tfm_s[op->opcode() & 0x07], hd6309_tfmregs[(pb >> 4) & 0xf], hd6309_tfmregs[pb & 0xf]); break; @@ -347,7 +269,7 @@ offs_t m6x09_disassembler_base::disassemble(std::ostream &stream, offs_t pc, con throw false; } - return p | op->flags() | DASMFLAG_SUPPORTED; + return (p - pc) | op->flags() | SUPPORTED; } @@ -355,7 +277,7 @@ offs_t m6x09_disassembler_base::disassemble(std::ostream &stream, offs_t pc, con // M6809/HD6309 disassembler //************************************************************************** -static const opcodeinfo m6x09_opcodes[] = +const m6x09_base_disassembler::opcodeinfo m6x09_disassembler::m6x09_opcodes[] = { // Page 0 opcodes (single byte) { 0x00, 2, "NEG", DIR, M6x09_GENERAL }, @@ -381,7 +303,7 @@ static const opcodeinfo m6x09_opcodes[] = { 0x13, 1, "SYNC", INH, M6x09_GENERAL }, { 0x14, 1, "SEXW", INH, HD6309_EXCLUSIVE }, { 0x16, 3, "LBRA", LREL, M6x09_GENERAL }, - { 0x17, 3, "LBSR", LREL, M6x09_GENERAL, DASMFLAG_STEP_OVER }, + { 0x17, 3, "LBSR", LREL, M6x09_GENERAL, STEP_OVER }, { 0x19, 1, "DAA", INH, M6x09_GENERAL }, { 0x1A, 2, "ORCC", IMM, M6x09_GENERAL }, { 0x1C, 2, "ANDCC", IMM, M6x09_GENERAL }, @@ -491,7 +413,7 @@ static const opcodeinfo m6x09_opcodes[] = { 0x8A, 2, "ORA", IMM, M6x09_GENERAL }, { 0x8B, 2, "ADDA", IMM, M6x09_GENERAL }, { 0x8C, 3, "CMPX", IMM, M6x09_GENERAL }, - { 0x8D, 2, "BSR", REL, M6x09_GENERAL, DASMFLAG_STEP_OVER }, + { 0x8D, 2, "BSR", REL, M6x09_GENERAL, STEP_OVER }, { 0x8E, 3, "LDX", IMM, M6x09_GENERAL }, { 0x90, 2, "SUBA", DIR, M6x09_GENERAL }, @@ -507,7 +429,7 @@ static const opcodeinfo m6x09_opcodes[] = { 0x9A, 2, "ORA", DIR, M6x09_GENERAL }, { 0x9B, 2, "ADDA", DIR, M6x09_GENERAL }, { 0x9C, 2, "CMPX", DIR, M6x09_GENERAL }, - { 0x9D, 2, "JSR", DIR, M6x09_GENERAL, DASMFLAG_STEP_OVER }, + { 0x9D, 2, "JSR", DIR, M6x09_GENERAL, STEP_OVER }, { 0x9E, 2, "LDX", DIR, M6x09_GENERAL }, { 0x9F, 2, "STX", DIR, M6x09_GENERAL }, @@ -524,7 +446,7 @@ static const opcodeinfo m6x09_opcodes[] = { 0xAA, 2, "ORA", IND, M6x09_GENERAL }, { 0xAB, 2, "ADDA", IND, M6x09_GENERAL }, { 0xAC, 2, "CMPX", IND, M6x09_GENERAL }, - { 0xAD, 2, "JSR", IND, M6x09_GENERAL, DASMFLAG_STEP_OVER }, + { 0xAD, 2, "JSR", IND, M6x09_GENERAL, STEP_OVER }, { 0xAE, 2, "LDX", IND, M6x09_GENERAL }, { 0xAF, 2, "STX", IND, M6x09_GENERAL }, @@ -541,7 +463,7 @@ static const opcodeinfo m6x09_opcodes[] = { 0xBA, 3, "ORA", EXT, M6x09_GENERAL }, { 0xBB, 3, "ADDA", EXT, M6x09_GENERAL }, { 0xBC, 3, "CMPX", EXT, M6x09_GENERAL }, - { 0xBD, 3, "JSR", EXT, M6x09_GENERAL, DASMFLAG_STEP_OVER }, + { 0xBD, 3, "JSR", EXT, M6x09_GENERAL, STEP_OVER }, { 0xBE, 3, "LDX", EXT, M6x09_GENERAL }, { 0xBF, 3, "STX", EXT, M6x09_GENERAL }, @@ -875,33 +797,17 @@ static const opcodeinfo m6x09_opcodes[] = // ======================> m6x09_disassembler -// M6809/HD6309 disassembler -namespace +m6x09_disassembler::m6x09_disassembler(m6x09_instruction_level level, const char teregs[16][4]) + : m6x09_base_disassembler(m6x09_opcodes, ARRAY_LENGTH(m6x09_opcodes), level) + , m_teregs(*reinterpret_cast, 16> *>(teregs)) { - class m6x09_disassembler : public m6x09_disassembler_base - { - public: - m6x09_disassembler(m6x09_instruction_level level, const char teregs[16][4]) - : m6x09_disassembler_base(m6x09_opcodes, ARRAY_LENGTH(m6x09_opcodes), level) - , m_teregs(*reinterpret_cast, 16> *>(teregs)) - { - } - - protected: - virtual void indirect(std::ostream &stream, uint8_t pb, const uint8_t *opram, int &p) override; - virtual void register_register(std::ostream &stream, uint8_t pb) override; - - private: - const std::array, 16> &m_teregs; - }; -}; - +} //------------------------------------------------- // indirect addressing mode for M6809/HD6309 //------------------------------------------------- -void m6x09_disassembler::indirect(std::ostream &stream, uint8_t pb, const uint8_t *opram, int &p) +void m6x09_disassembler::indirect(std::ostream &stream, uint8_t pb, const data_buffer ¶ms, offs_t &p) { uint8_t reg = (pb >> 5) & 3; uint8_t pbm = pb & 0x8f; @@ -924,7 +830,7 @@ void m6x09_disassembler::indirect(std::ostream &stream, uint8_t pb, const uint8_ util::stream_format(stream, ",W"); break; case 0x01: - offset = (int16_t)((opram[p + 0] << 8) + opram[p + 1]); + offset = (int16_t)params.r16(p); p += 2; util::stream_format(stream, "%s", (offset < 0) ? "-" : ""); util::stream_format(stream, "$%04X,W", (offset < 0) ? -offset : offset); @@ -973,14 +879,14 @@ void m6x09_disassembler::indirect(std::ostream &stream, uint8_t pb, const uint8_ break; case 0x88: // (+/- 7 bit offset),R - offset = (int8_t)opram[p++]; + offset = (int8_t)params.r8(p++); util::stream_format(stream, "%s", (offset < 0) ? "-" : ""); util::stream_format(stream, "$%02X,", (offset < 0) ? -offset : offset); util::stream_format(stream, "%s", m6x09_regs[reg]); break; case 0x89: // (+/- 15 bit offset),R - offset = (int16_t)((opram[p + 0] << 8) + opram[p + 1]); + offset = (int16_t)params.r16(p); p += 2; util::stream_format(stream, "%s", (offset < 0) ? "-" : ""); util::stream_format(stream, "$%04X,", (offset < 0) ? -offset : offset); @@ -996,13 +902,13 @@ void m6x09_disassembler::indirect(std::ostream &stream, uint8_t pb, const uint8_ break; case 0x8c: // (+/- 7 bit offset),PC - offset = (int8_t)opram[p++]; + offset = (int8_t)params.r8(p); util::stream_format(stream, "%s", (offset < 0) ? "-" : ""); util::stream_format(stream, "$%02X,PC", (offset < 0) ? -offset : offset); break; case 0x8d: // (+/- 15 bit offset),PC - offset = (int16_t)((opram[p + 0] << 8) + opram[p + 1]); + offset = (int16_t)params.r16(p); p += 2; util::stream_format(stream, "%s", (offset < 0) ? "-" : ""); util::stream_format(stream, "$%04X,PC", (offset < 0) ? -offset : offset); @@ -1015,7 +921,7 @@ void m6x09_disassembler::indirect(std::ostream &stream, uint8_t pb, const uint8_ case 0x8f: // address or operations relative to W if (indirect) { - ea = (uint16_t)((opram[p + 0] << 8) + opram[p + 1]); + ea = (uint16_t)params.r16(p); p += 2; util::stream_format(stream, "$%04X", ea); break; @@ -1028,7 +934,7 @@ void m6x09_disassembler::indirect(std::ostream &stream, uint8_t pb, const uint8_ util::stream_format(stream, ",W"); break; case 0x01: - offset = (int16_t)((opram[p + 0] << 8) + opram[p + 1]); + offset = (int16_t)params.r16(p); p += 2; util::stream_format(stream, "%s", (offset < 0) ? "-" : ""); util::stream_format(stream, "$%04X,W", (offset < 0) ? -offset : offset); @@ -1075,15 +981,15 @@ void m6x09_disassembler::register_register(std::ostream &stream, uint8_t pb) // M6809 disassembler entry point //------------------------------------------------- -CPU_DISASSEMBLE(m6809) +const char m6809_disassembler::m6809_teregs[16][4] = +{ + "D", "X", "Y", "U", "S", "PC", "inv", "inv", + "A", "B", "CC", "DP", "inv", "inv", "inv", "inv" +}; + + +m6809_disassembler::m6809_disassembler() : m6x09_disassembler(M6x09_GENERAL, m6809_teregs) { - static const char m6809_teregs[16][4] = - { - "D", "X", "Y", "U", "S", "PC", "inv", "inv", - "A", "B", "CC", "DP", "inv", "inv", "inv", "inv" - }; - m6x09_disassembler disasm(M6x09_GENERAL, m6809_teregs); - return disasm.disassemble(stream, pc, oprom, opram); } @@ -1091,15 +997,14 @@ CPU_DISASSEMBLE(m6809) // HD6309 disassembler entry point //------------------------------------------------- -CPU_DISASSEMBLE(hd6309) +const char hd6309_disassembler::hd6309_teregs[16][4] = +{ + "D", "X", "Y", "U", "S", "PC", "W", "V", + "A", "B", "CC", "DP", "0", "0", "E", "F" +}; + +hd6309_disassembler::hd6309_disassembler() : m6x09_disassembler(HD6309_EXCLUSIVE, hd6309_teregs) { - static const char hd6309_teregs[16][4] = - { - "D", "X", "Y", "U", "S", "PC", "W", "V", - "A", "B", "CC", "DP", "0", "0", "E", "F" - }; - m6x09_disassembler disasm(HD6309_EXCLUSIVE, hd6309_teregs); - return disasm.disassemble(stream, pc, oprom, opram); } @@ -1107,7 +1012,7 @@ CPU_DISASSEMBLE(hd6309) // Konami disassembler //************************************************************************** -static const opcodeinfo konami_opcodes[] = +const m6x09_base_disassembler::opcodeinfo konami_disassembler::konami_opcodes[] = { { 0x08, 2, "LEAX", IND, M6x09_GENERAL }, { 0x09, 2, "LEAY", IND, M6x09_GENERAL }, @@ -1277,9 +1182,9 @@ static const opcodeinfo konami_opcodes[] = { 0xA6, 2, "ASLW", IND, M6x09_GENERAL }, { 0xA7, 2, "ROLW", IND, M6x09_GENERAL }, { 0xA8, 2, "JMP", IND, M6x09_GENERAL }, - { 0xA9, 2, "JSR", IND, M6x09_GENERAL, DASMFLAG_STEP_OVER }, - { 0xAA, 2, "BSR", REL, M6x09_GENERAL, DASMFLAG_STEP_OVER }, - { 0xAB, 3, "LBSR", LREL, M6x09_GENERAL, DASMFLAG_STEP_OVER }, + { 0xA9, 2, "JSR", IND, M6x09_GENERAL, STEP_OVER }, + { 0xAA, 2, "BSR", REL, M6x09_GENERAL, STEP_OVER }, + { 0xAB, 3, "LBSR", LREL, M6x09_GENERAL, STEP_OVER }, { 0xAC, 2, "DECB,JNZ", REL, M6x09_GENERAL }, { 0xAD, 2, "DECX,JNZ", REL, M6x09_GENERAL }, { 0xAE, 1, "NOP", INH, M6x09_GENERAL }, @@ -1324,27 +1229,15 @@ static const opcodeinfo konami_opcodes[] = // ======================> konami_disassembler -namespace +konami_disassembler::konami_disassembler() : m6x09_base_disassembler(konami_opcodes, ARRAY_LENGTH(konami_opcodes), M6x09_GENERAL) { - // Konami disassembler - class konami_disassembler : public m6x09_disassembler_base - { - public: - konami_disassembler() - : m6x09_disassembler_base(konami_opcodes, ARRAY_LENGTH(konami_opcodes), M6x09_GENERAL) { } - - protected: - virtual void indirect(std::ostream &stream, uint8_t pb, const uint8_t *opram, int &p) override; - virtual void register_register(std::ostream &stream, uint8_t pb) override; - }; -}; - +} //------------------------------------------------- // indirect addressing mode for Konami //------------------------------------------------- -void konami_disassembler::indirect(std::ostream &stream, uint8_t mode, const uint8_t *opram, int &p) +void konami_disassembler::indirect(std::ostream &stream, uint8_t mode, const data_buffer ¶ms, offs_t &p) { static const char index_reg[8][3] = { @@ -1379,7 +1272,7 @@ void konami_disassembler::indirect(std::ostream &stream, uint8_t mode, const uin break; case 0x04: /* direct - mode */ - util::stream_format(stream, "[$%02x]", opram[p++]); + util::stream_format(stream, "[$%02x]", params.r8(p++)); break; case 0x07: /* register d */ @@ -1404,7 +1297,7 @@ void konami_disassembler::indirect(std::ostream &stream, uint8_t mode, const uin break; case 0x04: /* direct - mode */ - util::stream_format(stream, "$%02x", opram[p++]); + util::stream_format(stream, "$%02x", params.r8(p++)); break; case 0x07: /* register d */ @@ -1441,7 +1334,7 @@ void konami_disassembler::indirect(std::ostream &stream, uint8_t mode, const uin break; case 4: // post byte offset - val = opram[p++]; + val = params.r8(p++); if (val & 0x80) util::stream_format(stream, "[#$-%02x,%s]", 0x100 - val, index_reg[idx]); @@ -1450,8 +1343,8 @@ void konami_disassembler::indirect(std::ostream &stream, uint8_t mode, const uin break; case 5: // post word offset - val = opram[p++] << 8; - val |= opram[p++]; + val = params.r16(p); + p += 2; if (val & 0x8000) util::stream_format(stream, "[#$-%04x,%s]", 0x10000 - val, index_reg[idx]); @@ -1464,8 +1357,8 @@ void konami_disassembler::indirect(std::ostream &stream, uint8_t mode, const uin break; case 7: // extended - val = opram[p++] << 8; - val |= opram[p++]; + val = params.r16(p); + p += 2; util::stream_format(stream, "[$%04x]", val); break; @@ -1492,7 +1385,7 @@ void konami_disassembler::indirect(std::ostream &stream, uint8_t mode, const uin break; case 4: // post byte offset - val = opram[p++]; + val = params.r8(p++); if (val & 0x80) util::stream_format(stream, "#$-%02x,%s", 0x100 - val, index_reg[idx]); @@ -1501,8 +1394,8 @@ void konami_disassembler::indirect(std::ostream &stream, uint8_t mode, const uin break; case 5: // post word offset - val = opram[p++] << 8; - val |= opram[p++]; + val = params.r16(p); + p += 2; if (val & 0x8000) util::stream_format(stream, "#$-%04x,%s", 0x10000 - val, index_reg[idx]); @@ -1515,8 +1408,8 @@ void konami_disassembler::indirect(std::ostream &stream, uint8_t mode, const uin break; case 7: // extended - val = opram[p++] << 8; - val |= opram[p++]; + val = params.r16(p); + p += 2; util::stream_format(stream, "$%04x", val); break; @@ -1540,14 +1433,3 @@ void konami_disassembler::register_register(std::ostream &stream, uint8_t pb) konami_teregs[(pb >> 0) & 0x7], konami_teregs[(pb >> 4) & 0x7]); } - - -//------------------------------------------------- -// Konami disassembler entry point -//------------------------------------------------- - -CPU_DISASSEMBLE(konami) -{ - konami_disassembler disasm; - return disasm.disassemble(stream, pc, oprom, opram); -} diff --git a/src/devices/cpu/m6809/6x09dasm.h b/src/devices/cpu/m6809/6x09dasm.h new file mode 100644 index 00000000000..4a230799801 --- /dev/null +++ b/src/devices/cpu/m6809/6x09dasm.h @@ -0,0 +1,166 @@ +// license:BSD-3-Clause +// copyright-holders:Nathan Woods,Sean Riddle,Tim Lindner +/***************************************************************************** + + 6x09dasm.cpp - a 6809/6309/Konami opcode disassembler + + Based on: + 6309dasm.c - a 6309 opcode disassembler + Version 1.0 5-AUG-2000 + Copyright Tim Lindner + + and + + 6809dasm.c - a 6809 opcode disassembler + Version 1.4 1-MAR-95 + Copyright Sean Riddle + + Thanks to Franklin Bowen for bug fixes, ideas + + Freely distributable on any medium given all copyrights are retained + by the author and no charge greater than $7.00 is made for obtaining + this software + + Please send all bug reports, update ideas and data files to: + sriddle@ionet.net and tlindner@ix.netcom.com + +*****************************************************************************/ + +#ifndef MAME_CPU_M6809_6X09DASM_H +#define MAME_CPU_M6809_6X09DASM_H + +#pragma once + +class m6x09_base_disassembler : public util::disasm_interface +{ +protected: + class opcodeinfo; + +public: + // General, or 6309 only? + enum m6x09_instruction_level + { + M6x09_GENERAL, + HD6309_EXCLUSIVE + }; + + m6x09_base_disassembler(const opcodeinfo *opcodes, size_t opcode_count, m6x09_instruction_level level) + : m_opcodes(opcodes, opcode_count), m_level(level) + { + } + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +protected: + enum m6x09_addressing_mode + { + INH, // Inherent + PSHS, PSHU, // Push + PULS, PULU, // Pull + DIR, // Direct + DIR_IM, // Direct in memory (6309 only) + IND, // Indexed + REL, // Relative (8 bit) + LREL, // Long relative (16 bit) + EXT, // Extended + IMM, // Immediate + IMM_RR, // Register-to-register + IMM_BW, // Bitwise operations (6309 only) + IMM_TFM, // Transfer from memory (6309 only) + PG1, // Switch to page 1 opcodes + PG2 // Switch to page 2 opcodes + }; + + // Opcode structure + class opcodeinfo + { + public: + constexpr opcodeinfo(uint16_t opcode, uint8_t length, const char *name, m6x09_addressing_mode mode, m6x09_instruction_level level, unsigned flags = 0) + : m_opcode(opcode), m_length(length), m_mode(mode), m_level(level), m_flags(flags), m_name(name) + { + } + + uint16_t opcode() const { return m_opcode; } + uint8_t length() const { return m_length; } + m6x09_addressing_mode mode() const { return m_mode; } + m6x09_instruction_level level() const { return m_level; } + unsigned flags() const { return m_flags; } + const char *name() const { return m_name; } + + private: + uint16_t m_opcode; // 8-bit opcode value + uint8_t m_length; // Opcode length in bytes + m6x09_addressing_mode m_mode : 6; // Addressing mode + m6x09_instruction_level m_level : 2; // General, or 6309 only? + unsigned m_flags; // Disassembly flags + const char * m_name; // Opcode name + }; + + static const char *const m6x09_regs[5]; + static const char *const m6x09_btwregs[5]; + static const char *const hd6309_tfmregs[16]; + static const char *const tfm_s[]; + + virtual void indirect(std::ostream &stream, uint8_t pb, const data_buffer ¶ms, offs_t &p) = 0; + virtual void register_register(std::ostream &stream, uint8_t pb) = 0; + +private: + util::contiguous_sequence_wrapper m_opcodes; + m6x09_instruction_level m_level; + + const opcodeinfo *fetch_opcode(const data_buffer &opcodes, offs_t &p); + + void assert_hd6309_exclusive() + { + if (m_level < HD6309_EXCLUSIVE) + throw false; + } +}; + +class m6x09_disassembler : public m6x09_base_disassembler +{ +public: + m6x09_disassembler(m6x09_instruction_level level, const char teregs[16][4]); + +protected: + virtual void indirect(std::ostream &stream, uint8_t pb, const data_buffer ¶ms, offs_t &p) override; + virtual void register_register(std::ostream &stream, uint8_t pb) override; + +private: + static const opcodeinfo m6x09_opcodes[]; + const std::array, 16> &m_teregs; +}; + + +class konami_disassembler : public m6x09_base_disassembler +{ +public: + konami_disassembler(); + +protected: + virtual void indirect(std::ostream &stream, uint8_t pb, const data_buffer ¶ms, offs_t &p) override; + virtual void register_register(std::ostream &stream, uint8_t pb) override; + +private: + static const opcodeinfo konami_opcodes[]; +}; + +class m6809_disassembler : public m6x09_disassembler +{ +public: + m6809_disassembler(); + +private: + static const char m6809_teregs[16][4]; +}; + +class hd6309_disassembler : public m6x09_disassembler +{ +public: + hd6309_disassembler(); + +private: + static const char hd6309_teregs[16][4]; +}; + +#endif diff --git a/src/devices/cpu/m6809/hd6309.cpp b/src/devices/cpu/m6809/hd6309.cpp index 30de26db2c6..1b40d17e06f 100644 --- a/src/devices/cpu/m6809/hd6309.cpp +++ b/src/devices/cpu/m6809/hd6309.cpp @@ -118,6 +118,7 @@ March 2013 NPW: #include "debugger.h" #include "hd6309.h" #include "m6809inl.h" +#include "6x09dasm.h" //************************************************************************** @@ -285,38 +286,13 @@ void hd6309_device::device_post_load() //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t hd6309_device::disasm_min_opcode_bytes() const -{ - return 1; -} - - - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t hd6309_device::disasm_max_opcode_bytes() const -{ - return 5; -} - - - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t hd6309_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *hd6309_device::create_disassembler() { - extern CPU_DISASSEMBLE( hd6309 ); - return CPU_DISASSEMBLE_NAME(hd6309)(this, stream, pc, oprom, opram, options); + return new hd6309_disassembler; } diff --git a/src/devices/cpu/m6809/hd6309.h b/src/devices/cpu/m6809/hd6309.h index a097902da1f..8e209f9f7b2 100644 --- a/src/devices/cpu/m6809/hd6309.h +++ b/src/devices/cpu/m6809/hd6309.h @@ -42,9 +42,7 @@ protected: virtual void execute_run() override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual bool is_6809() override { return false; }; diff --git a/src/devices/cpu/m6809/konami.cpp b/src/devices/cpu/m6809/konami.cpp index 55f3a864744..cf41649a101 100644 --- a/src/devices/cpu/m6809/konami.cpp +++ b/src/devices/cpu/m6809/konami.cpp @@ -58,6 +58,7 @@ March 2013 NPW: #include "debugger.h" #include "konami.h" #include "m6809inl.h" +#include "6x09dasm.h" //************************************************************************** @@ -105,14 +106,13 @@ void konami_cpu_device::device_start() //------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t konami_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *konami_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( konami ); - return CPU_DISASSEMBLE_NAME(konami)(this, stream, pc, oprom, opram, options); + return new konami_disassembler; } diff --git a/src/devices/cpu/m6809/konami.h b/src/devices/cpu/m6809/konami.h index 1d9d900c138..216b007302a 100644 --- a/src/devices/cpu/m6809/konami.h +++ b/src/devices/cpu/m6809/konami.h @@ -46,7 +46,7 @@ protected: virtual void execute_run() override; // device_disasm_interface overrides - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: typedef m6809_base_device super; diff --git a/src/devices/cpu/m6809/m6809.cpp b/src/devices/cpu/m6809/m6809.cpp index 584af3e4912..9c27d4680a3 100644 --- a/src/devices/cpu/m6809/m6809.cpp +++ b/src/devices/cpu/m6809/m6809.cpp @@ -83,6 +83,7 @@ March 2013 NPW: #include "debugger.h" #include "m6809.h" #include "m6809inl.h" +#include "6x09dasm.h" //************************************************************************** @@ -350,36 +351,13 @@ void m6809_base_device::state_string_export(const device_state_entry &entry, std //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t m6809_base_device::disasm_min_opcode_bytes() const -{ - return 1; -} - - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t m6809_base_device::disasm_max_opcode_bytes() const -{ - return 5; -} - - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t m6809_base_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *m6809_base_device::create_disassembler() { - extern CPU_DISASSEMBLE( m6809 ); - return CPU_DISASSEMBLE_NAME(m6809)(this, stream, pc, oprom, opram, options); + return new m6809_disassembler; } diff --git a/src/devices/cpu/m6809/m6809.h b/src/devices/cpu/m6809/m6809.h index 29d1acbcf9e..3bab3e17b57 100644 --- a/src/devices/cpu/m6809/m6809.h +++ b/src/devices/cpu/m6809/m6809.h @@ -71,9 +71,7 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // device_state_interface overrides virtual void state_import(const device_state_entry &entry) override; diff --git a/src/devices/cpu/mb86233/mb86233.cpp b/src/devices/cpu/mb86233/mb86233.cpp index 526ac63e208..7c6bd87ae6a 100644 --- a/src/devices/cpu/mb86233/mb86233.cpp +++ b/src/devices/cpu/mb86233/mb86233.cpp @@ -18,6 +18,7 @@ #include "emu.h" #include "debugger.h" #include "mb86233.h" +#include "mb86233d.h" DEFINE_DEVICE_TYPE(MB86233, mb86233_cpu_device, "mb86233", "MB86233") @@ -46,10 +47,9 @@ device_memory_interface::space_config_vector mb86233_cpu_device::memory_space_co } -offs_t mb86233_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *mb86233_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( mb86233 ); - return CPU_DISASSEMBLE_NAME(mb86233)(this, stream, pc, oprom, opram, options); + return new mb86233_disassembler; } diff --git a/src/devices/cpu/mb86233/mb86233.h b/src/devices/cpu/mb86233/mb86233.h index c60aabd987e..297b90f7382 100644 --- a/src/devices/cpu/mb86233/mb86233.h +++ b/src/devices/cpu/mb86233/mb86233.h @@ -77,9 +77,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 4; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/mb86233/mb86233d.cpp b/src/devices/cpu/mb86233/mb86233d.cpp index 0919ca1ef58..5d5c9b13a27 100644 --- a/src/devices/cpu/mb86233/mb86233d.cpp +++ b/src/devices/cpu/mb86233/mb86233d.cpp @@ -1,8 +1,7 @@ // license:BSD-3-Clause // copyright-holders:Ernesto Corvi #include "emu.h" -#include "debugger.h" -#include "mb86233.h" +#include "mb86233d.h" /* @@ -74,14 +73,14 @@ -static const char *const regnames[0x40] = { +const char *const mb86233_disassembler::regnames[0x40] = { "b0", "b1", "x0", "x1", "x2", "i0", "i1", "i2", "sp", "pag", "vsm", "dmc", "c0", "c1", "pc", "-", "a", "ah", "al", "b", "bh", "bl", "c", "ch", "cl", "d", "dh", "dl", "p", "ph", "pl", "sft", "rf0", "rf1", "rf2", "rf3", "rf4", "rf5", "rf6", "rf7", "rf8", "rf9", "rfa", "rfb", "rfc", "rfd", "rfe", "rff", "sio0", "si1", "pio", "pioa", "rpc", "r?35", "r?36", "r?37", "pad", "mod", "ear", "st", "mask", "tim", "cx", "dx" }; -static std::string condition(unsigned int cond, bool invert) +std::string mb86233_disassembler::condition(unsigned int cond, bool invert) { std::ostringstream stream; @@ -101,12 +100,12 @@ static std::string condition(unsigned int cond, bool invert) return stream.str(); } -static std::string regs(uint32_t reg) +std::string mb86233_disassembler::regs(u32 reg) { return regnames[reg & 0x3f]; } -static std::string memory(uint32_t reg, bool x1) +std::string mb86233_disassembler::memory(u32 reg, bool x1) { std::ostringstream stream; @@ -182,7 +181,7 @@ static std::string memory(uint32_t reg, bool x1) return stream.str(); } -static std::string alu0_func( uint32_t alu) +std::string mb86233_disassembler::alu0_func(u32 alu) { std::ostringstream stream; @@ -224,14 +223,16 @@ static std::string alu0_func( uint32_t alu) return stream.str(); } -static unsigned dasm_mb86233(std::ostream &stream, uint32_t opcode ) +offs_t mb86233_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { + u32 opcode = opcodes.r32(pc); + switch((opcode >> 26) & 0x3f) { case 0x00: { // Dual move AB - uint32_t r1 = opcode & 0x1ff; - uint32_t r2 = (opcode >> 9) & 0x1ff; - uint32_t alu = (opcode >> 21) & 0x1f; - uint32_t op = (opcode >> 18) & 0x7; + u32 r1 = opcode & 0x1ff; + u32 r2 = (opcode >> 9) & 0x1ff; + u32 alu = (opcode >> 21) & 0x1f; + u32 op = (opcode >> 18) & 0x7; if(alu) util::stream_format(stream, "%s : ", alu0_func(alu) ); @@ -253,10 +254,10 @@ static unsigned dasm_mb86233(std::ostream &stream, uint32_t opcode ) } case 0x07: { // LD/MOV - uint32_t r1 = opcode & 0x1ff; - uint32_t r2 = (opcode >> 9) & 0x1ff; - uint32_t alu = (opcode >> 21) & 0x1f; - uint32_t op = (opcode >> 18) & 0x7; + u32 r1 = opcode & 0x1ff; + u32 r2 = (opcode >> 9) & 0x1ff; + u32 alu = (opcode >> 21) & 0x1f; + u32 op = (opcode >> 18) & 0x7; if(alu) { util::stream_format(stream, "%s", alu0_func(alu)); @@ -345,8 +346,8 @@ static unsigned dasm_mb86233(std::ostream &stream, uint32_t opcode ) } case 0x0f: { // rep/clr0/clr1/set - uint32_t alu = (opcode >> 21) & 0x1f; - uint32_t sub2 = (opcode >> 17) & 7; + u32 alu = (opcode >> 21) & 0x1f; + u32 sub2 = (opcode >> 17) & 7; if(alu) util::stream_format(stream, "%s : ", alu0_func(alu)); @@ -400,9 +401,9 @@ static unsigned dasm_mb86233(std::ostream &stream, uint32_t opcode ) break; case 0x2f: case 0x3f: { - uint32_t cond = ( opcode >> 20 ) & 0x1f; - uint32_t subtype = ( opcode >> 17 ) & 7; - uint32_t data = opcode & 0xffff; + u32 cond = ( opcode >> 20 ) & 0x1f; + u32 subtype = ( opcode >> 17 ) & 7; + u32 data = opcode & 0xffff; bool invert = opcode & 0x40000000; switch(subtype) { @@ -454,12 +455,10 @@ static unsigned dasm_mb86233(std::ostream &stream, uint32_t opcode ) break; } - return (1 | DASMFLAG_SUPPORTED); + return 1 | SUPPORTED; } -CPU_DISASSEMBLE(mb86233) +u32 mb86233_disassembler::opcode_alignment() const { - uint32_t op = *(uint32_t *)oprom; - op = little_endianize_int32(op); - return dasm_mb86233(stream, op); + return 1; } diff --git a/src/devices/cpu/mb86233/mb86233d.h b/src/devices/cpu/mb86233/mb86233d.h new file mode 100644 index 00000000000..50a48a6f0a9 --- /dev/null +++ b/src/devices/cpu/mb86233/mb86233d.h @@ -0,0 +1,26 @@ +// license:BSD-3-Clause +// copyright-holders:Ernesto Corvi + +#ifndef MAME_CPU_MB86233_MB86233D_H +#define MAME_CPU_MB86233_MB86233D_H + +#pragma once + +class mb86233_disassembler : public util::disasm_interface +{ +public: + mb86233_disassembler() = default; + virtual ~mb86233_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *const regnames[0x40]; + static std::string condition(unsigned int cond, bool invert); + static std::string regs(u32 reg); + static std::string memory(u32 reg, bool x1); + static std::string alu0_func(u32 alu); +}; + +#endif diff --git a/src/devices/cpu/mb86235/mb86235.cpp b/src/devices/cpu/mb86235/mb86235.cpp index 223b27db6d3..cac1f550035 100644 --- a/src/devices/cpu/mb86235/mb86235.cpp +++ b/src/devices/cpu/mb86235/mb86235.cpp @@ -14,6 +14,7 @@ #include "emu.h" #include "mb86235.h" #include "mb86235fe.h" +#include "mb86235d.h" #include "debugger.h" @@ -234,10 +235,9 @@ void mb86235_device::state_string_export(const device_state_entry &entry, std::s } } -offs_t mb86235_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *mb86235_device::create_disassembler() { - extern CPU_DISASSEMBLE( mb86235 ); - return CPU_DISASSEMBLE_NAME(mb86235)(this, stream, pc, oprom, opram, options); + return new mb86235_disassembler; } diff --git a/src/devices/cpu/mb86235/mb86235.h b/src/devices/cpu/mb86235/mb86235.h index ebe151213da..ba174da7382 100644 --- a/src/devices/cpu/mb86235/mb86235.h +++ b/src/devices/cpu/mb86235/mb86235.h @@ -71,9 +71,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 8; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 8; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; direct_read_data *m_direct; @@ -228,7 +226,4 @@ private: DECLARE_DEVICE_TYPE(MB86235, mb86235_device) - -CPU_DISASSEMBLE( mb86235 ); - #endif // MAME_CPU_MB86235_MB86235_H diff --git a/src/devices/cpu/mb86235/mb86235d.cpp b/src/devices/cpu/mb86235/mb86235d.cpp index f32fcba8969..e705500f1cd 100644 --- a/src/devices/cpu/mb86235/mb86235d.cpp +++ b/src/devices/cpu/mb86235/mb86235d.cpp @@ -1,10 +1,9 @@ // license:BSD-3-Clause // copyright-holders:Angelo Salese, ElSemi, Ville Linde #include "emu.h" -#include "debugger.h" -#include "mb86235.h" +#include "mb86235d.h" -static const char *regname[128] = +const char *mb86235_disassembler::regname[128] = { "MA0", "MA1", "MA2", "MA3", "MA4", "MA5", "MA6", "MA7", "AA0", "AA1", "AA2", "AA3", "AA4", "AA5", "AA6", "AA7", @@ -16,7 +15,7 @@ static const char *regname[128] = "???", "???", "???", "???", "???", "???", "???", "???" }; -static const char *db_mnemonic[64] = +const char *mb86235_disassembler::db_mnemonic[64] = { "DBMN", "DBMZ", "DBMV", "DBMU", "DBZD", "DBNR", "DBIL", "DBZC", "DBAN", "DBAZ", "DBAV", "DBAU", "DBMD", "DBAD", "???", "???", @@ -28,7 +27,7 @@ static const char *db_mnemonic[64] = "???", "???", "???", "???", "???", "???", "???", "???" }; -static const char *dbn_mnemonic[64] = +const char *mb86235_disassembler::dbn_mnemonic[64] = { "DBNMN", "DBNMZ", "DBNMV", "DBNMU", "DBNZD", "DBNNR", "DBNIL", "DBNZC", "DBNAN", "DBNAZ", "DBNAV", "DBNAU", "DBNMD", "DBNAD", "???", "???", @@ -40,7 +39,7 @@ static const char *dbn_mnemonic[64] = "???", "???", "???", "???", "???", "???", "???", "???" }; -static const char *dc_mnemonic[64] = +const char *mb86235_disassembler::dc_mnemonic[64] = { "DCMN", "DCMZ", "DCMV", "DCMU", "DCZD", "DCNR", "DCIL", "DCZC", "DCAN", "DCAZ", "DCAV", "DCAU", "DCMD", "DCAD", "???", "???", @@ -52,7 +51,7 @@ static const char *dc_mnemonic[64] = "???", "???", "???", "???", "???", "???", "???", "???" }; -static const char *dcn_mnemonic[64] = +const char *mb86235_disassembler::dcn_mnemonic[64] = { "DCNMN", "DCNMZ", "DCNMV", "DCNMU", "DCNZD", "DCNNR", "DCNIL", "DCNZC", "DCNAN", "DCNAZ", "DCNAV", "DCNAU", "DCNMD", "DCNAD", "???", "???", @@ -64,29 +63,29 @@ static const char *dcn_mnemonic[64] = "???", "???", "???", "???", "???", "???", "???", "???" }; -static const char *mi1_field[16] = +const char *mb86235_disassembler::mi1_field[16] = { "MA0", "MA1", "MA2", "MA3", "MA4", "MA5", "MA6", "MA7", "MB0", "MB1", "MB2", "MB3", "MB4", "MB5", "MB6", "MB7" }; -static const char *mi2_field[32] = +const char *mb86235_disassembler::mi2_field[32] = { "MA0", "MA1", "MA2", "MA3", "MA4", "MA5", "MA6", "MA7", "MB0", "MB1", "MB2", "MB3", "MB4", "MB5", "MB6", "MB7", "PR", "PR++", "PR--", "PR#0", "???", "???", "???", "???", "-1.0E+0", "0.0E+0", "0.5E+0", "1.0E+0", "1.5E+0", "2.0E+0", "3.0E+0", "5.0E+0" }; -static const char *mo_field[32] = +const char *mb86235_disassembler::mo_field[32] = { "MA0", "MA1", "MA2", "MA3", "MA4", "MA5", "MA6", "MA7", "MB0", "MB1", "MB2", "MB3", "MB4", "MB5", "MB6", "MB7", "AA0", "AA1", "AA2", "AA3", "AA4", "AA5", "AA6", "AA7", "AB0", "AB1", "AB2", "AB3", "AB4", "AB5", "AB6", "AB7" }; -static const char *ai1_field[16] = +const char *mb86235_disassembler::ai1_field[16] = { "AA0", "AA1", "AA2", "AA3", "AA4", "AA5", "AA6", "AA7", "AB0", "AB1", "AB2", "AB3", "AB4", "AB5", "AB6", "AB7" }; -static const char *ai2_field[32] = +const char *mb86235_disassembler::ai2_field[32] = { "AA0", "AA1", "AA2", "AA3", "AA4", "AA5", "AA6", "AA7", "AB0", "AB1", "AB2", "AB3", "AB4", "AB5", "AB6", "AB7", "PR", "PR++", "PR--", "PR#0", "???", "???", "???", "???", "0", "1", "-1", "???", "???", "???", "???", "???" }; -static const char *ai2f_field[32] = +const char *mb86235_disassembler::ai2f_field[32] = { "AA0", "AA1", "AA2", "AA3", "AA4", "AA5", "AA6", "AA7", "AB0", "AB1", "AB2", "AB3", "AB4", "AB5", "AB6", "AB7", "PR", "PR++", "PR--", "PR#0", "???", "???", "???", "???", "-1.0E+0", "0.0E+0", "0.5E+0", "1.0E+0", "1.5E+0", "2.0E+0", "3.0E+0", "5.0E+0" }; -static void dasm_ea(std::ostream &stream, int md, int arx, int ary, int disp) +void mb86235_disassembler::dasm_ea(std::ostream &stream, int md, int arx, int ary, int disp) { if (arx & 0x20) stream << "B("; @@ -117,7 +116,7 @@ static void dasm_ea(std::ostream &stream, int md, int arx, int ary, int disp) stream << ')'; } -static void dasm_alu_mul(std::ostream &stream, uint64_t opcode, bool twoop) +void mb86235_disassembler::dasm_alu_mul(std::ostream &stream, uint64_t opcode, bool twoop) { int ma = (opcode & ((uint64_t)(1) << 41)) ? 1 : 0; int o = (opcode >> 42) & 0x1f; @@ -220,7 +219,7 @@ static void dasm_alu_mul(std::ostream &stream, uint64_t opcode, bool twoop) } } -static void dasm_control(std::ostream &stream, uint32_t pc, uint64_t opcode) +void mb86235_disassembler::dasm_control(std::ostream &stream, uint32_t pc, uint64_t opcode) { int ef1 = (opcode >> 16) & 0x3f; int ef2 = opcode & 0xffff; @@ -335,7 +334,7 @@ static void dasm_control(std::ostream &stream, uint32_t pc, uint64_t opcode) } } -static void dasm_double_xfer1(std::ostream &stream, uint64_t opcode) +void mb86235_disassembler::dasm_double_xfer1(std::ostream &stream, uint64_t opcode) { int sd = (opcode >> 25) & 3; @@ -413,7 +412,7 @@ static void dasm_double_xfer1(std::ostream &stream, uint64_t opcode) } } -static void dasm_xfer1(std::ostream &stream, uint64_t opcode) +void mb86235_disassembler::dasm_xfer1(std::ostream &stream, uint64_t opcode) { int dr = (opcode >> 12) & 0x7f; int sr = (opcode >> 19) & 0x7f; @@ -469,7 +468,7 @@ static void dasm_xfer1(std::ostream &stream, uint64_t opcode) } } -static void dasm_double_xfer2_field(std::ostream &stream, int sd, uint32_t field) +void mb86235_disassembler::dasm_double_xfer2_field(std::ostream &stream, int sd, uint32_t field) { switch (sd) { @@ -537,7 +536,7 @@ static void dasm_double_xfer2_field(std::ostream &stream, int sd, uint32_t field } } -static void dasm_double_xfer2(std::ostream &stream, uint64_t opcode) +void mb86235_disassembler::dasm_double_xfer2(std::ostream &stream, uint64_t opcode) { int asd = (opcode >> 38) & 3; int bsd = (opcode >> 18) & 3; @@ -583,7 +582,7 @@ static void dasm_double_xfer2(std::ostream &stream, uint64_t opcode) } } -static void dasm_xfer2(std::ostream &stream, uint64_t opcode) +void mb86235_disassembler::dasm_xfer2(std::ostream &stream, uint64_t opcode) { int op = (opcode >> 39) & 3; int trm = (opcode >> 38) & 1; @@ -652,7 +651,7 @@ static void dasm_xfer2(std::ostream &stream, uint64_t opcode) } } -static void dasm_xfer3(std::ostream &stream, uint64_t opcode) +void mb86235_disassembler::dasm_xfer3(std::ostream &stream, uint64_t opcode) { uint32_t imm = (uint32_t)(opcode >> 27); int dr = (opcode >> 19) & 0x7f; @@ -668,8 +667,9 @@ static void dasm_xfer3(std::ostream &stream, uint64_t opcode) dasm_ea(stream, md, dr, ary, disp); } -static unsigned dasm_mb86235(std::ostream &stream, uint32_t pc, uint64_t opcode) +offs_t mb86235_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { + u64 opcode = opcodes.r64(pc); switch ((opcode >> 61) & 7) { case 0: // ALU / MUL / double transfer (type 1) @@ -711,14 +711,11 @@ static unsigned dasm_mb86235(std::ostream &stream, uint32_t pc, uint64_t opcode) break; } - return (1 | DASMFLAG_SUPPORTED); + return 1 | SUPPORTED; } - -CPU_DISASSEMBLE(mb86235) +u32 mb86235_disassembler::opcode_alignment() const { - uint64_t op = *(uint64_t*)oprom; - op = little_endianize_int64(op); - - return dasm_mb86235(stream, pc, op); + return 1; } + diff --git a/src/devices/cpu/mb86235/mb86235d.h b/src/devices/cpu/mb86235/mb86235d.h new file mode 100644 index 00000000000..a29fe41f064 --- /dev/null +++ b/src/devices/cpu/mb86235/mb86235d.h @@ -0,0 +1,42 @@ +// license:BSD-3-Clause +// copyright-holders:Angelo Salese, ElSemi, Ville Linde +#ifndef MAME_CPU_MB86235_MB86235D_H +#define MAME_CPU_MB86235_MB86235D_H + +#pragma once + +class mb86235_disassembler : public util::disasm_interface +{ +public: + mb86235_disassembler() = default; + virtual ~mb86235_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *regname[128]; + static const char *db_mnemonic[64]; + static const char *dbn_mnemonic[64]; + static const char *dc_mnemonic[64]; + static const char *dcn_mnemonic[64]; + static const char *mi1_field[16]; + static const char *mi2_field[32]; + static const char *mo_field[32]; + static const char *ai1_field[16]; + static const char *ai2_field[32]; + static const char *ai2f_field[32]; + + void dasm_ea(std::ostream &stream, int md, int arx, int ary, int disp); + void dasm_alu_mul(std::ostream &stream, uint64_t opcode, bool twoop); + void dasm_control(std::ostream &stream, uint32_t pc, uint64_t opcode); + void dasm_double_xfer1(std::ostream &stream, uint64_t opcode); + void dasm_xfer1(std::ostream &stream, uint64_t opcode); + void dasm_double_xfer2_field(std::ostream &stream, int sd, uint32_t field); + void dasm_double_xfer2(std::ostream &stream, uint64_t opcode); + void dasm_xfer2(std::ostream &stream, uint64_t opcode); + void dasm_xfer3(std::ostream &stream, uint64_t opcode); + +}; + +#endif diff --git a/src/devices/cpu/mb88xx/mb88dasm.cpp b/src/devices/cpu/mb88xx/mb88dasm.cpp index eced68233b0..2ab2856e1e8 100644 --- a/src/devices/cpu/mb88xx/mb88dasm.cpp +++ b/src/devices/cpu/mb88xx/mb88dasm.cpp @@ -10,14 +10,18 @@ *******************************************************************************/ #include "emu.h" -#include "mb88xx.h" +#include "mb88dasm.h" +u32 mb88_disassembler::opcode_alignment() const +{ + return 1; +} -CPU_DISASSEMBLE(mb88) +offs_t mb88_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { unsigned startpc = pc; - uint8_t op = oprom[pc++ - startpc]; - uint8_t arg = oprom[pc - startpc]; + uint8_t op = opcodes.r8(pc++); + uint8_t arg = opcodes.r8(pc); switch( op ) { @@ -220,5 +224,5 @@ CPU_DISASSEMBLE(mb88) break; } - return (pc - startpc) | DASMFLAG_SUPPORTED; + return (pc - startpc) | SUPPORTED; } diff --git a/src/devices/cpu/mb88xx/mb88dasm.h b/src/devices/cpu/mb88xx/mb88dasm.h new file mode 100644 index 00000000000..80a37a374c7 --- /dev/null +++ b/src/devices/cpu/mb88xx/mb88dasm.h @@ -0,0 +1,28 @@ +// license:BSD-3-Clause +// copyright-holders:Ernesto Corvi +/******************************************************************************* + + mb88dasm.c + Core implementation for the portable Fujitsu MB88xx series MCU disassembler. + + Written by Ernesto Corvi + +*******************************************************************************/ + + +#ifndef MAME_CPU_MB88XX_MB88DASM_H +#define MAME_CPU_MB88XX_MB88DASM_H + +#pragma once + +class mb88_disassembler : public util::disasm_interface +{ +public: + mb88_disassembler() = default; + virtual ~mb88_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/mb88xx/mb88xx.cpp b/src/devices/cpu/mb88xx/mb88xx.cpp index b896a07c6cf..f90dd868ee7 100644 --- a/src/devices/cpu/mb88xx/mb88xx.cpp +++ b/src/devices/cpu/mb88xx/mb88xx.cpp @@ -17,6 +17,7 @@ #include "emu.h" #include "mb88xx.h" +#include "mb88dasm.h" #include "debugger.h" @@ -162,10 +163,9 @@ device_memory_interface::space_config_vector mb88_cpu_device::memory_space_confi }; } -offs_t mb88_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *mb88_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( mb88 ); - return CPU_DISASSEMBLE_NAME(mb88)(this, stream, pc, oprom, opram, options); + return new mb88_disassembler; } diff --git a/src/devices/cpu/mb88xx/mb88xx.h b/src/devices/cpu/mb88xx/mb88xx.h index f4485e47f26..ca40ac14fe6 100644 --- a/src/devices/cpu/mb88xx/mb88xx.h +++ b/src/devices/cpu/mb88xx/mb88xx.h @@ -122,9 +122,6 @@ enum #define MB88_IRQ_LINE 0 -CPU_DISASSEMBLE( mb88 ); - - class mb88_cpu_device : public cpu_device { public: @@ -165,9 +162,7 @@ protected: virtual void state_export(const device_state_entry &entry) override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 2; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/mc68hc11/hc11dasm.cpp b/src/devices/cpu/mc68hc11/hc11dasm.cpp index 20ad20c4d0a..9fdc77409fe 100644 --- a/src/devices/cpu/mc68hc11/hc11dasm.cpp +++ b/src/devices/cpu/mc68hc11/hc11dasm.cpp @@ -7,33 +7,9 @@ */ #include "emu.h" +#include "hc11dasm.h" -enum -{ - EA_IMM8 = 1, - EA_IMM16, - EA_EXT, - EA_REL, - EA_DIRECT, - EA_DIRECT_IMM8, - EA_DIRECT_IMM8_REL, - EA_IND_X, - EA_IND_X_IMM8, - EA_IND_X_IMM8_REL, - EA_IND_Y, - EA_IND_Y_IMM8, - EA_IND_Y_IMM8_REL, - PAGE2, - PAGE3, - PAGE4 -}; - -struct M68HC11_OPCODE { - char mnemonic[32]; - int address_mode; -}; - -static const M68HC11_OPCODE opcode_table[256] = +const hc11_disassembler::M68HC11_OPCODE hc11_disassembler::opcode_table[256] = { /* 0x00 - 0x0f */ { "test", 0, }, @@ -313,7 +289,7 @@ static const M68HC11_OPCODE opcode_table[256] = /*****************************************************************************/ -static const M68HC11_OPCODE opcode_table_page2[256] = +const hc11_disassembler::M68HC11_OPCODE hc11_disassembler::opcode_table_page2[256] = { /* 0x00 - 0x0f */ { "?", 0, }, @@ -593,7 +569,7 @@ static const M68HC11_OPCODE opcode_table_page2[256] = /*****************************************************************************/ -static const M68HC11_OPCODE opcode_table_page3[256] = +const hc11_disassembler::M68HC11_OPCODE hc11_disassembler::opcode_table_page3[256] = { /* 0x00 - 0x0f */ { "?", 0, }, @@ -873,7 +849,7 @@ static const M68HC11_OPCODE opcode_table_page3[256] = /*****************************************************************************/ -static const M68HC11_OPCODE opcode_table_page4[256] = +const hc11_disassembler::M68HC11_OPCODE hc11_disassembler::opcode_table_page4[256] = { /* 0x00 - 0x0f */ { "?", 0, }, @@ -1152,137 +1128,126 @@ static const M68HC11_OPCODE opcode_table_page4[256] = /*****************************************************************************/ -static const uint8_t *rombase; - -static uint8_t fetch(void) +u32 hc11_disassembler::opcode_alignment() const { - return *rombase++; + return 1; } -static uint16_t fetch16(void) +offs_t hc11_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - uint16_t w; - w = (rombase[0] << 8) | rombase[1]; - rombase+=2; - return w; -} + offs_t cpc = pc; + + uint8_t opcode = opcodes.r8(cpc++); + const M68HC11_OPCODE *op_table = &opcode_table[opcode]; -static uint32_t decode_opcode(std::ostream &stream, uint32_t pc, const M68HC11_OPCODE *op_table) -{ uint8_t imm8, mask; int8_t rel8; uint16_t imm16; uint8_t op2; uint32_t flags = 0; + loop: if (!strcmp(op_table->mnemonic, "jsr") || !strcmp(op_table->mnemonic, "bsr")) - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; else if (!strcmp(op_table->mnemonic, "rts") || !strcmp(op_table->mnemonic, "rti")) - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; switch(op_table->address_mode) { case EA_IMM8: - imm8 = fetch(); + imm8 = opcodes.r8(cpc++); util::stream_format(stream, "%s 0x%02X", op_table->mnemonic, imm8); break; case EA_IMM16: - imm16 = fetch16(); + imm16 = opcodes.r16(cpc++); + cpc += 2; util::stream_format(stream, "%s 0x%04X", op_table->mnemonic, imm16); break; case EA_DIRECT: - imm8 = fetch(); + imm8 = opcodes.r8(cpc++); util::stream_format(stream, "%s (0x%04X)", op_table->mnemonic, imm8); break; case EA_EXT: - imm16 = fetch16(); + imm16 = opcodes.r16(cpc++); + cpc += 2; util::stream_format(stream, "%s (0x%04X)", op_table->mnemonic, imm16); break; case EA_IND_X: - imm8 = fetch(); + imm8 = opcodes.r8(cpc++); util::stream_format(stream, "%s (X+0x%02X)", op_table->mnemonic, imm8); break; case EA_REL: - rel8 = fetch(); + rel8 = opcodes.r8(cpc++); util::stream_format(stream, "%s [0x%04X]", op_table->mnemonic, pc+2+rel8); break; case EA_DIRECT_IMM8: - imm8 = fetch(); - mask = fetch(); + imm8 = opcodes.r8(cpc++); + mask = opcodes.r8(cpc++); util::stream_format(stream, "%s (0x%04X), 0x%02X", op_table->mnemonic, imm8, mask); break; case EA_IND_X_IMM8: - imm8 = fetch(); - mask = fetch(); + imm8 = opcodes.r8(cpc++); + mask = opcodes.r8(cpc++); util::stream_format(stream, "%s (X+0x%02X), 0x%02X", op_table->mnemonic, imm8, mask); break; case EA_DIRECT_IMM8_REL: - imm8 = fetch(); - mask = fetch(); - rel8 = fetch(); + imm8 = opcodes.r8(cpc++); + mask = opcodes.r8(cpc++); + rel8 = opcodes.r8(cpc++); util::stream_format(stream, "%s (0x%04X), 0x%02X, [0x%04X]", op_table->mnemonic, imm8, mask, pc+4+rel8); break; case EA_IND_X_IMM8_REL: - imm8 = fetch(); - mask = fetch(); - rel8 = fetch(); + imm8 = opcodes.r8(cpc++); + mask = opcodes.r8(cpc++); + rel8 = opcodes.r8(cpc++); util::stream_format(stream, "%s (X+0x%02X), 0x%02X, [0x%04X]", op_table->mnemonic, imm8, mask, pc+4+rel8); break; case EA_IND_Y: - imm8 = fetch(); + imm8 = opcodes.r8(cpc++); util::stream_format(stream, "%s (Y+0x%02X)", op_table->mnemonic, imm8); break; case EA_IND_Y_IMM8: - imm8 = fetch(); - mask = fetch(); + imm8 = opcodes.r8(cpc++); + mask = opcodes.r8(cpc++); util::stream_format(stream, "%s (Y+0x%02X), 0x%02X", op_table->mnemonic, imm8, mask); break; case EA_IND_Y_IMM8_REL: - imm8 = fetch(); - mask = fetch(); - rel8 = fetch(); + imm8 = opcodes.r8(cpc++); + mask = opcodes.r8(cpc++); + rel8 = opcodes.r8(cpc++); util::stream_format(stream, "%s (Y+0x%02X), 0x%02X, [0x%04X]", op_table->mnemonic, imm8, mask, pc+2+rel8); break; case PAGE2: - op2 = fetch(); - return decode_opcode(stream, pc, &opcode_table_page2[op2]); + op2 = opcodes.r8(cpc++); + op_table = &opcode_table_page2[op2]; + goto loop; case PAGE3: - op2 = fetch(); - return decode_opcode(stream, pc, &opcode_table_page3[op2]); + op2 = opcodes.r8(cpc++); + op_table = &opcode_table_page3[op2]; + goto loop; case PAGE4: - op2 = fetch(); - return decode_opcode(stream, pc, &opcode_table_page4[op2]); + op2 = opcodes.r8(cpc++); + op_table = &opcode_table_page4[op2]; + goto loop; default: util::stream_format(stream, "%s", op_table->mnemonic); } - return flags; -} - -CPU_DISASSEMBLE(hc11) -{ - uint32_t flags; - uint8_t opcode; - - rombase = oprom; - - opcode = fetch(); - flags = decode_opcode(stream, pc, &opcode_table[opcode]); - return (rombase-oprom) | flags | DASMFLAG_SUPPORTED; + return (cpc - pc) | flags | SUPPORTED; } diff --git a/src/devices/cpu/mc68hc11/hc11dasm.h b/src/devices/cpu/mc68hc11/hc11dasm.h new file mode 100644 index 00000000000..d1c606a964d --- /dev/null +++ b/src/devices/cpu/mc68hc11/hc11dasm.h @@ -0,0 +1,55 @@ +// license:BSD-3-Clause +// copyright-holders:Ville Linde +/* + Motorola M68HC11 disassembler + + Written by Ville Linde +*/ + +#ifndef MAME_CPU_MC68HC11_HC11DASM_H +#define MAME_CPU_MC68HC11_HC11DASM_H + +#pragma once + +class hc11_disassembler : public util::disasm_interface +{ +public: + hc11_disassembler() = default; + virtual ~hc11_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum + { + EA_IMM8 = 1, + EA_IMM16, + EA_EXT, + EA_REL, + EA_DIRECT, + EA_DIRECT_IMM8, + EA_DIRECT_IMM8_REL, + EA_IND_X, + EA_IND_X_IMM8, + EA_IND_X_IMM8_REL, + EA_IND_Y, + EA_IND_Y_IMM8, + EA_IND_Y_IMM8_REL, + PAGE2, + PAGE3, + PAGE4 + }; + + struct M68HC11_OPCODE { + char mnemonic[32]; + int address_mode; + }; + + static const M68HC11_OPCODE opcode_table[256]; + static const M68HC11_OPCODE opcode_table_page2[256]; + static const M68HC11_OPCODE opcode_table_page3[256]; + static const M68HC11_OPCODE opcode_table_page4[256]; +}; + +#endif diff --git a/src/devices/cpu/mc68hc11/mc68hc11.cpp b/src/devices/cpu/mc68hc11/mc68hc11.cpp index 1ecd2793529..76da1fbaf8c 100644 --- a/src/devices/cpu/mc68hc11/mc68hc11.cpp +++ b/src/devices/cpu/mc68hc11/mc68hc11.cpp @@ -16,6 +16,7 @@ TODO: #include "emu.h" #include "debugger.h" #include "mc68hc11.h" +#include "hc11dasm.h" enum { @@ -61,10 +62,9 @@ device_memory_interface::space_config_vector mc68hc11_cpu_device::memory_space_c }; } -offs_t mc68hc11_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *mc68hc11_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( hc11 ); - return CPU_DISASSEMBLE_NAME(hc11)(this, stream, pc, oprom, opram, options); + return new hc11_disassembler; } diff --git a/src/devices/cpu/mc68hc11/mc68hc11.h b/src/devices/cpu/mc68hc11/mc68hc11.h index e2a1f52f3d7..cb8c0813e4d 100644 --- a/src/devices/cpu/mc68hc11/mc68hc11.h +++ b/src/devices/cpu/mc68hc11/mc68hc11.h @@ -70,9 +70,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 5; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/mcs40/mcs40.cpp b/src/devices/cpu/mcs40/mcs40.cpp index 866587579d3..b954d292458 100644 --- a/src/devices/cpu/mcs40/mcs40.cpp +++ b/src/devices/cpu/mcs40/mcs40.cpp @@ -9,6 +9,7 @@ *****************************************************************************/ #include "emu.h" #include "mcs40.h" +#include "mcs40dasm.h" #include "debugger.h" @@ -415,21 +416,6 @@ void mcs40_cpu_device_base::state_string_export(device_state_entry const &entry, } -/*********************************************************************** - device_disasm_interface implementation -***********************************************************************/ - -u32 mcs40_cpu_device_base::disasm_min_opcode_bytes() const -{ - return 1U; -} - -u32 mcs40_cpu_device_base::disasm_max_opcode_bytes() const -{ - return 2U; -} - - /*********************************************************************** register access ***********************************************************************/ @@ -874,15 +860,9 @@ void i4004_cpu_device::execute_set_input(int inputnum, int state) device_disasm_interface implementation ***********************************************************************/ -offs_t i4004_cpu_device::disasm_disassemble( - std::ostream &stream, - offs_t pc, - uint8_t const *oprom, - uint8_t const *opram, - uint32_t options) +util::disasm_interface *i4004_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE(i4004); - return CPU_DISASSEMBLE_NAME(i4004)(this, stream, pc, oprom, opram, options); + return new i4004_disassembler; } @@ -1190,15 +1170,9 @@ void i4040_cpu_device::execute_set_input(int inputnum, int state) device_disasm_interface implementation ***********************************************************************/ -offs_t i4040_cpu_device::disasm_disassemble( - std::ostream &stream, - offs_t pc, - uint8_t const *oprom, - uint8_t const *opram, - uint32_t options) +util::disasm_interface *i4040_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE(i4040); - return CPU_DISASSEMBLE_NAME(i4040)(this, stream, pc, oprom, opram, options); + return new i4040_disassembler; } diff --git a/src/devices/cpu/mcs40/mcs40.h b/src/devices/cpu/mcs40/mcs40.h index 42302263d50..5c2bab6a5ee 100644 --- a/src/devices/cpu/mcs40/mcs40.h +++ b/src/devices/cpu/mcs40/mcs40.h @@ -200,10 +200,6 @@ protected: virtual void state_export(device_state_entry const &entry) override; virtual void state_string_export(device_state_entry const &entry, std::string &str) const override; - // device_disasm_interface implementation - virtual u32 disasm_min_opcode_bytes() const override; - virtual u32 disasm_max_opcode_bytes() const override; - // instruction execution virtual bool is_io_op(u8 opr) = 0; virtual cycle do_cycle1(u8 opr, u8 opa, pmem &program_op) = 0; @@ -378,12 +374,7 @@ protected: virtual void execute_set_input(int inputnum, int state) override; // device_disasm_interface implementation - virtual offs_t disasm_disassemble( - std::ostream &stream, - offs_t pc, - uint8_t const *oprom, - uint8_t const *opram, - uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // mcs40_cpu_device_base implementation virtual bool is_io_op(u8 opr) override; @@ -417,12 +408,7 @@ public: protected: // device_disasm_interface implementation - virtual offs_t disasm_disassemble( - std::ostream &stream, - offs_t pc, - uint8_t const *oprom, - uint8_t const *opram, - uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // device_execute_interface implementation virtual u32 execute_input_lines() const override; diff --git a/src/devices/cpu/mcs40/mcs40dasm.cpp b/src/devices/cpu/mcs40/mcs40dasm.cpp index 3ecf5712308..fbc938f61c1 100644 --- a/src/devices/cpu/mcs40/mcs40dasm.cpp +++ b/src/devices/cpu/mcs40/mcs40dasm.cpp @@ -9,96 +9,68 @@ *****************************************************************************/ #include "emu.h" +#include "mcs40dasm.h" -namespace { - -enum class format -{ - ILL, - SIMPLE, - IMM4, - REG, - REGPAGE, - PAIR, - PAIRIMM, - ABS, - PAGE, - COND, - EXT -}; - -enum class level -{ - I4004, - I4040 -}; - -struct op -{ - format m_format; - level m_level; - char const *m_name; - op const *m_ext; -}; #define OP(fmt, lvl, name) { format::fmt, level::lvl, #name, nullptr } #define OPX(tbl) { format::EXT, level::I4004, nullptr, f_opx_##tbl } -op const f_opx_0[16] = { +mcs40_disassembler::op const mcs40_disassembler::f_opx_0[16] = { OP(SIMPLE, I4004, nop), OP(SIMPLE, I4040, hlt), OP(SIMPLE, I4040, bbs), OP(SIMPLE, I4040, lcr), OP(SIMPLE, I4040, or4), OP(SIMPLE, I4040, or5), OP(SIMPLE, I4040, an6), OP(SIMPLE, I4040, an7), OP(SIMPLE, I4040, db0), OP(SIMPLE, I4040, db1), OP(SIMPLE, I4040, sb0), OP(SIMPLE, I4040, sb1), OP(SIMPLE, I4040, ein), OP(SIMPLE, I4040, din), OP(SIMPLE, I4040, rpm), OP(ILL, I4004, ill) }; -op const f_opx_2[16] = { +mcs40_disassembler::op const mcs40_disassembler::f_opx_2[16] = { OP(PAIRIMM, I4004, fim), OP(PAIR, I4004, src), OP(PAIRIMM, I4004, fim), OP(PAIR, I4004, src), OP(PAIRIMM, I4004, fim), OP(PAIR, I4004, src), OP(PAIRIMM, I4004, fim), OP(PAIR, I4004, src), OP(PAIRIMM, I4004, fim), OP(PAIR, I4004, src), OP(PAIRIMM, I4004, fim), OP(PAIR, I4004, src), OP(PAIRIMM, I4004, fim), OP(PAIR, I4004, src), OP(PAIRIMM, I4004, fim), OP(PAIR, I4004, src) }; -op const f_opx_3[16] = { +mcs40_disassembler::op const mcs40_disassembler::f_opx_3[16] = { OP(PAIR, I4004, fin), OP(PAIR, I4004, jin), OP(PAIR, I4004, fin), OP(PAIR, I4004, jin), OP(PAIR, I4004, fin), OP(PAIR, I4004, jin), OP(PAIR, I4004, fin), OP(PAIR, I4004, jin), OP(PAIR, I4004, fin), OP(PAIR, I4004, jin), OP(PAIR, I4004, fin), OP(PAIR, I4004, jin), OP(PAIR, I4004, fin), OP(PAIR, I4004, jin), OP(PAIR, I4004, fin), OP(PAIR, I4004, jin) }; -op const f_opx_io[16] = { +mcs40_disassembler::op const mcs40_disassembler::f_opx_io[16] = { OP(SIMPLE, I4004, wrm), OP(SIMPLE, I4004, wmp), OP(SIMPLE, I4004, wrr), OP(SIMPLE, I4004, wpm), OP(SIMPLE, I4004, wr0), OP(SIMPLE, I4004, wr1), OP(SIMPLE, I4004, wr2), OP(SIMPLE, I4004, wr3), OP(SIMPLE, I4004, sbm), OP(SIMPLE, I4004, rdm), OP(SIMPLE, I4004, rdr), OP(SIMPLE, I4004, adm), OP(SIMPLE, I4004, rd0), OP(SIMPLE, I4004, rd1), OP(SIMPLE, I4004, rd2), OP(SIMPLE, I4004, rd3) }; -op const f_opx_f[16] = { +mcs40_disassembler::op const mcs40_disassembler::f_opx_f[16] = { OP(SIMPLE, I4004, clb), OP(SIMPLE, I4004, clc), OP(SIMPLE, I4004, iac), OP(SIMPLE, I4004, cmc), OP(SIMPLE, I4004, cma), OP(SIMPLE, I4004, ral), OP(SIMPLE, I4004, rar), OP(SIMPLE, I4004, tcc), OP(SIMPLE, I4004, dac), OP(SIMPLE, I4004, tcs), OP(SIMPLE, I4004, stc), OP(SIMPLE, I4004, daa), OP(SIMPLE, I4004, kbp), OP(SIMPLE, I4004, dcl), OP(ILL, I4004, ill), OP(ILL, I4004, ill) }; -op const f_ops[16] = { +mcs40_disassembler::op const mcs40_disassembler::f_ops[16] = { OPX(0), OP(COND, I4004, jcn), OPX(2), OPX(3), OP(ABS, I4004, jun), OP(ABS, I4004, jms), OP(REG, I4004, inc), OP(REGPAGE, I4004, isz), OP(REG, I4004, add), OP(REG, I4004, sub), OP(REG, I4004, ld ), OP(REG, I4004, xch), OP(IMM4, I4004, bbl), OP(IMM4, I4004, ldm), OPX(io), OPX(f) }; -char const *const f_cond[16] = { +char const *const mcs40_disassembler::f_cond[16] = { "$0", "nt", "c", "$3", "z", "$5", "$6", "$7", "$8", "t", "nc", "$b", "nz", "$d", "$e", "$f" }; -offs_t disassemble( - cpu_device *device, - std::ostream &stream, - offs_t pc, - u8 const *oprom, - u8 const *opram, - int options, - level lvl, - unsigned pcmask) +u32 mcs40_disassembler::opcode_alignment() const +{ + return 1; +} + +mcs40_disassembler::mcs40_disassembler(level lvl, unsigned pcmask) : m_lvl(lvl), m_pcmask(pcmask) +{ +} + +offs_t mcs40_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { offs_t npc(pc + 1); - u8 const opcode(oprom[0]); + u8 const opcode(opcodes.r8(pc)); op const &base_op(f_ops[(opcode >> 4) & 0x0f]); op const &ext_op((base_op.m_format == format::EXT) ? base_op.m_ext[opcode & 0x0f] : base_op); - op const desc((ext_op.m_level > lvl) ? f_opx_f[0x0f] : ext_op); + op const desc((ext_op.m_level > m_lvl) ? f_opx_f[0x0f] : ext_op); u8 const imm4(opcode & 0x0f); u8 const pair(opcode & 0x0e); @@ -118,26 +90,26 @@ offs_t disassemble( break; case format::REGPAGE: npc++; - util::stream_format(stream, "%-3s r%01x,$%03x", desc.m_name, imm4, oprom[1] | (npc & 0x0f00U)); + util::stream_format(stream, "%-3s r%01x,$%03x", desc.m_name, imm4, opcodes.r8(pc+1) | (npc & 0x0f00U)); break; case format::PAIR: util::stream_format(stream, "%-3s r%01xr%01x", desc.m_name, pair, pair + 1U); break; case format::PAIRIMM: npc++; - util::stream_format(stream, "%-3s r%01xr%01x,$%02x", desc.m_name, pair, pair + 1, oprom[1]); + util::stream_format(stream, "%-3s r%01xr%01x,$%02x", desc.m_name, pair, pair + 1, opcodes.r8(pc+1)); break; case format::ABS: npc++; - util::stream_format(stream, "%-3s $%03x", desc.m_name, ((u16(opcode) & 0x0fU) << 8) | oprom[1]); + util::stream_format(stream, "%-3s $%03x", desc.m_name, ((u16(opcode) & 0x0fU) << 8) | opcodes.r8(pc+1)); break; case format::PAGE: npc++; - util::stream_format(stream, "%-3s $%03x", desc.m_name, oprom[1] | (npc & 0x0f00U)); + util::stream_format(stream, "%-3s $%03x", desc.m_name, opcodes.r8(pc+1) | (npc & 0x0f00U)); break; case format::COND: npc++; - util::stream_format(stream, "%-3s %s,$%03x", desc.m_name, f_cond[imm4], oprom[1] | (npc & 0x0f00U)); + util::stream_format(stream, "%-3s %s,$%03x", desc.m_name, f_cond[imm4], opcodes.r8(pc+1) | (npc & 0x0f00U)); break; default: throw false; @@ -147,16 +119,19 @@ offs_t disassemble( if (format::ILL != desc.m_format) { if (0x50U == (opcode & 0xf0U)) // JMS - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; else if ((0xc0 == (opcode & 0xf0)) || (0x02 == opcode)) // BBL/BBS - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; } - return (npc - pc) | flags | DASMFLAG_SUPPORTED; + return (npc - pc) | flags | SUPPORTED; } -} // anonymous namespace +i4004_disassembler::i4004_disassembler() : mcs40_disassembler(level::I4004, 0x0fffU) +{ +} -CPU_DISASSEMBLE(i4004) { return disassemble(device, stream, pc, oprom, opram, options, level::I4004, 0x0fffU); } -CPU_DISASSEMBLE(i4040) { return disassemble(device, stream, pc, oprom, opram, options, level::I4040, 0x1fffU); } +i4040_disassembler::i4040_disassembler() : mcs40_disassembler(level::I4040, 0x1fffU) +{ +} diff --git a/src/devices/cpu/mcs40/mcs40dasm.h b/src/devices/cpu/mcs40/mcs40dasm.h new file mode 100644 index 00000000000..937b71d9358 --- /dev/null +++ b/src/devices/cpu/mcs40/mcs40dasm.h @@ -0,0 +1,81 @@ +// license:BSD-3-Clause +// copyright-holders:Vas Crabb +/***************************************************************************** + * + * 4004dasm.cpp + * + * Intel MCS-40 CPU Disassembly + * + *****************************************************************************/ + +#ifndef MAME_CPU_MCS40_MCS40DASM_H +#define MAME_CPU_MCS40_MCS40DASM_H + +#pragma once + +class mcs40_disassembler : public util::disasm_interface +{ +public: + enum class level + { + I4004, + I4040 + }; + + mcs40_disassembler(level lvl, unsigned pcmask); + virtual ~mcs40_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum class format + { + ILL, + SIMPLE, + IMM4, + REG, + REGPAGE, + PAIR, + PAIRIMM, + ABS, + PAGE, + COND, + EXT + }; + + struct op + { + format m_format; + level m_level; + char const *m_name; + op const *m_ext; + }; + + static op const f_opx_0[16]; + static op const f_opx_2[16]; + static op const f_opx_3[16]; + static op const f_opx_io[16]; + static op const f_opx_f[16]; + static op const f_ops[16]; + static char const *const f_cond[16]; + + level m_lvl; + unsigned m_pcmask; +}; + +class i4004_disassembler : public mcs40_disassembler +{ +public: + i4004_disassembler(); + virtual ~i4004_disassembler() = default; +}; + +class i4040_disassembler : public mcs40_disassembler +{ +public: + i4040_disassembler(); + virtual ~i4040_disassembler() = default; +}; + +#endif diff --git a/src/devices/cpu/mcs48/mcs48.cpp b/src/devices/cpu/mcs48/mcs48.cpp index dfe68df8b4c..75d70a93480 100644 --- a/src/devices/cpu/mcs48/mcs48.cpp +++ b/src/devices/cpu/mcs48/mcs48.cpp @@ -85,6 +85,7 @@ #include "emu.h" #include "debugger.h" #include "mcs48.h" +#include "mcs48dsm.h" /*************************************************************************** @@ -329,17 +330,14 @@ device_memory_interface::space_config_vector mcs48_cpu_device::memory_space_conf }; } -offs_t mcs48_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *mcs48_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( mcs48 ); - return CPU_DISASSEMBLE_NAME(mcs48)(this, stream, pc, oprom, opram, options); + return new mcs48_disassembler(false); } - -offs_t upi41_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *upi41_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( upi41 ); - return CPU_DISASSEMBLE_NAME(upi41)(this, stream, pc, oprom, opram, options); + return new mcs48_disassembler(true); } /*************************************************************************** diff --git a/src/devices/cpu/mcs48/mcs48.h b/src/devices/cpu/mcs48/mcs48.h index f718fde7c0b..6594a837d5d 100644 --- a/src/devices/cpu/mcs48/mcs48.h +++ b/src/devices/cpu/mcs48/mcs48.h @@ -180,9 +180,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 2; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; protected: address_space_config m_program_config; @@ -650,7 +648,7 @@ protected: // construction/destruction upi41_cpu_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock, int rom_size, int ram_size); - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; TIMER_CALLBACK_MEMBER( master_callback ); }; diff --git a/src/devices/cpu/mcs48/mcs48dsm.cpp b/src/devices/cpu/mcs48/mcs48dsm.cpp index 08afa12f6b3..e265e83534e 100644 --- a/src/devices/cpu/mcs48/mcs48dsm.cpp +++ b/src/devices/cpu/mcs48/mcs48dsm.cpp @@ -10,27 +10,35 @@ ***************************************************************************/ #include "emu.h" +#include "mcs48dsm.h" +mcs48_disassembler::mcs48_disassembler(bool upi41) : m_upi41(upi41) +{ +} -static uint32_t common_dasm(device_t *device, std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, bool upi41) +u32 mcs48_disassembler::opcode_alignment() const { - const uint8_t *startram = opram; - uint32_t flags = 0; + return 1; +} - opram++; - switch (*oprom++) +offs_t mcs48_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + offs_t cpc = pc; + offs_t flags = 0; + + switch (opcodes.r8(cpc++)) { case 0x00: util::stream_format(stream, "nop"); break; - case 0x02: if (!upi41) + case 0x02: if (!m_upi41) util::stream_format(stream, "out bus,a"); else util::stream_format(stream, "out dbb,a"); break; - case 0x03: util::stream_format(stream, "add a,#$%02X", *opram++); break; - case 0x04: util::stream_format(stream, "jmp $0%02X", *opram++); break; + case 0x03: util::stream_format(stream, "add a,#$%02X", params.r8(cpc++)); break; + case 0x04: util::stream_format(stream, "jmp $0%02X", params.r8(cpc++)); break; case 0x05: util::stream_format(stream, "en i"); break; case 0x07: util::stream_format(stream, "dec a"); break; - case 0x08: if (!upi41) + case 0x08: if (!m_upi41) util::stream_format(stream, "in a,bus"); else util::stream_format(stream, "illegal"); @@ -43,11 +51,11 @@ static uint32_t common_dasm(device_t *device, std::ostream &stream, offs_t pc, c case 0x0f: util::stream_format(stream, "movd a,p7"); break; case 0x10: util::stream_format(stream, "inc @r0"); break; case 0x11: util::stream_format(stream, "inc @r1"); break; - case 0x12: util::stream_format(stream, "jb0 $%03X", (pc & 0xf00) | *opram++); break; - case 0x13: util::stream_format(stream, "addc a,#$%02X", *opram++); break; - case 0x14: util::stream_format(stream, "call $0%02X", *opram++); flags = DASMFLAG_STEP_OVER; break; + case 0x12: util::stream_format(stream, "jb0 $%03X", (pc & 0xf00) | params.r8(cpc++)); break; + case 0x13: util::stream_format(stream, "addc a,#$%02X", params.r8(cpc++)); break; + case 0x14: util::stream_format(stream, "call $0%02X", params.r8(cpc++)); flags = STEP_OVER; break; case 0x15: util::stream_format(stream, "dis i"); break; - case 0x16: util::stream_format(stream, "jtf $%03X", (pc & 0xf00) | *opram++); break; + case 0x16: util::stream_format(stream, "jtf $%03X", (pc & 0xf00) | params.r8(cpc++)); break; case 0x17: util::stream_format(stream, "inc a"); break; case 0x18: util::stream_format(stream, "inc r0"); break; case 0x19: util::stream_format(stream, "inc r1"); break; @@ -59,15 +67,15 @@ static uint32_t common_dasm(device_t *device, std::ostream &stream, offs_t pc, c case 0x1f: util::stream_format(stream, "inc r7"); break; case 0x20: util::stream_format(stream, "xch a,@r0"); break; case 0x21: util::stream_format(stream, "xch a,@r1"); break; - case 0x22: if (!upi41) + case 0x22: if (!m_upi41) util::stream_format(stream, "illegal"); else util::stream_format(stream, "in a,dbb"); break; - case 0x23: util::stream_format(stream, "mov a,#$%02X", *opram++); break; - case 0x24: util::stream_format(stream, "jmp $1%02X", *opram++); break; + case 0x23: util::stream_format(stream, "mov a,#$%02X", params.r8(cpc++)); break; + case 0x24: util::stream_format(stream, "jmp $1%02X", params.r8(cpc++)); break; case 0x25: util::stream_format(stream, "en tcnti"); break; - case 0x26: util::stream_format(stream, "jnt0 $%03X", (pc & 0xf00) | *opram++); break; + case 0x26: util::stream_format(stream, "jnt0 $%03X", (pc & 0xf00) | params.r8(cpc++)); break; case 0x27: util::stream_format(stream, "clr a"); break; case 0x28: util::stream_format(stream, "xch a,r0"); break; case 0x29: util::stream_format(stream, "xch a,r1"); break; @@ -79,10 +87,10 @@ static uint32_t common_dasm(device_t *device, std::ostream &stream, offs_t pc, c case 0x2f: util::stream_format(stream, "xch a,r7"); break; case 0x30: util::stream_format(stream, "xchd a,@r0"); break; case 0x31: util::stream_format(stream, "xchd a,@r1"); break; - case 0x32: util::stream_format(stream, "jb1 $%03X", (pc & 0xf00) | *opram++); break; - case 0x34: util::stream_format(stream, "call $1%02X", *opram++); flags = DASMFLAG_STEP_OVER; break; + case 0x32: util::stream_format(stream, "jb1 $%03X", (pc & 0xf00) | params.r8(cpc++)); break; + case 0x34: util::stream_format(stream, "call $1%02X", params.r8(cpc++)); flags = STEP_OVER; break; case 0x35: util::stream_format(stream, "dis tcnti"); break; - case 0x36: util::stream_format(stream, "jt0 $%03X", (pc & 0xf00) | *opram++); break; + case 0x36: util::stream_format(stream, "jt0 $%03X", (pc & 0xf00) | params.r8(cpc++)); break; case 0x37: util::stream_format(stream, "cpl a"); break; case 0x39: util::stream_format(stream, "outl p1,a"); break; case 0x3a: util::stream_format(stream, "outl p2,a"); break; @@ -93,10 +101,10 @@ static uint32_t common_dasm(device_t *device, std::ostream &stream, offs_t pc, c case 0x40: util::stream_format(stream, "orl a,@r0"); break; case 0x41: util::stream_format(stream, "orl a,@r1"); break; case 0x42: util::stream_format(stream, "mov a,t"); break; - case 0x43: util::stream_format(stream, "orl a,#$%02X", *opram++); break; - case 0x44: util::stream_format(stream, "jmp $2%02X", *opram++); break; + case 0x43: util::stream_format(stream, "orl a,#$%02X", params.r8(cpc++)); break; + case 0x44: util::stream_format(stream, "jmp $2%02X", params.r8(cpc++)); break; case 0x45: util::stream_format(stream, "strt cnt"); break; - case 0x46: util::stream_format(stream, "jnt1 $%03X", (pc & 0xf00) | *opram++); break; + case 0x46: util::stream_format(stream, "jnt1 $%03X", (pc & 0xf00) | params.r8(cpc++)); break; case 0x47: util::stream_format(stream, "swap a"); break; case 0x48: util::stream_format(stream, "orl a,r0"); break; case 0x49: util::stream_format(stream, "orl a,r1"); break; @@ -108,11 +116,11 @@ static uint32_t common_dasm(device_t *device, std::ostream &stream, offs_t pc, c case 0x4f: util::stream_format(stream, "orl a,r7"); break; case 0x50: util::stream_format(stream, "anl a,@r0"); break; case 0x51: util::stream_format(stream, "anl a,@r1"); break; - case 0x52: util::stream_format(stream, "jb2 $%03X", (pc & 0xf00) | *opram++); break; - case 0x53: util::stream_format(stream, "anl a,#$%02X", *opram++); break; - case 0x54: util::stream_format(stream, "call $2%02X", *opram++); flags = DASMFLAG_STEP_OVER; break; + case 0x52: util::stream_format(stream, "jb2 $%03X", (pc & 0xf00) | params.r8(cpc++)); break; + case 0x53: util::stream_format(stream, "anl a,#$%02X", params.r8(cpc++)); break; + case 0x54: util::stream_format(stream, "call $2%02X", params.r8(cpc++)); flags = STEP_OVER; break; case 0x55: util::stream_format(stream, "strt t"); break; - case 0x56: util::stream_format(stream, "jt1 $%03X", (pc & 0xf00) | *opram++); break; + case 0x56: util::stream_format(stream, "jt1 $%03X", (pc & 0xf00) | params.r8(cpc++)); break; case 0x57: util::stream_format(stream, "da a"); break; case 0x58: util::stream_format(stream, "anl a,r0"); break; case 0x59: util::stream_format(stream, "anl a,r1"); break; @@ -125,7 +133,7 @@ static uint32_t common_dasm(device_t *device, std::ostream &stream, offs_t pc, c case 0x60: util::stream_format(stream, "add a,@r0"); break; case 0x61: util::stream_format(stream, "add a,@r1"); break; case 0x62: util::stream_format(stream, "mov t,a"); break; - case 0x64: util::stream_format(stream, "jmp $3%02X", *opram++); break; + case 0x64: util::stream_format(stream, "jmp $3%02X", params.r8(cpc++)); break; case 0x65: util::stream_format(stream, "stop tcnt"); break; case 0x67: util::stream_format(stream, "rrc a"); break; case 0x68: util::stream_format(stream, "add a,r0"); break; @@ -138,14 +146,14 @@ static uint32_t common_dasm(device_t *device, std::ostream &stream, offs_t pc, c case 0x6f: util::stream_format(stream, "add a,r7"); break; case 0x70: util::stream_format(stream, "addc a,@r0"); break; case 0x71: util::stream_format(stream, "addc a,@r1"); break; - case 0x72: util::stream_format(stream, "jb3 $%03X", (pc & 0xf00) | *opram++); break; - case 0x74: util::stream_format(stream, "call $3%02X", *opram++); flags = DASMFLAG_STEP_OVER; break; - case 0x75: if (!upi41) + case 0x72: util::stream_format(stream, "jb3 $%03X", (pc & 0xf00) | params.r8(cpc++)); break; + case 0x74: util::stream_format(stream, "call $3%02X", params.r8(cpc++)); flags = STEP_OVER; break; + case 0x75: if (!m_upi41) util::stream_format(stream, "ent0 clk"); else util::stream_format(stream, "illegal"); break; - case 0x76: util::stream_format(stream, "jf1 $%03X", (pc & 0xf00) | *opram++); break; + case 0x76: util::stream_format(stream, "jf1 $%03X", (pc & 0xf00) | params.r8(cpc++)); break; case 0x77: util::stream_format(stream, "rr a"); break; case 0x78: util::stream_format(stream, "addc a,r0"); break; case 0x79: util::stream_format(stream, "addc a,r1"); break; @@ -155,58 +163,58 @@ static uint32_t common_dasm(device_t *device, std::ostream &stream, offs_t pc, c case 0x7d: util::stream_format(stream, "addc a,r5"); break; case 0x7e: util::stream_format(stream, "addc a,r6"); break; case 0x7f: util::stream_format(stream, "addc a,r7"); break; - case 0x80: if (!upi41) + case 0x80: if (!m_upi41) util::stream_format(stream, "movx a,@r0"); else util::stream_format(stream, "illegal"); break; - case 0x81: if (!upi41) + case 0x81: if (!m_upi41) util::stream_format(stream, "movx a,@r1"); else util::stream_format(stream, "illegal"); break; - case 0x83: util::stream_format(stream, "ret"); flags = DASMFLAG_STEP_OUT; break; - case 0x84: util::stream_format(stream, "jmp $4%02X", *opram++); break; + case 0x83: util::stream_format(stream, "ret"); flags = STEP_OUT; break; + case 0x84: util::stream_format(stream, "jmp $4%02X", params.r8(cpc++)); break; case 0x85: util::stream_format(stream, "clr f0"); break; - case 0x86: if (!upi41) - util::stream_format(stream, "jni $%03X", (pc & 0xf00) | *opram++); + case 0x86: if (!m_upi41) + util::stream_format(stream, "jni $%03X", (pc & 0xf00) | params.r8(cpc++)); else - util::stream_format(stream, "jobf $%03X", (pc & 0xf00) | *opram++); + util::stream_format(stream, "jobf $%03X", (pc & 0xf00) | params.r8(cpc++)); break; - case 0x88: if (!upi41) - util::stream_format(stream, "orl bus,#$%02X", *opram++); + case 0x88: if (!m_upi41) + util::stream_format(stream, "orl bus,#$%02X", params.r8(cpc++)); else util::stream_format(stream, "illegal"); break; - case 0x89: util::stream_format(stream, "orl p1,#$%02X", *opram++); break; - case 0x8a: util::stream_format(stream, "orl p2,#$%02X", *opram++); break; + case 0x89: util::stream_format(stream, "orl p1,#$%02X", params.r8(cpc++)); break; + case 0x8a: util::stream_format(stream, "orl p2,#$%02X", params.r8(cpc++)); break; case 0x8c: util::stream_format(stream, "orld p4,a"); break; case 0x8d: util::stream_format(stream, "orld p5,a"); break; case 0x8e: util::stream_format(stream, "orld p6,a"); break; case 0x8f: util::stream_format(stream, "orld p7,a"); break; - case 0x90: if (!upi41) + case 0x90: if (!m_upi41) util::stream_format(stream, "movx @r0,a"); else util::stream_format(stream, "mov sts,a"); break; - case 0x91: if (!upi41) + case 0x91: if (!m_upi41) util::stream_format(stream, "movx @r1,a"); else util::stream_format(stream, "illegal"); break; - case 0x92: util::stream_format(stream, "jb4 $%03X", (pc & 0xf00) | *opram++); break; - case 0x93: util::stream_format(stream, "retr"); flags = DASMFLAG_STEP_OUT; break; - case 0x94: util::stream_format(stream, "call $4%02X", *opram++); flags = DASMFLAG_STEP_OVER; break; + case 0x92: util::stream_format(stream, "jb4 $%03X", (pc & 0xf00) | params.r8(cpc++)); break; + case 0x93: util::stream_format(stream, "retr"); flags = STEP_OUT; break; + case 0x94: util::stream_format(stream, "call $4%02X", params.r8(cpc++)); flags = STEP_OVER; break; case 0x95: util::stream_format(stream, "cpl f0"); break; - case 0x96: util::stream_format(stream, "jnz $%03X", (pc & 0xf00) | *opram++); break; + case 0x96: util::stream_format(stream, "jnz $%03X", (pc & 0xf00) | params.r8(cpc++)); break; case 0x97: util::stream_format(stream, "clr c"); break; - case 0x98: if (!upi41) - util::stream_format(stream, "anl bus,#$%02X", *opram++); + case 0x98: if (!m_upi41) + util::stream_format(stream, "anl bus,#$%02X", params.r8(cpc++)); else util::stream_format(stream, "illegal"); break; - case 0x99: util::stream_format(stream, "anl p1,#$%02X", *opram++); break; - case 0x9a: util::stream_format(stream, "anl p2,#$%02X", *opram++); break; + case 0x99: util::stream_format(stream, "anl p1,#$%02X", params.r8(cpc++)); break; + case 0x9a: util::stream_format(stream, "anl p2,#$%02X", params.r8(cpc++)); break; case 0x9c: util::stream_format(stream, "anld p4,a"); break; case 0x9d: util::stream_format(stream, "anld p5,a"); break; case 0x9e: util::stream_format(stream, "anld p6,a"); break; @@ -214,7 +222,7 @@ static uint32_t common_dasm(device_t *device, std::ostream &stream, offs_t pc, c case 0xa0: util::stream_format(stream, "mov @r0,a"); break; case 0xa1: util::stream_format(stream, "mov @r1,a"); break; case 0xa3: util::stream_format(stream, "movp a,@a"); break; - case 0xa4: util::stream_format(stream, "jmp $5%02X", *opram++); break; + case 0xa4: util::stream_format(stream, "jmp $5%02X", params.r8(cpc++)); break; case 0xa5: util::stream_format(stream, "clr f1"); break; case 0xa7: util::stream_format(stream, "cpl c"); break; case 0xa8: util::stream_format(stream, "mov r0,a"); break; @@ -225,24 +233,24 @@ static uint32_t common_dasm(device_t *device, std::ostream &stream, offs_t pc, c case 0xad: util::stream_format(stream, "mov r5,a"); break; case 0xae: util::stream_format(stream, "mov r6,a"); break; case 0xaf: util::stream_format(stream, "mov r7,a"); break; - case 0xb0: util::stream_format(stream, "mov @r0,#$%02X", *opram++); break; - case 0xb1: util::stream_format(stream, "mov @r1,#$%02X", *opram++); break; - case 0xb2: util::stream_format(stream, "jb5 $%03X", (pc & 0xf00) | *opram++); break; + case 0xb0: util::stream_format(stream, "mov @r0,#$%02X", params.r8(cpc++)); break; + case 0xb1: util::stream_format(stream, "mov @r1,#$%02X", params.r8(cpc++)); break; + case 0xb2: util::stream_format(stream, "jb5 $%03X", (pc & 0xf00) | params.r8(cpc++)); break; case 0xb3: util::stream_format(stream, "jmpp @a"); break; - case 0xb4: util::stream_format(stream, "call $5%02X", *opram++); flags = DASMFLAG_STEP_OVER; break; + case 0xb4: util::stream_format(stream, "call $5%02X", params.r8(cpc++)); flags = STEP_OVER; break; case 0xb5: util::stream_format(stream, "cpl f1"); break; - case 0xb6: util::stream_format(stream, "jf0 $%03X", (pc & 0xf00) | *opram++); break; - case 0xb8: util::stream_format(stream, "mov r0,#$%02X", *opram++); break; - case 0xb9: util::stream_format(stream, "mov r1,#$%02X", *opram++); break; - case 0xba: util::stream_format(stream, "mov r2,#$%02X", *opram++); break; - case 0xbb: util::stream_format(stream, "mov r3,#$%02X", *opram++); break; - case 0xbc: util::stream_format(stream, "mov r4,#$%02X", *opram++); break; - case 0xbd: util::stream_format(stream, "mov r5,#$%02X", *opram++); break; - case 0xbe: util::stream_format(stream, "mov r6,#$%02X", *opram++); break; - case 0xbf: util::stream_format(stream, "mov r7,#$%02X", *opram++); break; - case 0xc4: util::stream_format(stream, "jmp $6%02X", *opram++); break; + case 0xb6: util::stream_format(stream, "jf0 $%03X", (pc & 0xf00) | params.r8(cpc++)); break; + case 0xb8: util::stream_format(stream, "mov r0,#$%02X", params.r8(cpc++)); break; + case 0xb9: util::stream_format(stream, "mov r1,#$%02X", params.r8(cpc++)); break; + case 0xba: util::stream_format(stream, "mov r2,#$%02X", params.r8(cpc++)); break; + case 0xbb: util::stream_format(stream, "mov r3,#$%02X", params.r8(cpc++)); break; + case 0xbc: util::stream_format(stream, "mov r4,#$%02X", params.r8(cpc++)); break; + case 0xbd: util::stream_format(stream, "mov r5,#$%02X", params.r8(cpc++)); break; + case 0xbe: util::stream_format(stream, "mov r6,#$%02X", params.r8(cpc++)); break; + case 0xbf: util::stream_format(stream, "mov r7,#$%02X", params.r8(cpc++)); break; + case 0xc4: util::stream_format(stream, "jmp $6%02X", params.r8(cpc++)); break; case 0xc5: util::stream_format(stream, "sel rb0"); break; - case 0xc6: util::stream_format(stream, "jz $%03X", (pc & 0xf00) | *opram++); break; + case 0xc6: util::stream_format(stream, "jz $%03X", (pc & 0xf00) | params.r8(cpc++)); break; case 0xc7: util::stream_format(stream, "mov a,psw"); break; case 0xc8: util::stream_format(stream, "dec r0"); break; case 0xc9: util::stream_format(stream, "dec r1"); break; @@ -254,14 +262,14 @@ static uint32_t common_dasm(device_t *device, std::ostream &stream, offs_t pc, c case 0xcf: util::stream_format(stream, "dec r7"); break; case 0xd0: util::stream_format(stream, "xrl a,@r0"); break; case 0xd1: util::stream_format(stream, "xrl a,@r1"); break; - case 0xd2: util::stream_format(stream, "jb6 $%03X", (pc & 0xf00) | *opram++); break; - case 0xd3: util::stream_format(stream, "xrl a,#$%02X", *opram++); break; - case 0xd4: util::stream_format(stream, "call $6%02X", *opram++); flags = DASMFLAG_STEP_OVER; break; + case 0xd2: util::stream_format(stream, "jb6 $%03X", (pc & 0xf00) | params.r8(cpc++)); break; + case 0xd3: util::stream_format(stream, "xrl a,#$%02X", params.r8(cpc++)); break; + case 0xd4: util::stream_format(stream, "call $6%02X", params.r8(cpc++)); flags = STEP_OVER; break; case 0xd5: util::stream_format(stream, "sel rb1"); break; - case 0xd6: if (!upi41) + case 0xd6: if (!m_upi41) util::stream_format(stream, "illegal"); else - util::stream_format(stream, "jnibf $%03X", (pc & 0xf00) | *opram++); + util::stream_format(stream, "jnibf $%03X", (pc & 0xf00) | params.r8(cpc++)); break; case 0xd7: util::stream_format(stream, "mov psw,a"); break; case 0xd8: util::stream_format(stream, "xrl a,r0"); break; @@ -273,32 +281,32 @@ static uint32_t common_dasm(device_t *device, std::ostream &stream, offs_t pc, c case 0xde: util::stream_format(stream, "xrl a,r6"); break; case 0xdf: util::stream_format(stream, "xrl a,r7"); break; case 0xe3: util::stream_format(stream, "movp3 a,@a"); break; - case 0xe4: util::stream_format(stream, "jmp $7%02X", *opram++); break; - case 0xe5: if (!upi41) + case 0xe4: util::stream_format(stream, "jmp $7%02X", params.r8(cpc++)); break; + case 0xe5: if (!m_upi41) util::stream_format(stream, "sel mb0"); else util::stream_format(stream, "en dma"); break; - case 0xe6: util::stream_format(stream, "jnc $%03X", (pc & 0xf00) | *opram++); break; + case 0xe6: util::stream_format(stream, "jnc $%03X", (pc & 0xf00) | params.r8(cpc++)); break; case 0xe7: util::stream_format(stream, "rl a"); break; - case 0xe8: util::stream_format(stream, "djnz r0,$%03X", (pc & 0xf00) | *opram++); flags = DASMFLAG_STEP_OVER; break; - case 0xe9: util::stream_format(stream, "djnz r1,$%03X", (pc & 0xf00) | *opram++); flags = DASMFLAG_STEP_OVER; break; - case 0xea: util::stream_format(stream, "djnz r2,$%03X", (pc & 0xf00) | *opram++); flags = DASMFLAG_STEP_OVER; break; - case 0xeb: util::stream_format(stream, "djnz r3,$%03X", (pc & 0xf00) | *opram++); flags = DASMFLAG_STEP_OVER; break; - case 0xec: util::stream_format(stream, "djnz r4,$%03X", (pc & 0xf00) | *opram++); flags = DASMFLAG_STEP_OVER; break; - case 0xed: util::stream_format(stream, "djnz r5,$%03X", (pc & 0xf00) | *opram++); flags = DASMFLAG_STEP_OVER; break; - case 0xee: util::stream_format(stream, "djnz r6,$%03X", (pc & 0xf00) | *opram++); flags = DASMFLAG_STEP_OVER; break; - case 0xef: util::stream_format(stream, "djnz r7,$%03X", (pc & 0xf00) | *opram++); flags = DASMFLAG_STEP_OVER; break; + case 0xe8: util::stream_format(stream, "djnz r0,$%03X", (pc & 0xf00) | params.r8(cpc++)); flags = STEP_OVER; break; + case 0xe9: util::stream_format(stream, "djnz r1,$%03X", (pc & 0xf00) | params.r8(cpc++)); flags = STEP_OVER; break; + case 0xea: util::stream_format(stream, "djnz r2,$%03X", (pc & 0xf00) | params.r8(cpc++)); flags = STEP_OVER; break; + case 0xeb: util::stream_format(stream, "djnz r3,$%03X", (pc & 0xf00) | params.r8(cpc++)); flags = STEP_OVER; break; + case 0xec: util::stream_format(stream, "djnz r4,$%03X", (pc & 0xf00) | params.r8(cpc++)); flags = STEP_OVER; break; + case 0xed: util::stream_format(stream, "djnz r5,$%03X", (pc & 0xf00) | params.r8(cpc++)); flags = STEP_OVER; break; + case 0xee: util::stream_format(stream, "djnz r6,$%03X", (pc & 0xf00) | params.r8(cpc++)); flags = STEP_OVER; break; + case 0xef: util::stream_format(stream, "djnz r7,$%03X", (pc & 0xf00) | params.r8(cpc++)); flags = STEP_OVER; break; case 0xf0: util::stream_format(stream, "mov a,@r0"); break; case 0xf1: util::stream_format(stream, "mov a,@r1"); break; - case 0xf2: util::stream_format(stream, "jb7 $%03X", (pc & 0xf00) | *opram++); break; - case 0xf4: util::stream_format(stream, "call $7%02X", *opram++); flags = DASMFLAG_STEP_OVER; break; - case 0xf5: if (!upi41) + case 0xf2: util::stream_format(stream, "jb7 $%03X", (pc & 0xf00) | params.r8(cpc++)); break; + case 0xf4: util::stream_format(stream, "call $7%02X", params.r8(cpc++)); flags = STEP_OVER; break; + case 0xf5: if (!m_upi41) util::stream_format(stream, "sel mb1"); else util::stream_format(stream, "en flags"); break; - case 0xf6: util::stream_format(stream, "jc $%03X", (pc & 0xf00) | *opram++); break; + case 0xf6: util::stream_format(stream, "jc $%03X", (pc & 0xf00) | params.r8(cpc++)); break; case 0xf7: util::stream_format(stream, "rlc a"); break; case 0xf8: util::stream_format(stream, "mov a,r0"); break; case 0xf9: util::stream_format(stream, "mov a,r1"); break; @@ -311,17 +319,5 @@ static uint32_t common_dasm(device_t *device, std::ostream &stream, offs_t pc, c default: util::stream_format(stream, "illegal"); break; } - return (opram - startram) | flags | DASMFLAG_SUPPORTED; -} - - -CPU_DISASSEMBLE( mcs48 ) -{ - return common_dasm(device, stream, pc, oprom, opram, false); -} - - -CPU_DISASSEMBLE( upi41 ) -{ - return common_dasm(device, stream, pc, oprom, opram, true); + return (cpc - pc) | flags | SUPPORTED; } diff --git a/src/devices/cpu/mcs48/mcs48dsm.h b/src/devices/cpu/mcs48/mcs48dsm.h new file mode 100644 index 00000000000..c4c7dde9a9c --- /dev/null +++ b/src/devices/cpu/mcs48/mcs48dsm.h @@ -0,0 +1,31 @@ +// license:BSD-3-Clause +// copyright-holders:Aaron Giles +/*************************************************************************** + + mcs48dsm.c + + Simple MCS-48/UPI-41 disassembler. + Written by Aaron Giles + +***************************************************************************/ + + +#ifndef MAME_CPU_MCS48_MCS48DASM_H +#define MAME_CPU_MCS48_MCS48DASM_H + +#pragma once + +class mcs48_disassembler : public util::disasm_interface +{ +public: + mcs48_disassembler(bool upi41); + virtual ~mcs48_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + bool m_upi41; +}; + +#endif diff --git a/src/devices/cpu/mcs51/mcs51.cpp b/src/devices/cpu/mcs51/mcs51.cpp index 1c682e06e0e..a46c927be89 100644 --- a/src/devices/cpu/mcs51/mcs51.cpp +++ b/src/devices/cpu/mcs51/mcs51.cpp @@ -130,6 +130,7 @@ #include "emu.h" #include "debugger.h" #include "mcs51.h" +#include "mcs51dasm.h" #define VERBOSE 0 @@ -2506,45 +2507,32 @@ void ds5002fp_device::nvram_write( emu_file &file ) file.write( m_sfr_ram, 0x80 ); } - - -offs_t mcs51_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *mcs51_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( i8051 ); - return CPU_DISASSEMBLE_NAME(i8051)(this, stream, pc, oprom, opram, options); + return new i8051_disassembler; } - -offs_t i8052_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *i8052_device::create_disassembler() { - extern CPU_DISASSEMBLE( i8052 ); - return CPU_DISASSEMBLE_NAME(i8052)(this, stream, pc, oprom, opram, options); + return new i8052_disassembler; } - -offs_t i80c31_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *i80c31_device::create_disassembler() { - extern CPU_DISASSEMBLE( i80c51 ); - return CPU_DISASSEMBLE_NAME(i80c51)(this, stream, pc, oprom, opram, options); + return new i80c51_disassembler; } - -offs_t i80c51_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *i80c51_device::create_disassembler() { - extern CPU_DISASSEMBLE( i80c51 ); - return CPU_DISASSEMBLE_NAME(i80c51)(this, stream, pc, oprom, opram, options); + return new i80c51_disassembler; } - -offs_t i80c52_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *i80c52_device::create_disassembler() { - extern CPU_DISASSEMBLE( i80c52 ); - return CPU_DISASSEMBLE_NAME(i80c52)(this, stream, pc, oprom, opram, options); + return new i80c52_disassembler; } - -offs_t ds5002fp_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *ds5002fp_device::create_disassembler() { - extern CPU_DISASSEMBLE( ds5002fp ); - return CPU_DISASSEMBLE_NAME(ds5002fp)(this, stream, pc, oprom, opram, options); + return new ds5002fp_disassembler; } diff --git a/src/devices/cpu/mcs51/mcs51.h b/src/devices/cpu/mcs51/mcs51.h index 13f19d3fd28..a789579867a 100644 --- a/src/devices/cpu/mcs51/mcs51.h +++ b/src/devices/cpu/mcs51/mcs51.h @@ -115,9 +115,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 5; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; protected: address_space_config m_program_config; @@ -390,7 +388,7 @@ public: protected: i8052_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock, int program_width, int data_width, uint8_t features = 0); - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; /* SFR Callbacks */ virtual void sfr_write(size_t offset, uint8_t data) override; @@ -418,7 +416,7 @@ public: i80c31_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); protected: - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; }; @@ -431,7 +429,7 @@ public: protected: i80c51_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock, int program_width, int data_width, uint8_t features = 0); - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; }; class i87c51_device : public i80c51_device @@ -451,7 +449,7 @@ public: protected: i80c52_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock, int program_width, int data_width, uint8_t features = 0); - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; /* SFR Callbacks */ virtual void sfr_write(size_t offset, uint8_t data) override; @@ -522,7 +520,7 @@ public: virtual void nvram_write( emu_file &file ) override; protected: - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; /* SFR Callbacks */ virtual void sfr_write(size_t offset, uint8_t data) override; diff --git a/src/devices/cpu/mcs51/mcs51dasm.cpp b/src/devices/cpu/mcs51/mcs51dasm.cpp index b96ae46a4a1..fce9b90208f 100644 --- a/src/devices/cpu/mcs51/mcs51dasm.cpp +++ b/src/devices/cpu/mcs51/mcs51dasm.cpp @@ -24,223 +24,215 @@ *****************************************************************************/ #include "emu.h" -#include "debugger.h" -#include "mcs51.h" +#include "mcs51dasm.h" + +// Note: addresses >= 0x100 are bit addresses + +const mcs51_disassembler::mem_info mcs51_disassembler::default_names[] = { + { 0x00, "rb0r0" }, + { 0x01, "rb0r1" }, + { 0x02, "rb0r2" }, + { 0x03, "rb0r3" }, + { 0x04, "rb0r4" }, + { 0x05, "rb0r5" }, + { 0x06, "rb0r6" }, + { 0x07, "rb0r7" }, + { 0x08, "rb1r0" }, + { 0x09, "rb1r1" }, + { 0x0a, "rb1r2" }, + { 0x0b, "rb1r3" }, + { 0x0c, "rb1r4" }, + { 0x0d, "rb1r5" }, + { 0x0e, "rb1r6" }, + { 0x0f, "rb1r7" }, + { 0x10, "rb2r0" }, + { 0x11, "rb2r1" }, + { 0x12, "rb2r2" }, + { 0x13, "rb2r3" }, + { 0x14, "rb2r4" }, + { 0x15, "rb2r5" }, + { 0x16, "rb2r6" }, + { 0x17, "rb2r7" }, + { 0x18, "rb3r0" }, + { 0x19, "rb3r1" }, + { 0x1a, "rb3r2" }, + { 0x1b, "rb3r3" }, + { 0x1c, "rb3r4" }, + { 0x1d, "rb3r5" }, + { 0x1e, "rb3r6" }, + { 0x1f, "rb3r7" }, + + { 0x80, "p0" }, + { 0x81, "sp" }, + { 0x82, "dpl" }, + { 0x83, "dph" }, + { 0x87, "pcon" }, + { 0x88, "tcon" }, + { 0x89, "tmod" }, + { 0x8a, "tl0" }, + { 0x8b, "tl1" }, + { 0x8c, "th0" }, + { 0x8d, "th1" }, + { 0x90, "p1" }, + { 0x98, "scon" }, + { 0x99, "sbuf" }, + { 0xa0, "p2" }, + { 0xa8, "ie" }, + { 0xb0, "p3" }, + { 0xb8, "ip" }, + { 0xd0, "psw" }, + { 0xe0, "acc" }, + { 0xf0, "b" }, + + { 0x188, "it0" }, + { 0x189, "ie0" }, + { 0x18a, "it1" }, + { 0x18b, "ie1" }, + { 0x18c, "tr0" }, + { 0x18d, "tf0" }, + { 0x18e, "tr1" }, + { 0x18f, "tf1" }, + + { 0x198, "ri" }, + { 0x199, "ti" }, + { 0x19a, "rb8" }, + { 0x19b, "tb8" }, + { 0x19c, "ren" }, + { 0x19d, "sm2" }, + { 0x19e, "sm1" }, + { 0x19f, "sm0" }, + + { 0x1a8, "ex0" }, + { 0x1a9, "et0" }, + { 0x1aa, "ex1" }, + { 0x1ab, "et1" }, + { 0x1ac, "es" }, + { 0x1ad, "ie.5" }, + { 0x1ae, "ie.6" }, + { 0x1af, "ea" }, -enum -{ - FEATURE_NONE = 0x00, - FEATURE_I8052 = 0x01, - FEATURE_CMOS = 0x02, - FEATURE_I80C52 = 0x04, - FEATURE_DS5002FP = 0x08, - FEATURE_I83C751 = 0x08 + /* FIXME: port 3 - depends on external circuits and not really + * implemented in the core. TBD */ + { 0x1b0, "rxd" }, + { 0x1b1, "txd" }, + { 0x1b2, "int0" }, + { 0x1b3, "int1" }, + { 0x1b4, "t0" }, + { 0x1b5, "t1" }, + { 0x1b6, "wr" }, + { 0x1b7, "rd" }, + + { 0x1b8, "px0" }, + { 0x1b9, "pt0" }, + { 0x1ba, "px1" }, + { 0x1bb, "pt1" }, + { 0x1bc, "ps" }, + { 0x1bd, "ip.5" }, + { 0x1be, "ip.6" }, + { 0x1bf, "ip.7" }, + + { 0x1d0, "p" }, + { 0x1d1, "psw.1" }, + { 0x1d2, "ov" }, + { 0x1d3, "rs0" }, + { 0x1d4, "rs1" }, + { 0x1d5, "f0" }, + { 0x1d6, "ac" }, + { 0x1d7, "cy" }, + + { -1 } }; +const mcs51_disassembler::mem_info mcs51_disassembler::i8052_names[] = { + { 0xc8, "t2con" }, + { 0xca, "rcap2l" }, + { 0xcb, "rcap2h" }, + { 0xcc, "tl2" }, + { 0xcd, "th2" }, + + { 0x1ad, "et2" }, + { 0x1bd, "pt2" }, + + { 0x1c8, "cprl2" }, + { 0x1c9, "ct2" }, + { 0x1ca, "tr2" }, + { 0x1cb, "exen2" }, + { 0x1cc, "tclk" }, + { 0x1cd, "rclk" }, + { 0x1ce, "exf2" }, + { 0x1cf, "tf2" }, -#define SHOW_MEMORY_NAMES 1 + { -1 } +}; -#ifdef SHOW_MEMORY_NAMES +const mcs51_disassembler::mem_info mcs51_disassembler::i80c52_names[] = { + { 0xb7, "iph" }, + { 0xa9, "saddr" }, + { 0xb9, "saden" }, -/*Display the memory address names for data & bit address access*/ + { -1 } +}; -//SFR Names +const mcs51_disassembler::mem_info mcs51_disassembler::ds5002fp_names[] = { + { 0x8e, "pwcm" }, + { 0x8f, "pwmp" }, + { 0xc1, "crcr" }, + { 0xc2, "crcl" }, + { 0xc3, "crch" }, + { 0xc6, "mcon" }, + { 0xc7, "ta" }, + { 0xcf, "rnr" }, + { 0xd8, "rpctl" }, + { 0xd9, "rps" }, + + { 0x1d8, "rg0" }, + { 0x1d9, "rpc" }, + { 0x1da, "dma" }, + { 0x1db, "ibi" }, + { 0x1dc, "ae" }, + { 0x1dd, "exbs" }, + { 0x1de, "d8.6" }, + { 0x1df, "rnr" }, -static const struct { - int feature; - int addr; - const char *name; -} mem_name_feature[] = -{ - { FEATURE_NONE, 0x00, "rb0r0" }, - { FEATURE_NONE, 0x01, "rb0r1" }, - { FEATURE_NONE, 0x02, "rb0r2" }, - { FEATURE_NONE, 0x03, "rb0r3" }, - { FEATURE_NONE, 0x04, "rb0r4" }, - { FEATURE_NONE, 0x05, "rb0r5" }, - { FEATURE_NONE, 0x06, "rb0r6" }, - { FEATURE_NONE, 0x07, "rb0r7" }, - { FEATURE_NONE, 0x08, "rb1r0" }, - { FEATURE_NONE, 0x09, "rb1r1" }, - { FEATURE_NONE, 0x0a, "rb1r2" }, - { FEATURE_NONE, 0x0b, "rb1r3" }, - { FEATURE_NONE, 0x0c, "rb1r4" }, - { FEATURE_NONE, 0x0d, "rb1r5" }, - { FEATURE_NONE, 0x0e, "rb1r6" }, - { FEATURE_NONE, 0x0f, "rb1r7" }, - { FEATURE_NONE, 0x10, "rb2r0" }, - { FEATURE_NONE, 0x11, "rb2r1" }, - { FEATURE_NONE, 0x12, "rb2r2" }, - { FEATURE_NONE, 0x13, "rb2r3" }, - { FEATURE_NONE, 0x14, "rb2r4" }, - { FEATURE_NONE, 0x15, "rb2r5" }, - { FEATURE_NONE, 0x16, "rb2r6" }, - { FEATURE_NONE, 0x17, "rb2r7" }, - { FEATURE_NONE, 0x18, "rb3r0" }, - { FEATURE_NONE, 0x19, "rb3r1" }, - { FEATURE_NONE, 0x1a, "rb3r2" }, - { FEATURE_NONE, 0x1b, "rb3r3" }, - { FEATURE_NONE, 0x1c, "rb3r4" }, - { FEATURE_NONE, 0x1d, "rb3r5" }, - { FEATURE_NONE, 0x1e, "rb3r6" }, - { FEATURE_NONE, 0x1f, "rb3r7" }, - - { FEATURE_NONE, 0x80, "p0" }, - { FEATURE_NONE, 0x81, "sp" }, - { FEATURE_NONE, 0x82, "dpl" }, - { FEATURE_NONE, 0x83, "dph" }, - { FEATURE_NONE, 0x87, "pcon" }, - { FEATURE_NONE, 0x88, "tcon" }, - { FEATURE_NONE, 0x89, "tmod" }, - { FEATURE_NONE, 0x8a, "tl0" }, - { FEATURE_NONE, 0x8b, "tl1" }, - { FEATURE_NONE, 0x8c, "th0" }, - { FEATURE_NONE, 0x8d, "th1" }, - { FEATURE_NONE, 0x90, "p1" }, - { FEATURE_NONE, 0x98, "scon" }, - { FEATURE_NONE, 0x99, "sbuf" }, - { FEATURE_NONE, 0xa0, "p2" }, - { FEATURE_NONE, 0xa8, "ie" }, - { FEATURE_NONE, 0xb0, "p3" }, - { FEATURE_NONE, 0xb8, "ip" }, - { FEATURE_NONE, 0xd0, "psw" }, - { FEATURE_NONE, 0xe0, "acc" }, - { FEATURE_NONE, 0xf0, "b" }, - - { FEATURE_I8052, 0xc8, "t2con" }, - { FEATURE_I8052, 0xca, "rcap2l" }, - { FEATURE_I8052, 0xcb, "rcap2h" }, - { FEATURE_I8052, 0xcc, "tl2" }, - { FEATURE_I8052, 0xcd, "th2" }, - - { FEATURE_I80C52, 0xb7, "iph" }, - { FEATURE_I80C52, 0xa9, "saddr" }, - { FEATURE_I80C52, 0xb9, "saden" }, - - { FEATURE_DS5002FP, 0x8e, "pwcm" }, - { FEATURE_DS5002FP, 0x8f, "pwmp" }, - { FEATURE_DS5002FP, 0xc1, "crcr" }, - { FEATURE_DS5002FP, 0xc2, "crcl" }, - { FEATURE_DS5002FP, 0xc3, "crch" }, - { FEATURE_DS5002FP, 0xc6, "mcon" }, - { FEATURE_DS5002FP, 0xc7, "ta" }, - { FEATURE_DS5002FP, 0xcf, "rnr" }, - { FEATURE_DS5002FP, 0xd8, "rpctl" }, - { FEATURE_DS5002FP, 0xd9, "rps" }, - - { FEATURE_I83C751, 0x98, "i2con" }, - { FEATURE_I83C751, 0x99, "i2dat" }, - { FEATURE_I83C751, 0xd8, "i2cfg" }, - { FEATURE_I83C751, 0xf8, "i2sta" }, /* read only */ - - /* bit addresses */ - - { FEATURE_NONE, 0x188, "it0" }, - { FEATURE_NONE, 0x189, "ie0" }, - { FEATURE_NONE, 0x18a, "it1" }, - { FEATURE_NONE, 0x18b, "ie1" }, - { FEATURE_NONE, 0x18c, "tr0" }, - { FEATURE_NONE, 0x18d, "tf0" }, - { FEATURE_NONE, 0x18e, "tr1" }, - { FEATURE_NONE, 0x18f, "tf1" }, - - { FEATURE_NONE, 0x198, "ri" }, - { FEATURE_NONE, 0x199, "ti" }, - { FEATURE_NONE, 0x19a, "rb8" }, - { FEATURE_NONE, 0x19b, "tb8" }, - { FEATURE_NONE, 0x19c, "ren" }, - { FEATURE_NONE, 0x19d, "sm2" }, - { FEATURE_NONE, 0x19e, "sm1" }, - { FEATURE_NONE, 0x19f, "sm0" }, - - { FEATURE_I83C751, 0x198, "xstp" }, /* read: no function */ - { FEATURE_I83C751, 0x199, "xstr" }, /* read: MASTER */ - { FEATURE_I83C751, 0x19a, "cstp" }, /* read: STP */ - { FEATURE_I83C751, 0x19b, "cstr" }, /* read: STR */ - { FEATURE_I83C751, 0x19c, "carl" }, /* read: ARL */ - { FEATURE_I83C751, 0x19d, "cdr" }, /* read: DRDY */ - { FEATURE_I83C751, 0x19e, "idle" }, /* read: ATN */ - { FEATURE_I83C751, 0x19f, "cxa" }, /* read: RDAT */ - - { FEATURE_NONE, 0x1a8, "ex0" }, - { FEATURE_NONE, 0x1a9, "et0" }, - { FEATURE_NONE, 0x1aa, "ex1" }, - { FEATURE_NONE, 0x1ab, "et1" }, - { FEATURE_NONE, 0x1ac, "es" }, - { FEATURE_NONE, 0x1ad, "ie.5" }, - { FEATURE_NONE, 0x1ae, "ie.6" }, - { FEATURE_NONE, 0x1af, "ea" }, - - { FEATURE_I83C751, 0x1ac, "ei2" }, - { FEATURE_I8052, 0x1ad, "et2" }, + { -1 } +}; - /* FIXME: port 3 - depends on external circuits and not really - * implemented in the core. TBD */ - { FEATURE_NONE, 0x1b0, "rxd" }, - { FEATURE_NONE, 0x1b1, "txd" }, - { FEATURE_NONE, 0x1b2, "int0" }, - { FEATURE_NONE, 0x1b3, "int1" }, - { FEATURE_NONE, 0x1b4, "t0" }, - { FEATURE_NONE, 0x1b5, "t1" }, - { FEATURE_NONE, 0x1b6, "wr" }, - { FEATURE_NONE, 0x1b7, "rd" }, - - { FEATURE_NONE, 0x1b8, "px0" }, - { FEATURE_NONE, 0x1b9, "pt0" }, - { FEATURE_NONE, 0x1ba, "px1" }, - { FEATURE_NONE, 0x1bb, "pt1" }, - { FEATURE_NONE, 0x1bc, "ps" }, - { FEATURE_NONE, 0x1bd, "ip.5" }, - { FEATURE_NONE, 0x1be, "ip.6" }, - { FEATURE_NONE, 0x1bf, "ip.7" }, - - { FEATURE_I8052, 0x1bd, "pt2" }, - { FEATURE_I83C751, 0x1bc, "pi2" }, - - { FEATURE_I8052, 0x1c8, "cprl2" }, - { FEATURE_I8052, 0x1c9, "ct2" }, - { FEATURE_I8052, 0x1ca, "tr2" }, - { FEATURE_I8052, 0x1cb, "exen2" }, - { FEATURE_I8052, 0x1cc, "tclk" }, - { FEATURE_I8052, 0x1cd, "rclk" }, - { FEATURE_I8052, 0x1ce, "exf2" }, - { FEATURE_I8052, 0x1cf, "tf2" }, - - { FEATURE_NONE, 0x1d0, "p" }, - { FEATURE_NONE, 0x1d1, "psw.1" }, - { FEATURE_NONE, 0x1d2, "ov" }, - { FEATURE_NONE, 0x1d3, "rs0" }, - { FEATURE_NONE, 0x1d4, "rs1" }, - { FEATURE_NONE, 0x1d5, "f0" }, - { FEATURE_NONE, 0x1d6, "ac" }, - { FEATURE_NONE, 0x1d7, "cy" }, - - { FEATURE_DS5002FP, 0x1d8, "rg0" }, - { FEATURE_DS5002FP, 0x1d9, "rpc" }, - { FEATURE_DS5002FP, 0x1da, "dma" }, - { FEATURE_DS5002FP, 0x1db, "ibi" }, - { FEATURE_DS5002FP, 0x1dc, "ae" }, - { FEATURE_DS5002FP, 0x1dd, "exbs" }, - { FEATURE_DS5002FP, 0x1de, "d8.6" }, - { FEATURE_DS5002FP, 0x1df, "rnr" }, - - { FEATURE_I83C751, 0x1d8, "ct0" }, - { FEATURE_I83C751, 0x1d9, "ct1" }, - { FEATURE_I83C751, 0x1da, "i2cfg.2" }, - { FEATURE_I83C751, 0x1db, "i2cfg.3" }, - { FEATURE_I83C751, 0x1dc, "tirun" }, - { FEATURE_I83C751, 0x1dd, "clrti" }, - { FEATURE_I83C751, 0x1de, "masterq" }, - { FEATURE_I83C751, 0x1df, "slaven" }, - - { FEATURE_I83C751, 0x1f8, "xstp" }, - { FEATURE_I83C751, 0x1f9, "xstr" }, - { FEATURE_I83C751, 0x1fa, "makstp" }, - { FEATURE_I83C751, 0x1fb, "makstr" }, - { FEATURE_I83C751, 0x1fc, "xactv" }, - { FEATURE_I83C751, 0x1fd, "xdata" }, - { FEATURE_I83C751, 0x1fe, "idle" }, - { FEATURE_I83C751, 0x1ff, "i2sta.7" }, +const mcs51_disassembler::mem_info mcs51_disassembler::i8xc751_names[] = { + { 0x98, "i2con" }, + { 0x99, "i2dat" }, + { 0xd8, "i2cfg" }, + { 0xf8, "i2sta" }, /* read only */ + + { 0x198, "xstp" }, /* read: no function */ + { 0x199, "xstr" }, /* read: MASTER */ + { 0x19a, "cstp" }, /* read: STP */ + { 0x19b, "cstr" }, /* read: STR */ + { 0x19c, "carl" }, /* read: ARL */ + { 0x19d, "cdr" }, /* read: DRDY */ + { 0x19e, "idle" }, /* read: ATN */ + { 0x19f, "cxa" }, /* read: RDAT */ + + { 0x1ac, "ei2" }, + + { 0x1bc, "pi2" }, + + { 0x1d8, "ct0" }, + { 0x1d9, "ct1" }, + { 0x1da, "i2cfg.2" }, + { 0x1db, "i2cfg.3" }, + { 0x1dc, "tirun" }, + { 0x1dd, "clrti" }, + { 0x1de, "masterq" }, + { 0x1df, "slaven" }, + + { 0x1f8, "xstp" }, + { 0x1f9, "xstr" }, + { 0x1fa, "makstp" }, + { 0x1fb, "makstr" }, + { 0x1fc, "xactv" }, + { 0x1fd, "xdata" }, + { 0x1fe, "idle" }, + { 0x1ff, "i2sta.7" }, /* unknown * "ibf", "obf", "idsm", "obfc", e8 - eb @@ -250,97 +242,67 @@ static const struct { { -1 } }; -static void init_mem_names(int feature_set, const char **mem_names) +mcs51_disassembler::mcs51_disassembler() { - int i; - int feature; - - /* Set defaults / i8051 */ - for (i = 0; feature = mem_name_feature[i].feature, feature >= 0; i++) - { - if ( feature == FEATURE_NONE ) - mem_names[mem_name_feature[i].addr] = mem_name_feature[i].name; - } - - /* Set specific memory names */ - for (i = 0; feature = mem_name_feature[i].feature, feature >= 0; i++) - { - if (feature & feature_set) - mem_names[mem_name_feature[i].addr] = mem_name_feature[i].name; - } +} +void mcs51_disassembler::add_names(const mem_info *info) +{ + for(unsigned int i=0; info[i].addr >= 0; i++) + m_names[info[i].addr] = info[i].name; } -static const char *get_data_address( const char **mem_names, uint8_t arg ) +u32 mcs51_disassembler::opcode_alignment() const { - static char buffer_array[4][32]; - static int whichbuf; - char *buffer = &buffer_array[++whichbuf % 4][0]; + return 1; +} + - if (mem_names[arg] == nullptr) - sprintf(buffer,"$%02X",arg); +std::string mcs51_disassembler::get_data_address( uint8_t arg ) const +{ + auto i = m_names.find(arg); + if (i == m_names.end()) + return util::string_format("$%02X", arg); else - sprintf(buffer,"%s", mem_names[arg]); - return buffer; + return i->second; } -static const char *get_bit_address( const char **mem_names, uint8_t arg ) +std::string mcs51_disassembler::get_bit_address( uint8_t arg ) const { - static char buffer[32]; - if(arg < 0x80) { //Bit address 0-7F can be referred to as 20.0, 20.1, to 20.7 for address 0, and 2f.0,2f.1 to 2f.7 for address 7f if(arg < 0x7f) - sprintf(buffer,"$%02X.%d",(arg >> 3) | 0x20, arg & 0x07); + return util::string_format("$%02X.%d", (arg >> 3) | 0x20, arg & 0x07); else - sprintf(buffer,"$%02X",arg); + return util::string_format("$%02X", arg); } else { - if (mem_names[arg | 0x100] == nullptr) + auto i = m_names.find(arg | 0x100); + if (i == m_names.end()) { - if (mem_names[arg & 0xf8] == nullptr) - sprintf(buffer,"$%02X.%d", arg & 0xf8, arg & 0x07); + i = m_names.find(arg & 0xf8); + if (i == m_names.end()) + return util::string_format("$%02X.%d", arg & 0xf8, arg & 0x07); else - sprintf(buffer,"%s.%d", mem_names[arg & 0xf8], arg & 0x07); + return util::string_format("%s.%d", i->second, arg & 0x07); } else - sprintf(buffer,"%s", mem_names[arg | 0x100]); + return i->second; } - return buffer; } -#else - -/*Just display the actual memory address for data & bit address access*/ - -static const char *get_data_address( uint8_t arg ) -{ - static char buffer[32]; - sprintf(buffer,"$%02X",arg); - return buffer; -} - -static const char *get_bit_address( uint8_t arg ) -{ - static char buffer[32]; - sprintf(buffer,"$%02X",arg); - return buffer; -} - -#endif - -static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram) +offs_t mcs51_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { uint32_t flags = 0; unsigned PC = pc; - const char *sym, *sym2; + std::string sym, sym2; uint8_t op, data; uint16_t addr; int8_t rel; - op = oprom[PC++ - pc]; + op = opcodes.r8(PC++); switch( op ) { //NOP @@ -357,15 +319,15 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p case 0xa1: case 0xc1: case 0xe1: - addr = opram[PC++ - pc]; + addr = params.r8(PC++); addr|= (PC & 0xf800) | ((op & 0xe0) << 3); util::stream_format(stream, "ajmp $%04X", addr); break; //LJMP code addr case 0x02: /* 1: 0000 0010 */ - addr = (opram[PC++ - pc]<<8) & 0xff00; - addr|= opram[PC++ - pc]; + addr = (params.r8(PC++)<<8) & 0xff00; + addr|= params.r8(PC++); util::stream_format(stream, "ljmp $%04X", addr); break; @@ -381,7 +343,7 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //INC data addr case 0x05: /* 1: 0000 0101 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "inc %s", sym); break; @@ -405,8 +367,8 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //JBC bit addr, code addr case 0x10: /* 1: 0001 0000 */ - sym = get_bit_address(mem_names, opram[PC++ - pc]); - rel = opram[PC++ - pc]; + sym = get_bit_address(params.r8(PC++)); + rel = params.r8(PC++); util::stream_format(stream, "jbc %s,$%04X", sym, PC + rel); break; @@ -419,17 +381,17 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p case 0xb1: case 0xd1: case 0xf1: - util::stream_format(stream, "acall $%04X", (PC & 0xf800) | ((op & 0xe0) << 3) | opram[PC - pc]); + util::stream_format(stream, "acall $%04X", (PC & 0xf800) | ((op & 0xe0) << 3) | params.r8(PC)); PC++; - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; //LCALL code addr case 0x12: /* 1: 0001 0010 */ - addr = (opram[PC++ - pc]<<8) & 0xff00; - addr|= opram[PC++ - pc]; + addr = (params.r8(PC++)<<8) & 0xff00; + addr|= params.r8(PC++); util::stream_format(stream, "lcall $%04X", addr); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; //RRC A @@ -444,7 +406,7 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //DEC data addr case 0x15: /* 1: 0001 0101 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "dec %s", sym); break; @@ -469,15 +431,15 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //JB bit addr, code addr case 0x20: /* 1: 0010 0000 */ - sym = get_bit_address(mem_names, opram[PC++ - pc]); - rel = opram[PC++ - pc]; + sym = get_bit_address(params.r8(PC++)); + rel = params.r8(PC++); util::stream_format(stream, "jb %s,$%04X", sym, (PC + rel)); break; //RET case 0x22: /* 1: 0010 0010 */ util::stream_format(stream, "ret"); - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; //RL A @@ -487,12 +449,12 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //ADD A, #data case 0x24: /* 1: 0010 0100 */ - util::stream_format(stream, "add a,#$%02X", opram[PC++ - pc]); + util::stream_format(stream, "add a,#$%02X", params.r8(PC++)); break; //ADD A, data addr case 0x25: /* 1: 0010 0101 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "add a,%s", sym); break; @@ -517,15 +479,15 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //JNB bit addr, code addr case 0x30: /* 1: 0011 0000 */ - sym = get_bit_address(mem_names, opram[PC++ - pc]); - rel = opram[PC++ - pc]; + sym = get_bit_address(params.r8(PC++)); + rel = params.r8(PC++); util::stream_format(stream, "jnb %s,$%04X", sym, (PC + rel)); break; //RETI case 0x32: /* 1: 0011 0010 */ util::stream_format(stream, "reti"); - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; //RLC A @@ -535,12 +497,12 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //ADDC A, #data case 0x34: /* 1: 0011 0100 */ - util::stream_format(stream, "addc a,#$%02X", opram[PC++ - pc]); + util::stream_format(stream, "addc a,#$%02X", params.r8(PC++)); break; //ADDC A, data addr case 0x35: /* 1: 0011 0101 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "addc a,%s", sym); break; @@ -564,31 +526,31 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //JC code addr case 0x40: /* 1: 0100 0000 */ - rel = opram[PC++ - pc]; + rel = params.r8(PC++); util::stream_format(stream, "jc $%04X", PC + rel); break; //ORL data addr, A case 0x42: /* 1: 0100 0010 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "orl %s,a", sym); break; //ORL data addr, #data case 0x43: /* 1: 0100 0011 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); - util::stream_format(stream, "orl %s,#$%02X", sym, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); + util::stream_format(stream, "orl %s,#$%02X", sym, params.r8(PC++)); break; //Unable to Test //ORL A, #data case 0x44: /* 1: 0100 0100 */ - util::stream_format(stream, "orl a,#$%02X", opram[PC++ - pc]); + util::stream_format(stream, "orl a,#$%02X", params.r8(PC++)); break; //ORL A, data addr case 0x45: /* 1: 0100 0101 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "orl a,%s", sym); break; @@ -612,32 +574,32 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //JNC code addr case 0x50: /* 1: 0101 0000 */ - rel = opram[PC++ - pc]; + rel = params.r8(PC++); util::stream_format(stream, "jnc $%04X", PC + rel); break; //Unable to test //ANL data addr, A case 0x52: /* 1: 0101 0010 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "anl %s,a", sym); break; //Unable to test //ANL data addr, #data case 0x53: /* 1: 0101 0011 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); - util::stream_format(stream, "anl %s,#$%02X", sym, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); + util::stream_format(stream, "anl %s,#$%02X", sym, params.r8(PC++)); break; //ANL A, #data case 0x54: /* 1: 0101 0100 */ - util::stream_format(stream, "anl a,#$%02X", opram[PC++ - pc]); + util::stream_format(stream, "anl a,#$%02X", params.r8(PC++)); break; //ANL A, data addr case 0x55: /* 1: 0101 0101 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "anl a,%s", sym); break; @@ -662,31 +624,31 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //JZ code addr case 0x60: /* 1: 0110 0000 */ - rel = opram[PC++ - pc]; + rel = params.r8(PC++); util::stream_format(stream, "jz $%04X", PC + rel); break; //Unable to test //XRL data addr, A case 0x62: /* 1: 0110 0010 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "xrl %s,a", sym); break; //XRL data addr, #data case 0x63: /* 1: 0110 0011 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); - util::stream_format(stream, "xrl %s,#$%02X", sym, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); + util::stream_format(stream, "xrl %s,#$%02X", sym, params.r8(PC++)); break; //XRL A, #data case 0x64: /* 1: 0110 0100 */ - util::stream_format(stream, "xrl a,#$%02X", opram[PC++ - pc]); + util::stream_format(stream, "xrl a,#$%02X", params.r8(PC++)); break; //XRL A, data addr case 0x65: /* 1: 0110 0101 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "xrl a,%s", sym); break; @@ -711,14 +673,14 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //JNZ code addr case 0x70: /* 1: 0111 0000 */ - rel = opram[PC++ - pc]; + rel = params.r8(PC++); util::stream_format(stream, "jnz $%04X", PC + rel); break; //Unable to test //ORL C, bit addr case 0x72: /* 1: 0111 0010 */ - sym = get_bit_address(mem_names, opram[PC++ - pc]); + sym = get_bit_address(params.r8(PC++)); util::stream_format(stream, "orl c,%s", sym); break; @@ -730,20 +692,20 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //MOV A, #data case 0x74: /* 1: 0111 0100 */ - util::stream_format(stream, "mov a,#$%02X", opram[PC++ - pc]); + util::stream_format(stream, "mov a,#$%02X", params.r8(PC++)); break; //MOV data addr, #data case 0x75: /* 1: 0111 0101 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); - util::stream_format(stream, "mov %s,#$%02X", sym, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); + util::stream_format(stream, "mov %s,#$%02X", sym, params.r8(PC++)); break; //Unable to test //MOV @R0/@R1, #data /* 1: 0111 011i */ case 0x76: case 0x77: - util::stream_format(stream, "mov @r%d,#$%02X", op&1, opram[PC++ - pc]); + util::stream_format(stream, "mov @r%d,#$%02X", op&1, params.r8(PC++)); break; //MOV R0 to R7, #data /* 1: 0111 1rrr */ @@ -755,18 +717,18 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p case 0x7d: case 0x7e: case 0x7f: - util::stream_format(stream, "mov r%d,#$%02X", (op & 7), opram[PC++ - pc]); + util::stream_format(stream, "mov r%d,#$%02X", (op & 7), params.r8(PC++)); break; //SJMP code addr case 0x80: /* 1: 1000 0000 */ - rel = opram[PC++ - pc]; + rel = params.r8(PC++); util::stream_format(stream, "sjmp $%04X", PC + rel); break; //ANL C, bit addr case 0x82: /* 1: 1000 0010 */ - sym = get_bit_address(mem_names, opram[PC++ - pc]); + sym = get_bit_address(params.r8(PC++)); util::stream_format(stream, "anl c,%s", sym); break; @@ -782,8 +744,8 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //MOV data addr, data addr (Note: 1st address is src, 2nd is dst, but the mov command works as mov dst,src) case 0x85: /* 1: 1000 0101 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); - sym2 = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); + sym2 = get_data_address(params.r8(PC++)); util::stream_format(stream, "mov %s,%s", sym2, sym); break; @@ -791,7 +753,7 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //MOV data addr, @R0/@R1/* 1: 1000 011i */ case 0x86: case 0x87: - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "mov %s,@r%d", sym, op&1); break; @@ -804,20 +766,20 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p case 0x8d: case 0x8e: case 0x8f: - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "mov %s,r%d", sym, op&7); break; //MOV DPTR, #data16 case 0x90: /* 1: 1001 0000 */ - addr = (opram[PC++ - pc]<<8) & 0xff00; - addr|= opram[PC++ - pc]; + addr = (params.r8(PC++)<<8) & 0xff00; + addr|= params.r8(PC++); util::stream_format(stream, "mov dptr,#$%04X", addr); break; //MOV bit addr, C case 0x92: /* 1: 1001 0010 */ - sym = get_bit_address(mem_names, opram[PC++ - pc]); + sym = get_bit_address(params.r8(PC++)); util::stream_format(stream, "mov %s,c", sym); break; @@ -828,12 +790,12 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //SUBB A, #data case 0x94: /* 1: 1001 0100 */ - util::stream_format(stream, "subb a,#$%02X", opram[PC++ - pc]); + util::stream_format(stream, "subb a,#$%02X", params.r8(PC++)); break; //SUBB A, data addr case 0x95: /* 1: 1001 0101 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "subb a,%s", sym); break; @@ -859,13 +821,13 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //Unable to test //ORL C, /bit addr case 0xa0: /* 1: 1010 0000 */ - sym = get_bit_address(mem_names, opram[PC++ - pc]); + sym = get_bit_address(params.r8(PC++)); util::stream_format(stream, "orl c,/%s", sym); break; //MOV C, bit addr case 0xa2: /* 1: 1010 0010 */ - sym = get_bit_address(mem_names, opram[PC++ - pc]); + sym = get_bit_address(params.r8(PC++)); util::stream_format(stream, "mov c,%s", sym); break; @@ -888,7 +850,7 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //MOV @R0/@R1, data addr /* 1: 1010 011i */ case 0xa6: case 0xa7: - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "mov @r%d,%s", op&1, sym); break; @@ -901,19 +863,19 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p case 0xad: case 0xae: case 0xaf: - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "mov r%d,%s", op&7, sym); break; //ANL C,/bit addr case 0xb0: /* 1: 1011 0000 */ - sym = get_bit_address(mem_names, opram[PC++ - pc]); + sym = get_bit_address(params.r8(PC++)); util::stream_format(stream, "anl c,/%s", sym); break; //CPL bit addr case 0xb2: /* 1: 1011 0010 */ - sym = get_bit_address(mem_names, opram[PC++ - pc]); + sym = get_bit_address(params.r8(PC++)); util::stream_format(stream, "cpl %s", sym); break; @@ -925,15 +887,15 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //CJNE A, #data, code addr case 0xb4: /* 1: 1011 0100 */ - data = opram[PC++ - pc]; - rel = opram[PC++ - pc]; + data = params.r8(PC++); + rel = params.r8(PC++); util::stream_format(stream, "cjne a,#$%02X,$%04X", data, PC + rel); break; //CJNE A, data addr, code addr case 0xb5: /* 1: 1011 0101 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); - rel = opram[PC++ - pc]; + sym = get_data_address(params.r8(PC++)); + rel = params.r8(PC++); util::stream_format(stream, "cjne a,%s,$%04X", sym, PC + rel); break; @@ -941,8 +903,8 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //CJNE @R0/@R1, #data, code addr /* 1: 1011 011i */ case 0xb6: case 0xb7: - data = opram[PC++ - pc]; - rel = opram[PC++ - pc]; + data = params.r8(PC++); + rel = params.r8(PC++); util::stream_format(stream, "cjne @r%d,#$%02X,$%04X", op&1, data, PC + rel); break; @@ -955,20 +917,20 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p case 0xbd: case 0xbe: case 0xbf: - data = opram[PC++ - pc]; - rel = opram[PC++ - pc]; + data = params.r8(PC++); + rel = params.r8(PC++); util::stream_format(stream, "cjne r%d,#$%02X,$%04X", op&7, data, PC + rel); break; //PUSH data addr case 0xc0: /* 1: 1100 0000 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "push %s", sym); break; //CLR bit addr case 0xc2: /* 1: 1100 0010 */ - sym = get_bit_address(mem_names, opram[PC++ - pc]); + sym = get_bit_address(params.r8(PC++)); util::stream_format(stream, "clr %s", sym); break; @@ -984,7 +946,7 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //XCH A, data addr case 0xc5: /* 1: 1100 0101 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "xch a,%s", sym); break; @@ -1008,13 +970,13 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //POP data addr case 0xd0: /* 1: 1101 0000 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "pop %s", sym); break; //SETB bit addr case 0xd2: /* 1: 1101 0010 */ - sym = get_bit_address(mem_names, opram[PC++ - pc]); + sym = get_bit_address(params.r8(PC++)); util::stream_format(stream, "setb %s", sym); break; @@ -1031,10 +993,10 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //DJNZ data addr, code addr case 0xd5: /* 1: 1101 0101 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); - rel = opram[PC++ - pc]; + sym = get_data_address(params.r8(PC++)); + rel = params.r8(PC++); util::stream_format(stream, "djnz %s,$%04X", sym, PC + rel); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; //XCHD A, @R0/@R1 /* 1: 1101 011i */ @@ -1052,9 +1014,9 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p case 0xdd: case 0xde: case 0xdf: - rel = opram[PC++ - pc]; + rel = params.r8(PC++); util::stream_format(stream, "djnz r%d,$%04X", op&7, (PC + rel)); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; //MOVX A,@DPTR @@ -1076,7 +1038,7 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //MOV A, data addr case 0xe5: /* 1: 1110 0101 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "mov a,%s", sym); break; @@ -1118,7 +1080,7 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p //MOV data addr, A case 0xf5: /* 1: 1111 0101 */ - sym = get_data_address(mem_names, opram[PC++ - pc]); + sym = get_data_address(params.r8(PC++)); util::stream_format(stream, "mov %s,a", sym); break; @@ -1144,70 +1106,25 @@ static offs_t mcs51_dasm( const char **mem_names, std::ostream &stream, offs_t p util::stream_format(stream, "illegal"); } - return (PC - pc) | flags | DASMFLAG_SUPPORTED; + return (PC - pc) | flags | SUPPORTED; } -CPU_DISASSEMBLE( i8051 ) +i8051_disassembler::i8051_disassembler() : mcs51_disassembler(default_names) { - static const char *mem_names[0x200]; - static int mem_names_initialized = 0; - - if (!mem_names_initialized) - { - init_mem_names( FEATURE_NONE, mem_names); - mem_names_initialized = 1; - } - return mcs51_dasm(mem_names, stream, pc, oprom, opram); } -CPU_DISASSEMBLE( i8052 ) +i8052_disassembler::i8052_disassembler() : mcs51_disassembler(default_names, i8052_names) { - static const char *mem_names[0x200]; - static int mem_names_initialized = 0; - - if (!mem_names_initialized) - { - init_mem_names( FEATURE_I8052, mem_names); - mem_names_initialized = 1; - } - return mcs51_dasm(mem_names, stream, pc, oprom, opram); } -CPU_DISASSEMBLE( i80c51 ) +i80c51_disassembler::i80c51_disassembler() : mcs51_disassembler(default_names, i80c52_names) { - static const char *mem_names[0x200]; - static int mem_names_initialized = 0; - - if (!mem_names_initialized) - { - init_mem_names( FEATURE_CMOS, mem_names); - mem_names_initialized = 1; - } - return mcs51_dasm(mem_names, stream, pc, oprom, opram); } -CPU_DISASSEMBLE( i80c52 ) +i80c52_disassembler::i80c52_disassembler() : mcs51_disassembler(default_names, i80c52_names, i80c52_names) { - static const char *mem_names[0x200]; - static int mem_names_initialized = 0; - - if (!mem_names_initialized) - { - init_mem_names( FEATURE_I8052 | FEATURE_CMOS | FEATURE_I80C52, mem_names); - mem_names_initialized = 1; - } - return mcs51_dasm(mem_names, stream, pc, oprom, opram); } -CPU_DISASSEMBLE( ds5002fp ) +ds5002fp_disassembler::ds5002fp_disassembler() : mcs51_disassembler(default_names, i80c52_names, ds5002fp_names, i8xc751_names) { - static const char *mem_names[0x200]; - static int mem_names_initialized = 0; - - if (!mem_names_initialized) - { - init_mem_names( FEATURE_DS5002FP | FEATURE_CMOS, mem_names); - mem_names_initialized = 1; - } - return mcs51_dasm(mem_names, stream, pc, oprom, opram); } diff --git a/src/devices/cpu/mcs51/mcs51dasm.h b/src/devices/cpu/mcs51/mcs51dasm.h new file mode 100644 index 00000000000..98272befc89 --- /dev/null +++ b/src/devices/cpu/mcs51/mcs51dasm.h @@ -0,0 +1,106 @@ +// license:BSD-3-Clause +// copyright-holders:Steve Ellenoff +/***************************************************************************** + * + * i8051dasm.c + * Portable MCS-51 Family Emulator + * + * Chips in the family: + * 8051 Product Line (8031,8051,8751) + * 8052 Product Line (8032,8052,8752) + * 8054 Product Line (8054) + * 8058 Product Line (8058) + * + * Copyright Steve Ellenoff, all rights reserved. + * + * This work is based on: + * #1) 'Intel(tm) MC51 Microcontroller Family Users Manual' and + * #2) 8051 simulator by Travis Marlatte + * #3) Portable UPI-41/8041/8741/8042/8742 emulator V0.1 by Juergen Buchmueller (MAME CORE) + * + ***************************************************************************** + * Symbol Memory Name Tables borrowed from: + * D52 8052 Disassembler - Copyright Jeffery L. Post + *****************************************************************************/ + +#ifndef MAME_CPU_MCS51_MCS51DASM_H +#define MAME_CPU_MCS51_MCS51DASM_H + +#pragma once + +class mcs51_disassembler : public util::disasm_interface +{ +public: + struct mem_info { + int addr; + const char *name; + }; + + static const mem_info default_names[]; + static const mem_info i8052_names[]; + static const mem_info i80c52_names[]; + static const mem_info ds5002fp_names[]; + static const mem_info i8xc751_names[]; + + template mcs51_disassembler(Names &&... names) : mcs51_disassembler() { + add_names(names...); + } + + mcs51_disassembler(); + virtual ~mcs51_disassembler() = default; + + template void add_names(const mem_info *info, Names &&... names) + { + add_names(names...); + add_names(info); + } + + void add_names(const mem_info *info); + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + std::unordered_map m_names; + + std::string get_data_address( uint8_t arg ) const; + std::string get_bit_address( uint8_t arg ) const; +}; + +class i8051_disassembler : public mcs51_disassembler +{ +public: + i8051_disassembler(); + virtual ~i8051_disassembler() = default; +}; + +class i8052_disassembler : public mcs51_disassembler +{ +public: + i8052_disassembler(); + virtual ~i8052_disassembler() = default; +}; + +class i80c51_disassembler : public mcs51_disassembler +{ +public: + i80c51_disassembler(); + virtual ~i80c51_disassembler() = default; +}; + +class i80c52_disassembler : public mcs51_disassembler +{ +public: + i80c52_disassembler(); + virtual ~i80c52_disassembler() = default; +}; + +class ds5002fp_disassembler : public mcs51_disassembler +{ +public: + ds5002fp_disassembler(); + virtual ~ds5002fp_disassembler() = default; +}; + + +#endif diff --git a/src/devices/cpu/mcs96/i8x9x.cpp b/src/devices/cpu/mcs96/i8x9x.cpp index c3a6c7876af..a5faff3f258 100644 --- a/src/devices/cpu/mcs96/i8x9x.cpp +++ b/src/devices/cpu/mcs96/i8x9x.cpp @@ -10,6 +10,7 @@ #include "emu.h" #include "i8x9x.h" +#include "i8x9xd.h" i8x9x_device::i8x9x_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock) : mcs96_device(mconfig, type, tag, owner, clock, 8), @@ -18,9 +19,9 @@ i8x9x_device::i8x9x_device(const machine_config &mconfig, device_type type, cons { } -offs_t i8x9x_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *i8x9x_device::create_disassembler() { - return disasm_generic(stream, pc, oprom, opram, options, disasm_entries); + return new i8x9x_disassembler; } device_memory_interface::space_config_vector i8x9x_device::memory_space_config() const diff --git a/src/devices/cpu/mcs96/i8x9x.h b/src/devices/cpu/mcs96/i8x9x.h index 8fda92de323..5684a95afc3 100644 --- a/src/devices/cpu/mcs96/i8x9x.h +++ b/src/devices/cpu/mcs96/i8x9x.h @@ -30,9 +30,8 @@ protected: virtual void device_reset() override; virtual space_config_vector memory_space_config() const override; - static const disasm_entry disasm_entries[0x100]; + virtual util::disasm_interface *create_disassembler() override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; virtual void do_exec_full() override; virtual void do_exec_partial() override; virtual void internal_update(uint64_t current_time) override; diff --git a/src/devices/cpu/mcs96/i8x9xd.cpp b/src/devices/cpu/mcs96/i8x9xd.cpp new file mode 100644 index 00000000000..40b66d9d492 --- /dev/null +++ b/src/devices/cpu/mcs96/i8x9xd.cpp @@ -0,0 +1,19 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + i8x9x.h + + MCS96, 8x9x branch, the original version + +***************************************************************************/ + +#include "emu.h" +#include "i8x9xd.h" + +i8x9x_disassembler::i8x9x_disassembler() : mcs96_disassembler(disasm_entries) +{ +} + +#include "cpu/mcs96/i8x9xd.hxx" + diff --git a/src/devices/cpu/mcs96/i8x9xd.h b/src/devices/cpu/mcs96/i8x9xd.h new file mode 100644 index 00000000000..72227f7933f --- /dev/null +++ b/src/devices/cpu/mcs96/i8x9xd.h @@ -0,0 +1,26 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + i8x9x.h + + MCS96, 8x9x branch, the original version + +***************************************************************************/ + +#ifndef MAME_CPU_MCS96_I8X9XD_H +#define MAME_CPU_MCS96_I8X9XD_H + +#include "mcs96d.h" + +class i8x9x_disassembler : public mcs96_disassembler +{ +public: + i8x9x_disassembler(); + virtual ~i8x9x_disassembler() = default; + +private: + static const disasm_entry disasm_entries[0x100]; +}; + +#endif diff --git a/src/devices/cpu/mcs96/i8xc196.cpp b/src/devices/cpu/mcs96/i8xc196.cpp index adffde72dc0..d415630f0fa 100644 --- a/src/devices/cpu/mcs96/i8xc196.cpp +++ b/src/devices/cpu/mcs96/i8xc196.cpp @@ -10,15 +10,16 @@ #include "emu.h" #include "i8xc196.h" +#include "i8xc196d.h" i8xc196_device::i8xc196_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock) : mcs96_device(mconfig, type, tag, owner, clock, 16) { } -offs_t i8xc196_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *i8xc196_device::create_disassembler() { - return disasm_generic(stream, pc, oprom, opram, options, disasm_entries); + return new i8xc196_disassembler; } void i8xc196_device::io_w8(uint8_t adr, uint8_t data) diff --git a/src/devices/cpu/mcs96/i8xc196.h b/src/devices/cpu/mcs96/i8xc196.h index bd5489a1721..a82c1ea0515 100644 --- a/src/devices/cpu/mcs96/i8xc196.h +++ b/src/devices/cpu/mcs96/i8xc196.h @@ -17,9 +17,8 @@ class i8xc196_device : public mcs96_device { protected: i8xc196_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock); - static const disasm_entry disasm_entries[0x100]; + virtual util::disasm_interface *create_disassembler() override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; virtual void do_exec_full() override; virtual void do_exec_partial() override; diff --git a/src/devices/cpu/mcs96/i8xc196d.cpp b/src/devices/cpu/mcs96/i8xc196d.cpp new file mode 100644 index 00000000000..8d56aad09e7 --- /dev/null +++ b/src/devices/cpu/mcs96/i8xc196d.cpp @@ -0,0 +1,18 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + i8xc196.h + + MCS96, c196 branch, the enhanced 16 bits bus version + +***************************************************************************/ + +#include "emu.h" +#include "i8xc196d.h" + +i8xc196_disassembler::i8xc196_disassembler() : mcs96_disassembler(disasm_entries) +{ +} + +#include "cpu/mcs96/i8xc196d.hxx" diff --git a/src/devices/cpu/mcs96/i8xc196d.h b/src/devices/cpu/mcs96/i8xc196d.h new file mode 100644 index 00000000000..53c4f65db2f --- /dev/null +++ b/src/devices/cpu/mcs96/i8xc196d.h @@ -0,0 +1,26 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + i8xc196.h + + MCS96, c196 branch, the enhanced 16 bits bus version + +***************************************************************************/ + +#ifndef MAME_CPU_MCS96_I8XC196D_H +#define MAME_CPU_MCS96_I8XC196D_H + +#include "mcs96d.h" + +class i8xc196_disassembler : public mcs96_disassembler +{ +public: + i8xc196_disassembler(); + virtual ~i8xc196_disassembler() = default; + +private: + static const disasm_entry disasm_entries[0x100]; +}; + +#endif diff --git a/src/devices/cpu/mcs96/mcs96.cpp b/src/devices/cpu/mcs96/mcs96.cpp index 92a8ed23a37..d45d30153ac 100644 --- a/src/devices/cpu/mcs96/mcs96.cpp +++ b/src/devices/cpu/mcs96/mcs96.cpp @@ -156,276 +156,6 @@ void mcs96_device::state_string_export(const device_state_entry &entry, std::str } } -std::string mcs96_device::regname(uint8_t reg) -{ - char res[32]; - switch(reg) { - case 0x18: - strcpy(res, "sp"); - break; - - case 0x19: - strcpy(res, "sph"); - break; - - default: - sprintf(res, "%02x", reg); - break; - } - return res; -} - -offs_t mcs96_device::disasm_generic(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options, const disasm_entry *entries) -{ - bool prefix_fe = false; - int off = 0; - if(oprom[0] == 0xfe && entries[oprom[1]].opcode_fe) { - prefix_fe = true; - pc++; - off++; - oprom++; - } - const disasm_entry &e = entries[oprom[0]]; - uint32_t flags = e.flags | DASMFLAG_SUPPORTED; - util::stream_format(stream, "%s", prefix_fe ? e.opcode_fe : e.opcode); - - switch(e.mode) { - case DASM_none: - flags |= 1; - break; - - case DASM_nop_2: - util::stream_format(stream, " %02x", oprom[1]); - flags |= 2; - break; - - case DASM_rel8: { - int delta = oprom[1]; - if(delta & 0x80) - delta -= 0x100; - util::stream_format(stream, " %04x", (pc+2+delta) & 0xffff); - flags |= 2; - break; - } - - case DASM_rel11: { - int delta = ((oprom[0] << 8) | oprom[1]) & 0x7ff; - if(delta & 0x400) - delta -= 0x800; - util::stream_format(stream, " %04x", (pc+2+delta) & 0xffff); - flags |= 2; - break; - } - - case DASM_rel16: { - int delta = oprom[1] | (oprom[2] << 8); - util::stream_format(stream, " %04x", (pc+3+delta) & 0xffff); - flags |= 3; - break; - } - - case DASM_rrel8: { - int delta = oprom[2]; - if(delta & 0x80) - delta -= 0x100; - util::stream_format(stream, " %s, %04x", regname(oprom[1]), (pc+3+delta) & 0xffff); - flags |= 3; - break; - } - - case DASM_brrel8: { - int delta = oprom[2]; - if(delta & 0x80) - delta -= 0x100; - util::stream_format(stream, " %d, %s, %04x", oprom[0] & 7, regname(oprom[1]), (pc+3+delta) & 0xffff); - flags |= 3; - break; - } - - case DASM_direct_1: - util::stream_format(stream, " %s", regname(oprom[1])); - flags |= 2; - break; - - case DASM_direct_2: - util::stream_format(stream, " %s, %s", regname(oprom[2]), regname(oprom[1])); - flags |= 3; - break; - - case DASM_direct_3: - util::stream_format(stream, " %s, %s, %s", regname(oprom[3]), regname(oprom[2]), regname(oprom[1])); - flags |= 4; - break; - - case DASM_immed_1b: - util::stream_format(stream, " #%02x", oprom[1]); - flags |= 2; - break; - - case DASM_immed_2b: - util::stream_format(stream, " %s, #%02x", regname(oprom[2]), oprom[1]); - flags |= 3; - break; - - case DASM_immed_or_reg_2b: - if(oprom[1] >= 0x10) - util::stream_format(stream, " %s, %s", regname(oprom[2]), regname(oprom[1])); - else - util::stream_format(stream, " %s, #%02x", regname(oprom[2]), oprom[1]); - flags |= 3; - break; - - case DASM_immed_3b: - util::stream_format(stream, " %s, %s, #%02x", regname(oprom[3]), regname(oprom[2]), oprom[1]); - flags |= 4; - break; - - case DASM_immed_1w: - util::stream_format(stream, " #%02x%02x", oprom[2], oprom[1]); - flags |= 3; - break; - - case DASM_immed_2w: - util::stream_format(stream, " %s, #%02x%02x", regname(oprom[3]), oprom[2], oprom[1]); - flags |= 4; - break; - - case DASM_immed_3w: - util::stream_format(stream, " %s, %s, #%02x%02x", regname(oprom[4]), regname(oprom[3]), oprom[2], oprom[1]); - flags |= 5; - break; - - case DASM_indirect_1n: - util::stream_format(stream, " [%s]", regname(oprom[1])); - flags |= 2; - break; - - case DASM_indirect_1: - if(oprom[1] & 0x01) { - util::stream_format(stream, " [%s]+", regname(oprom[1]-1)); - flags |= 2; - } else { - util::stream_format(stream, " [%s]", regname(oprom[1])); - flags |= 2; - } - break; - - case DASM_indirect_2: - if(oprom[1] & 0x01) { - util::stream_format(stream, " %s, [%s]+", regname(oprom[2]), regname(oprom[1]-1)); - flags |= 3; - } else { - util::stream_format(stream, " %s, [%s]", regname(oprom[2]), regname(oprom[1])); - flags |= 3; - } - break; - - case DASM_indirect_3: - if(oprom[1] & 0x01) { - util::stream_format(stream, " %s, %s, [%s]+", regname(oprom[3]), regname(oprom[2]), regname(oprom[1]-1)); - flags |= 4; - } else { - util::stream_format(stream, " %s, %s, [%s]", regname(oprom[3]), regname(oprom[2]), regname(oprom[1])); - flags |= 4; - } - break; - - case DASM_indexed_1: - if(oprom[1] & 0x01) { - if(oprom[1] == 0x01) - util::stream_format(stream, " %02x%02x", oprom[3], oprom[2]); - else - util::stream_format(stream, " %02x%02x[%s]", oprom[3], oprom[2], regname(oprom[1]-1)); - flags |= 4; - } else { - int delta = oprom[2]; - if(delta & 0x80) - delta -= 0x100; - if(oprom[1] == 0x00) { - if(delta < 0) - util::stream_format(stream, " %04x", delta & 0xffff); - else - util::stream_format(stream, " %02x", delta); - } else { - if(delta < 0) - util::stream_format(stream, " -%02x[%s]", -delta, regname(oprom[1])); - else - util::stream_format(stream, " %02x[%s]", delta, regname(oprom[1])); - } - flags |= 3; - } - break; - - case DASM_indexed_2: - if(oprom[1] & 0x01) { - if(oprom[1] == 0x01) - util::stream_format(stream, " %s, %02x%02x", regname(oprom[4]), oprom[3], oprom[2]); - else - util::stream_format(stream, " %s, %02x%02x[%s]", regname(oprom[4]), oprom[3], oprom[2], regname(oprom[1]-1)); - flags |= 5; - } else { - int delta = oprom[2]; - if(delta & 0x80) - delta -= 0x100; - if(oprom[1] == 0x00) { - if(delta < 0) - util::stream_format(stream, " %s, %04x", regname(oprom[3]), delta & 0xffff); - else - util::stream_format(stream, " %s, %02x", regname(oprom[3]), delta); - } else { - if(delta < 0) - util::stream_format(stream, " %s, -%02x[%s]", regname(oprom[3]), -delta, regname(oprom[1])); - else - util::stream_format(stream, " %s, %02x[%s]", regname(oprom[3]), delta, regname(oprom[1])); - } - flags |= 4; - } - break; - - case DASM_indexed_3: - if(oprom[1] & 0x01) { - if(oprom[1] == 0x01) - util::stream_format(stream, " %s, %s, %02x%02x", regname(oprom[5]), regname(oprom[4]), oprom[3], oprom[2]); - else - util::stream_format(stream, " %s, %s, %02x%02x[%s]", regname(oprom[5]), regname(oprom[4]), oprom[3], oprom[2], regname(oprom[1]-1)); - flags |= 6; - } else { - int delta = oprom[2]; - if(delta & 0x80) - delta -= 0x100; - if(oprom[1] == 0x00) { - if(delta < 0) - util::stream_format(stream, " %s, %s, %04x", regname(oprom[4]), regname(oprom[3]), delta & 0xffff); - else - util::stream_format(stream, " %s, %s, %02x", regname(oprom[4]), regname(oprom[3]), delta); - } else { - if(delta < 0) - util::stream_format(stream, " %s, %s, -%02x[%s]", regname(oprom[4]), regname(oprom[3]), -delta, regname(oprom[1])); - else - util::stream_format(stream, " %s, %s, %02x[%s]", regname(oprom[4]), regname(oprom[3]), delta, regname(oprom[1])); - } - flags |= 5; - } - break; - - default: - fprintf(stderr, "Unhandled dasm mode %d\n", e.mode); - abort(); - }; - - return flags+off; -} - -uint32_t mcs96_device::disasm_min_opcode_bytes() const -{ - return 1; -} - -uint32_t mcs96_device::disasm_max_opcode_bytes() const -{ - return 7; -} - void mcs96_device::io_w8(uint8_t adr, uint8_t data) { switch(adr) { diff --git a/src/devices/cpu/mcs96/mcs96.h b/src/devices/cpu/mcs96/mcs96.h index 159d04bbdc3..a9440b78ee4 100644 --- a/src/devices/cpu/mcs96/mcs96.h +++ b/src/devices/cpu/mcs96/mcs96.h @@ -41,38 +41,6 @@ protected: F_Z = 0x8000 }; - struct disasm_entry { - const char *opcode, *opcode_fe; - int mode; - offs_t flags; - }; - - enum { - DASM_none, /* No parameters */ - DASM_nop_2, /* One ignored parameter byte */ - DASM_rel8, /* Relative, 8 bits */ - DASM_rel11, /* Relative, 11 bits */ - DASM_rel16, /* Relative, 16 bits */ - DASM_rrel8, /* Register + relative, 8 bits */ - DASM_brrel8, /* Bit test + register + relative, 8 bits */ - DASM_direct_1, /* Register-direct references, 1 operator */ - DASM_direct_2, /* Register-direct references, 2 operators */ - DASM_direct_3, /* Register-direct references, 3 operators */ - DASM_immed_1b, /* Immediate references to byte, 1 operator */ - DASM_immed_2b, /* Immediate references to byte, 2 operators */ - DASM_immed_or_reg_2b, /* Immediate references to byte or register, 2 operators */ - DASM_immed_3b, /* Immediate references to byte, 3 operators */ - DASM_immed_1w, /* Immediate references to word, 1 operator */ - DASM_immed_2w, /* Immediate references to word, 2 operators */ - DASM_immed_3w, /* Immediate references to word, 3 operators */ - DASM_indirect_1n, /* Indirect normal, 1 operator */ - DASM_indirect_1, /* Indirect, normal or auto-incrementing, 1 operator */ - DASM_indirect_2, /* Indirect, normal or auto-incrementing, 2 operators */ - DASM_indirect_3, /* Indirect, normal or auto-incrementing, 3 operators */ - DASM_indexed_1, /* Indexed, short or long, 1 operator */ - DASM_indexed_2, /* Indexed, short or long, 2 operators */ - DASM_indexed_3 /* Indexed, short or long, 3 operators */ - }; mcs96_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock, int data_width); @@ -95,11 +63,6 @@ protected: virtual void state_export(const device_state_entry &entry) override; virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; - // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_generic(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options, const disasm_entry *entries); - address_space_config program_config; address_space *program; direct_read_data *direct; @@ -122,7 +85,6 @@ protected: virtual uint16_t io_r16(uint8_t adr) = 0; void recompute_bcount(uint64_t event_time); - static std::string regname(uint8_t reg); inline void next(int cycles) { icount -= cycles_scaling*cycles; inst_state = STATE_FETCH; } inline void next_noirq(int cycles) { icount -= cycles_scaling*cycles; inst_state = STATE_FETCH_NOIRQ; } diff --git a/src/devices/cpu/mcs96/mcs96d.cpp b/src/devices/cpu/mcs96/mcs96d.cpp new file mode 100644 index 00000000000..1508fb3ca5f --- /dev/null +++ b/src/devices/cpu/mcs96/mcs96d.cpp @@ -0,0 +1,278 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + mcs96.h + + MCS96, 8098/8398/8798 branch + +***************************************************************************/ + +#include "emu.h" +#include "mcs96d.h" + +mcs96_disassembler::mcs96_disassembler(const disasm_entry *entries) : m_entries(entries) +{ +} + +u32 mcs96_disassembler::opcode_alignment() const +{ + return 1; +} + +std::string mcs96_disassembler::regname(uint8_t reg) +{ + switch(reg) { + case 0x18: + return "sp"; + break; + + case 0x19: + return "sph"; + break; + + default: + return util::string_format("%02x", reg); + break; + } +} + +offs_t mcs96_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + bool prefix_fe = false; + int off = 0; + if(opcodes.r8(pc) == 0xfe && m_entries[opcodes.r8(pc+1)].opcode_fe) { + prefix_fe = true; + pc++; + off++; + } + const disasm_entry &e = m_entries[opcodes.r8(pc)]; + uint32_t flags = e.flags | SUPPORTED; + util::stream_format(stream, "%s", prefix_fe ? e.opcode_fe : e.opcode); + + switch(e.mode) { + case DASM_none: + flags |= 1; + break; + + case DASM_nop_2: + util::stream_format(stream, " %02x", opcodes.r8(pc+1)); + flags |= 2; + break; + + case DASM_rel8: { + int delta = opcodes.r8(pc+1); + if(delta & 0x80) + delta -= 0x100; + util::stream_format(stream, " %04x", (pc+2+delta) & 0xffff); + flags |= 2; + break; + } + + case DASM_rel11: { + int delta = ((opcodes.r8(pc) << 8) | opcodes.r8(pc+1)) & 0x7ff; + if(delta & 0x400) + delta -= 0x800; + util::stream_format(stream, " %04x", (pc+2+delta) & 0xffff); + flags |= 2; + break; + } + + case DASM_rel16: { + int delta = opcodes.r8(pc+1) | (opcodes.r8(pc+2) << 8); + util::stream_format(stream, " %04x", (pc+3+delta) & 0xffff); + flags |= 3; + break; + } + + case DASM_rrel8: { + int delta = opcodes.r8(pc+2); + if(delta & 0x80) + delta -= 0x100; + util::stream_format(stream, " %s, %04x", regname(opcodes.r8(pc+1)), (pc+3+delta) & 0xffff); + flags |= 3; + break; + } + + case DASM_brrel8: { + int delta = opcodes.r8(pc+2); + if(delta & 0x80) + delta -= 0x100; + util::stream_format(stream, " %d, %s, %04x", opcodes.r8(pc) & 7, regname(opcodes.r8(pc+1)), (pc+3+delta) & 0xffff); + flags |= 3; + break; + } + + case DASM_direct_1: + util::stream_format(stream, " %s", regname(opcodes.r8(pc+1))); + flags |= 2; + break; + + case DASM_direct_2: + util::stream_format(stream, " %s, %s", regname(opcodes.r8(pc+2)), regname(opcodes.r8(pc+1))); + flags |= 3; + break; + + case DASM_direct_3: + util::stream_format(stream, " %s, %s, %s", regname(opcodes.r8(pc+3)), regname(opcodes.r8(pc+2)), regname(opcodes.r8(pc+1))); + flags |= 4; + break; + + case DASM_immed_1b: + util::stream_format(stream, " #%02x", opcodes.r8(pc+1)); + flags |= 2; + break; + + case DASM_immed_2b: + util::stream_format(stream, " %s, #%02x", regname(opcodes.r8(pc+2)), opcodes.r8(pc+1)); + flags |= 3; + break; + + case DASM_immed_or_reg_2b: + if(opcodes.r8(pc+1) >= 0x10) + util::stream_format(stream, " %s, %s", regname(opcodes.r8(pc+2)), regname(opcodes.r8(pc+1))); + else + util::stream_format(stream, " %s, #%02x", regname(opcodes.r8(pc+2)), opcodes.r8(pc+1)); + flags |= 3; + break; + + case DASM_immed_3b: + util::stream_format(stream, " %s, %s, #%02x", regname(opcodes.r8(pc+3)), regname(opcodes.r8(pc+2)), opcodes.r8(pc+1)); + flags |= 4; + break; + + case DASM_immed_1w: + util::stream_format(stream, " #%02x%02x", opcodes.r8(pc+2), opcodes.r8(pc+1)); + flags |= 3; + break; + + case DASM_immed_2w: + util::stream_format(stream, " %s, #%02x%02x", regname(opcodes.r8(pc+3)), opcodes.r8(pc+2), opcodes.r8(pc+1)); + flags |= 4; + break; + + case DASM_immed_3w: + util::stream_format(stream, " %s, %s, #%02x%02x", regname(opcodes.r8(pc+4)), regname(opcodes.r8(pc+3)), opcodes.r8(pc+2), opcodes.r8(pc+1)); + flags |= 5; + break; + + case DASM_indirect_1n: + util::stream_format(stream, " [%s]", regname(opcodes.r8(pc+1))); + flags |= 2; + break; + + case DASM_indirect_1: + if(opcodes.r8(pc+1) & 0x01) { + util::stream_format(stream, " [%s]+", regname(opcodes.r8(pc+1)-1)); + flags |= 2; + } else { + util::stream_format(stream, " [%s]", regname(opcodes.r8(pc+1))); + flags |= 2; + } + break; + + case DASM_indirect_2: + if(opcodes.r8(pc+1) & 0x01) { + util::stream_format(stream, " %s, [%s]+", regname(opcodes.r8(pc+2)), regname(opcodes.r8(pc+1)-1)); + flags |= 3; + } else { + util::stream_format(stream, " %s, [%s]", regname(opcodes.r8(pc+2)), regname(opcodes.r8(pc+1))); + flags |= 3; + } + break; + + case DASM_indirect_3: + if(opcodes.r8(pc+1) & 0x01) { + util::stream_format(stream, " %s, %s, [%s]+", regname(opcodes.r8(pc+3)), regname(opcodes.r8(pc+2)), regname(opcodes.r8(pc+1)-1)); + flags |= 4; + } else { + util::stream_format(stream, " %s, %s, [%s]", regname(opcodes.r8(pc+3)), regname(opcodes.r8(pc+2)), regname(opcodes.r8(pc+1))); + flags |= 4; + } + break; + + case DASM_indexed_1: + if(opcodes.r8(pc+1) & 0x01) { + if(opcodes.r8(pc+1) == 0x01) + util::stream_format(stream, " %02x%02x", opcodes.r8(pc+3), opcodes.r8(pc+2)); + else + util::stream_format(stream, " %02x%02x[%s]", opcodes.r8(pc+3), opcodes.r8(pc+2), regname(opcodes.r8(pc+1)-1)); + flags |= 4; + } else { + int delta = opcodes.r8(pc+2); + if(delta & 0x80) + delta -= 0x100; + if(opcodes.r8(pc+1) == 0x00) { + if(delta < 0) + util::stream_format(stream, " %04x", delta & 0xffff); + else + util::stream_format(stream, " %02x", delta); + } else { + if(delta < 0) + util::stream_format(stream, " -%02x[%s]", -delta, regname(opcodes.r8(pc+1))); + else + util::stream_format(stream, " %02x[%s]", delta, regname(opcodes.r8(pc+1))); + } + flags |= 3; + } + break; + + case DASM_indexed_2: + if(opcodes.r8(pc+1) & 0x01) { + if(opcodes.r8(pc+1) == 0x01) + util::stream_format(stream, " %s, %02x%02x", regname(opcodes.r8(pc+4)), opcodes.r8(pc+3), opcodes.r8(pc+2)); + else + util::stream_format(stream, " %s, %02x%02x[%s]", regname(opcodes.r8(pc+4)), opcodes.r8(pc+3), opcodes.r8(pc+2), regname(opcodes.r8(pc+1)-1)); + flags |= 5; + } else { + int delta = opcodes.r8(pc+2); + if(delta & 0x80) + delta -= 0x100; + if(opcodes.r8(pc+1) == 0x00) { + if(delta < 0) + util::stream_format(stream, " %s, %04x", regname(opcodes.r8(pc+3)), delta & 0xffff); + else + util::stream_format(stream, " %s, %02x", regname(opcodes.r8(pc+3)), delta); + } else { + if(delta < 0) + util::stream_format(stream, " %s, -%02x[%s]", regname(opcodes.r8(pc+3)), -delta, regname(opcodes.r8(pc+1))); + else + util::stream_format(stream, " %s, %02x[%s]", regname(opcodes.r8(pc+3)), delta, regname(opcodes.r8(pc+1))); + } + flags |= 4; + } + break; + + case DASM_indexed_3: + if(opcodes.r8(pc+1) & 0x01) { + if(opcodes.r8(pc+1) == 0x01) + util::stream_format(stream, " %s, %s, %02x%02x", regname(opcodes.r8(pc+5)), regname(opcodes.r8(pc+4)), opcodes.r8(pc+3), opcodes.r8(pc+2)); + else + util::stream_format(stream, " %s, %s, %02x%02x[%s]", regname(opcodes.r8(pc+5)), regname(opcodes.r8(pc+4)), opcodes.r8(pc+3), opcodes.r8(pc+2), regname(opcodes.r8(pc+1)-1)); + flags |= 6; + } else { + int delta = opcodes.r8(pc+2); + if(delta & 0x80) + delta -= 0x100; + if(opcodes.r8(pc+1) == 0x00) { + if(delta < 0) + util::stream_format(stream, " %s, %s, %04x", regname(opcodes.r8(pc+4)), regname(opcodes.r8(pc+3)), delta & 0xffff); + else + util::stream_format(stream, " %s, %s, %02x", regname(opcodes.r8(pc+4)), regname(opcodes.r8(pc+3)), delta); + } else { + if(delta < 0) + util::stream_format(stream, " %s, %s, -%02x[%s]", regname(opcodes.r8(pc+4)), regname(opcodes.r8(pc+3)), -delta, regname(opcodes.r8(pc+1))); + else + util::stream_format(stream, " %s, %s, %02x[%s]", regname(opcodes.r8(pc+4)), regname(opcodes.r8(pc+3)), delta, regname(opcodes.r8(pc+1))); + } + flags |= 5; + } + break; + + default: + fprintf(stderr, "Unhandled dasm mode %d\n", e.mode); + abort(); + }; + + return flags+off; +} diff --git a/src/devices/cpu/mcs96/mcs96d.h b/src/devices/cpu/mcs96/mcs96d.h new file mode 100644 index 00000000000..453727258bf --- /dev/null +++ b/src/devices/cpu/mcs96/mcs96d.h @@ -0,0 +1,64 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert, R. Belmont +/*************************************************************************** + + mcs96.h + + MCS96 + +***************************************************************************/ + +#ifndef MAME_CPU_MCS96_MCS96D_H +#define MAME_CPU_MCS96_MCS96D_H + +#pragma once + +class mcs96_disassembler : public util::disasm_interface +{ +public: + struct disasm_entry { + const char *opcode, *opcode_fe; + int mode; + offs_t flags; + }; + + mcs96_disassembler(const disasm_entry *entries); + virtual ~mcs96_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +protected: + enum { + DASM_none, /* No parameters */ + DASM_nop_2, /* One ignored parameter byte */ + DASM_rel8, /* Relative, 8 bits */ + DASM_rel11, /* Relative, 11 bits */ + DASM_rel16, /* Relative, 16 bits */ + DASM_rrel8, /* Register + relative, 8 bits */ + DASM_brrel8, /* Bit test + register + relative, 8 bits */ + DASM_direct_1, /* Register-direct references, 1 operator */ + DASM_direct_2, /* Register-direct references, 2 operators */ + DASM_direct_3, /* Register-direct references, 3 operators */ + DASM_immed_1b, /* Immediate references to byte, 1 operator */ + DASM_immed_2b, /* Immediate references to byte, 2 operators */ + DASM_immed_or_reg_2b, /* Immediate references to byte or register, 2 operators */ + DASM_immed_3b, /* Immediate references to byte, 3 operators */ + DASM_immed_1w, /* Immediate references to word, 1 operator */ + DASM_immed_2w, /* Immediate references to word, 2 operators */ + DASM_immed_3w, /* Immediate references to word, 3 operators */ + DASM_indirect_1n, /* Indirect normal, 1 operator */ + DASM_indirect_1, /* Indirect, normal or auto-incrementing, 1 operator */ + DASM_indirect_2, /* Indirect, normal or auto-incrementing, 2 operators */ + DASM_indirect_3, /* Indirect, normal or auto-incrementing, 3 operators */ + DASM_indexed_1, /* Indexed, short or long, 1 operator */ + DASM_indexed_2, /* Indexed, short or long, 2 operators */ + DASM_indexed_3 /* Indexed, short or long, 3 operators */ + }; + + const disasm_entry *m_entries; + + static std::string regname(uint8_t reg); +}; + +#endif diff --git a/src/devices/cpu/mcs96/mcs96make.py b/src/devices/cpu/mcs96/mcs96make.py index b4844942e3d..2a9398cd662 100644 --- a/src/devices/cpu/mcs96/mcs96make.py +++ b/src/devices/cpu/mcs96/mcs96make.py @@ -117,7 +117,7 @@ class OpcodeList: self.opcode_per_id[i] = inf def save_dasm(self, f, t): - print("const %s_device::disasm_entry %s_device::disasm_entries[0x100] = {" % (t, t), file=f) + print("const %s_disassembler::disasm_entry %s_disassembler::disasm_entries[0x100] = {" % (t, t), file=f) for i in range(0, 0x100): if i in self.opcode_per_id: opc = self.opcode_per_id[i] @@ -125,9 +125,9 @@ class OpcodeList: if i + 0xfe00 in self.opcode_per_id: alt = "\"" + self.opcode_per_id[i+0xfe00].name + "\"" if opc.name == "scall" or opc.name == "lcall": - flags = "DASMFLAG_STEP_OVER" + flags = "STEP_OVER" elif opc.name == "rts": - flags = "DASMFLAG_STEP_OUT" + flags = "STEP_OUT" else: flags = "0" print("\t{ \"%s\", %s, DASM_%s, %s }," % (opc.name, alt, opc.amode, flags), file=f) @@ -170,25 +170,26 @@ class OpcodeList: print("}", file=f) def main(argv): - if len(argv) != 4: + if len(argv) != 5: print(USAGE % argv[0]) return 1 - - t = argv[1] - opcodes = OpcodeList(argv[2], t == "i8xc196") + + m = argv[1] + t = argv[2] + opcodes = OpcodeList(argv[3], t == "i8xc196") try: - f = open(argv[3], "w") + f = open(argv[4], "w") except Exception: err = sys.exc_info()[1] - sys.stderr.write("cannot write file %s [%s]\n" % (argv[3], err)) + sys.stderr.write("cannot write file %s [%s]\n" % (argv[4], err)) sys.exit(1) - if t != "mcs96": + if t != "mcs96" and m == "d": opcodes.save_dasm(f, t) - if t != "i8x9x": + if t != "i8x9x" and m == "s": opcodes.save_opcodes(f, t) - if t != "mcs96": + if t != "mcs96" and m == "s": opcodes.save_exec(f, t) f.close() diff --git a/src/devices/cpu/melps4/m58846.cpp b/src/devices/cpu/melps4/m58846.cpp index 6f4924da86e..48c75803439 100644 --- a/src/devices/cpu/melps4/m58846.cpp +++ b/src/devices/cpu/melps4/m58846.cpp @@ -30,15 +30,6 @@ m58846_device::m58846_device(const machine_config &mconfig, const char *tag, dev { } -// disasm -offs_t m58846_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) -{ - extern CPU_DISASSEMBLE(m58846); - return CPU_DISASSEMBLE_NAME(m58846)(this, stream, pc, oprom, opram, options); -} - - - //------------------------------------------------- // device_start - device-specific startup //------------------------------------------------- diff --git a/src/devices/cpu/melps4/m58846.h b/src/devices/cpu/melps4/m58846.h index 4a3bf8674bf..34042e6a61b 100644 --- a/src/devices/cpu/melps4/m58846.h +++ b/src/devices/cpu/melps4/m58846.h @@ -29,9 +29,6 @@ protected: // device_execute_interface overrides virtual void execute_one() override; - // device_disasm_interface overrides - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; - // timers virtual void device_timer(emu_timer &timer, device_timer_id id, int param, void *ptr) override; virtual void write_v(uint8_t data) override; diff --git a/src/devices/cpu/melps4/melps4.cpp b/src/devices/cpu/melps4/melps4.cpp index bf386f1e30d..c8c5b6e1cd7 100644 --- a/src/devices/cpu/melps4/melps4.cpp +++ b/src/devices/cpu/melps4/melps4.cpp @@ -39,6 +39,7 @@ #include "emu.h" #include "melps4.h" +#include "melps4d.h" #include "debugger.h" @@ -471,3 +472,8 @@ void melps4_cpu_device::execute_run() execute_one(); } } + +util::disasm_interface *melps4_cpu_device::create_disassembler() +{ + return new melps4_disassembler; +} diff --git a/src/devices/cpu/melps4/melps4.h b/src/devices/cpu/melps4/melps4.h index 1f9a7752cd6..c268d74e508 100644 --- a/src/devices/cpu/melps4/melps4.h +++ b/src/devices/cpu/melps4/melps4.h @@ -135,8 +135,8 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 2; } + virtual util::disasm_interface *create_disassembler() override; + virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; address_space_config m_program_config; diff --git a/src/devices/cpu/melps4/melps4d.cpp b/src/devices/cpu/melps4/melps4d.cpp index efd199097c5..8ab9c0bd2c7 100644 --- a/src/devices/cpu/melps4/melps4d.cpp +++ b/src/devices/cpu/melps4/melps4d.cpp @@ -10,27 +10,9 @@ */ #include "emu.h" -#include "debugger.h" -#include "melps4.h" +#include "melps4d.h" - -// opcode mnemonics -enum e_mnemonics -{ - em_ILL, - em_TAB, em_TBA, em_TAY, em_TYA, em_TEAB, em_TABE, em_TEPA, em_TXA, em_TAX, - em_LXY, em_LZ, em_INY, em_DEY, em_LCPS, em_SADR, - em_TAM, em_XAM, em_XAMD, em_XAMI, - em_LA, em_AM, em_AMC, em_AMCS, em_A, em_SC, em_RC, em_SZC, em_CMA, em_RL, em_RR, - em_SB, em_RB, em_SZB, em_SEAM, em_SEY, - em_TLA, em_THA, em_TAJ, em_XAL, em_XAH, em_LC7, em_DEC, em_SHL, em_RHL, em_CPA, em_CPAS, em_CPAE, em_SZJ, - em_T1AB, em_TRAB, em_T2AB, em_TAB1, em_TABR, em_TAB2, em_TVA, em_TWA, em_SNZ1, em_SNZ2, - em_BA, em_SP, em_B, em_BM, em_RT, em_RTS, em_RTI, - em_CLD, em_CLS, em_CLDS, em_SD, em_RD, em_SZD, em_OSAB, em_OSPA, em_OSE, em_IAS, em_OFA, em_IAF, em_OGA, em_IAK, em_SZK, em_SU, em_RU, - em_EI, em_DI, em_INTH, em_INTL, em_NOP -}; - -static const char *const em_name[] = +const char *const melps4_disassembler::em_name[] = { "?", "TAB", "TBA", "TAY", "TYA", "TEAB", "TABE", "TEPA", "TXA", "TAX", @@ -46,7 +28,7 @@ static const char *const em_name[] = }; // number of bits per opcode parameter -static const uint8_t em_bits[] = +const uint8_t melps4_disassembler::em_bits[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, @@ -61,10 +43,7 @@ static const uint8_t em_bits[] = 0, 0, 0, 0, 0 }; -#define _OVER DASMFLAG_STEP_OVER -#define _OUT DASMFLAG_STEP_OUT - -static const uint32_t em_flags[] = +const uint32_t melps4_disassembler::em_flags[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, @@ -74,7 +53,7 @@ static const uint32_t em_flags[] = 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, _OVER, _OUT, _OUT, _OUT, + 0, 0, 0, STEP_OVER, STEP_OUT, STEP_OUT, STEP_OUT, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; @@ -83,7 +62,7 @@ static const uint32_t em_flags[] = // M58846 disasm -static const uint8_t m58846_opmap[0xc0] = +const uint8_t melps4_disassembler::m58846_opmap[0xc0] = { // 0 1 2 3 4 5 6 7 8 9 A B C D E F em_NOP, em_BA, em_INY, em_DEY, em_DI, em_EI, em_RU, em_SU, 0, em_TABE, em_AM, em_OSE, em_TYA, 0, 0, em_CMA, // 0x @@ -100,9 +79,9 @@ static const uint8_t m58846_opmap[0xc0] = em_LA, em_LA, em_LA, em_LA, em_LA, em_LA, em_LA, em_LA, em_LA, em_LA, em_LA, em_LA, em_LA, em_LA, em_LA, em_LA // Bx }; -CPU_DISASSEMBLE(m58846) +offs_t melps4_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - uint16_t op = (oprom[0] | oprom[1] << 8) & 0x1ff; + uint16_t op = opcodes.r16(pc) & 0x1ff; // get opcode uint8_t instr; @@ -136,5 +115,20 @@ CPU_DISASSEMBLE(m58846) util::stream_format(stream, " %d", param); } - return 1 | em_flags[instr] | DASMFLAG_SUPPORTED; + return 1 | em_flags[instr] | SUPPORTED; +} + +u32 melps4_disassembler::opcode_alignment() const +{ + return 1; +} + +u32 melps4_disassembler::interface_flags() const +{ + return PAGED; +} + +u32 melps4_disassembler::page_address_bits() const +{ + return 7; } diff --git a/src/devices/cpu/melps4/melps4d.h b/src/devices/cpu/melps4/melps4d.h new file mode 100644 index 00000000000..229358e7432 --- /dev/null +++ b/src/devices/cpu/melps4/melps4d.h @@ -0,0 +1,52 @@ +// license:BSD-3-Clause +// copyright-holders:hap +/* + + Mitsubishi MELPS 4 MCU family disassembler + + Not counting the extra opcodes for peripherals (eg. timers, A/D), + each MCU in the series has small differences in the opcode map. + +*/ + +#ifndef MAME_CPU_MELPS4_MELPS4D_H +#define MAME_CPU_MELPS4_MELPS4D_H + +#pragma once + +class melps4_disassembler : public util::disasm_interface +{ +public: + melps4_disassembler() = default; + virtual ~melps4_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual u32 interface_flags() const override; + virtual u32 page_address_bits() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + // opcode mnemonics + enum e_mnemonics + { + em_ILL, + em_TAB, em_TBA, em_TAY, em_TYA, em_TEAB, em_TABE, em_TEPA, em_TXA, em_TAX, + em_LXY, em_LZ, em_INY, em_DEY, em_LCPS, em_SADR, + em_TAM, em_XAM, em_XAMD, em_XAMI, + em_LA, em_AM, em_AMC, em_AMCS, em_A, em_SC, em_RC, em_SZC, em_CMA, em_RL, em_RR, + em_SB, em_RB, em_SZB, em_SEAM, em_SEY, + em_TLA, em_THA, em_TAJ, em_XAL, em_XAH, em_LC7, em_DEC, em_SHL, em_RHL, em_CPA, em_CPAS, em_CPAE, em_SZJ, + em_T1AB, em_TRAB, em_T2AB, em_TAB1, em_TABR, em_TAB2, em_TVA, em_TWA, em_SNZ1, em_SNZ2, + em_BA, em_SP, em_B, em_BM, em_RT, em_RTS, em_RTI, + em_CLD, em_CLS, em_CLDS, em_SD, em_RD, em_SZD, em_OSAB, em_OSPA, em_OSE, em_IAS, em_OFA, em_IAF, em_OGA, em_IAK, em_SZK, em_SU, em_RU, + em_EI, em_DI, em_INTH, em_INTL, em_NOP + }; + + static const char *const em_name[]; + static const uint8_t em_bits[]; + static const uint32_t em_flags[]; + static const uint8_t m58846_opmap[0xc0]; + +}; + +#endif diff --git a/src/devices/cpu/minx/minx.cpp b/src/devices/cpu/minx/minx.cpp index 883abb6f843..7e4a898e22c 100644 --- a/src/devices/cpu/minx/minx.cpp +++ b/src/devices/cpu/minx/minx.cpp @@ -46,6 +46,7 @@ TODO: #include "emu.h" #include "minx.h" +#include "minxd.h" #include "debugger.h" #define FLAG_I 0x80 @@ -234,8 +235,7 @@ void minx_cpu_device::execute_set_input(int inputnum, int state) } -offs_t minx_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *minx_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( minx ); - return CPU_DISASSEMBLE_NAME(minx)(this, stream, pc, oprom, opram, options); + return new minx_disassembler; } diff --git a/src/devices/cpu/minx/minx.h b/src/devices/cpu/minx/minx.h index babc3d182aa..57f0456c76b 100644 --- a/src/devices/cpu/minx/minx.h +++ b/src/devices/cpu/minx/minx.h @@ -39,9 +39,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 5; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/minx/minxd.cpp b/src/devices/cpu/minx/minxd.cpp index 0e3b9d5b090..413f588369f 100644 --- a/src/devices/cpu/minx/minxd.cpp +++ b/src/devices/cpu/minx/minxd.cpp @@ -8,61 +8,10 @@ ************************************************************/ #include "emu.h" -#include "debugger.h" -#include "minx.h" +#include "minxd.h" -enum e_mnemonic { - zADD=0, zADDC, zAND, zBCDD, zBCDE, zBCDX, zCALL, zCALLC, zCALLG, zCALLGE, zCALLL, - zCALLLE, zCALLN, zCALLNC, zCALLNO, zCALLNZ, zCALLO, zCALLP, zCALLNX0, - zCALLNX1, zCALLNX2, zCALLNX3, zCALLX0, zCALLX1, zCALLX2, zCALLX3, zCALLZ, - zCMP, zCMPN, zDEC, zDIV, zEXT, zHALT, zINC, zINT, - zJC, zJDBNZ, zJG, zJGE, zJINT, zJL, zJLE, zJMP, - zJN, zJNX0, zJNX1, zJNX2, zJNX3, zJNC, zJNO, zJNZ, - zJO, zJP, zJX0, zJX1, zJX2, zJX3, zJZ, zMOV, - zMUL, zNEG, zNOP, zNOT, zOR, zPOP, zPOPA, zPOPAX, - zPOPX, zPUSH, zPUSHA, zPUSHAX, zPUSHX, zRET, zRETI, zRETSKIP, - zROL, zROLC, zROR, zRORC, zSAL, zSAR, zSHL, zSHR, zSUB, - zSUBC, zTEST, zXCHG, zXOR, zDB -}; - -enum e_operand { - R_A=1, /* A */ - R_B, /* B */ - R_L, /* L */ - R_H, /* H */ - R_N, /* N */ - R_F, /* F */ - R_SP, /* SP */ - R_BA, /* BA */ - R_HL, /* HL */ - R_X, /* X */ - R_Y, /* Y */ - R_U, /* U */ - R_V, /* V */ - R_I, /* I */ - R_XI, /* XI */ - R_YI, /* YI */ - R_PC, /* PC */ - I_8, /* 8 bit immediate */ - I_16, /* 16 bit immediate */ - D_8, /* PC + 8 bit displacement (signed) */ - D_16, /* PC + 16 bit displacement */ - S_8, /* SP + 8 bit displacement (signed) */ - M_IHL, /* [I+HL] */ - M_N8, /* [I+N+ofs8] */ - M_I16, /* [I+ofs16] */ - M_X, /* [X] */ - M_Y, /* [Y] */ - M_X8, /* [X + 8 bit displacement (signed)] */ - M_Y8, /* [Y + 8 bit displacement (signed)] */ - M_XL, /* [X + L (signed)] */ - M_YL, /* [Y + L (signed)] */ - M_16, /* [16bit] */ - M_HL, /* [HL] */ - OP, OP1 -}; -static const char *const s_mnemonic[] = { +const char *const minx_disassembler::s_mnemonic[] = { "add", "addc", "and", "bcdd", "bcde", "bcdx", "call", "callc", "callg", "callge", "calll", "callle", "calln", "callnc", "callno", "callnz", "callo", "callp", "callnx0", "callnx1", "callnx2", "callnx3", "callx0", "callx1", "callx2", "callx3", "callz", @@ -76,30 +25,21 @@ static const char *const s_mnemonic[] = { "subc", "test", "xchg", "xor", "db" }; -#define _OVER DASMFLAG_STEP_OVER -#define _OUT DASMFLAG_STEP_OUT - -static const uint32_t s_flags[] = { - 0, 0, 0, 0, 0, 0, _OVER, _OVER, _OVER, _OVER, _OVER, - _OVER, _OVER, _OVER, _OVER, _OVER, _OVER, _OVER, _OVER, - _OVER, _OVER, _OVER, _OVER, _OVER, _OVER, _OVER, _OVER, - 0, 0, 0, 0, 0, _OVER, 0, _OVER, +const uint32_t minx_disassembler::s_flags[] = { + 0, 0, 0, 0, 0, 0, STEP_OVER, STEP_OVER, STEP_OVER, STEP_OVER, STEP_OVER, + STEP_OVER, STEP_OVER, STEP_OVER, STEP_OVER, STEP_OVER, STEP_OVER, STEP_OVER, STEP_OVER, + STEP_OVER, STEP_OVER, STEP_OVER, STEP_OVER, STEP_OVER, STEP_OVER, STEP_OVER, STEP_OVER, + 0, 0, 0, 0, 0, STEP_OVER, 0, STEP_OVER, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, _OUT, _OUT, _OUT, + 0, 0, 0, 0, 0, STEP_OUT, STEP_OUT, STEP_OUT, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, }; -struct minxdasm { - uint8_t mnemonic; - uint8_t argument1; - uint8_t argument2; -}; - -static const minxdasm mnemonic[256] = { +const minx_disassembler::minxdasm minx_disassembler::mnemonic[256] = { /* 00 - 0F */ {zADD,R_A,R_A}, {zADD,R_A,R_B}, {zADD,R_A,I_8}, {zADD,R_A,M_IHL}, {zADD,R_A,M_N8}, {zADD,R_A,M_I16}, {zADD,R_A,M_X}, {zADD,R_A,M_Y}, @@ -182,7 +122,7 @@ static const minxdasm mnemonic[256] = { {zINT,I_8,0}, {zJINT,I_8,0}, {zDB,OP,0}, {zNOP,0,0} }; -static const minxdasm mnemonic_ce[256] = { +const minx_disassembler::minxdasm minx_disassembler::mnemonic_ce[256] = { /* 00 - 0F */ {zADD,R_A,M_X8}, {zADD,R_A,M_Y8}, {zADD,R_A,M_XL}, {zADD,R_A,M_YL}, {zADD,M_IHL,R_A}, {zADD,M_IHL,I_8}, {zADD,M_IHL,M_X}, {zADD,M_IHL,M_Y}, @@ -265,7 +205,7 @@ static const minxdasm mnemonic_ce[256] = { {zCALLX0,D_8,0}, {zCALLX1,D_8,0}, {zCALLX2,D_8,0}, {zCALLX3,D_8,0} }; -static const minxdasm mnemonic_cf[256] = { +const minx_disassembler::minxdasm minx_disassembler::mnemonic_cf[256] = { /* 00 - 0F */ {zADD,R_BA,R_BA}, {zADD,R_BA,R_HL}, {zADD,R_BA,R_X}, {zADD,R_BA,R_Y}, {zADDC,R_BA,R_BA}, {zADDC,R_BA,R_HL}, {zADDC,R_BA,R_X}, {zADDC,R_BA,R_Y}, @@ -367,76 +307,81 @@ case R_XI: util::stream_format(stream, "%cXI", fill); break; \ case R_YI: util::stream_format(stream, "%cYI", fill); break; \ case R_PC: util::stream_format(stream, "%cPC", fill); break; \ case I_8: /* 8 bit immediate */ \ - ea = oprom[pos++]; \ + ea = opcodes.r8(pos++); \ util::stream_format(stream, "%c$%02X", fill, ea); \ break; \ case I_16: /* 16 bit immediate */ \ - ea = oprom[pos++]; \ - ea += oprom[pos++] << 8; \ + ea = opcodes.r8(pos++); \ + ea += opcodes.r8(pos++) << 8; \ util::stream_format(stream, "%c$%04X", fill, ea); \ break; \ case D_8: /* PC + 8 bit displacement (signed) */ \ - ofs8 = oprom[pos++]; \ + ofs8 = opcodes.r8(pos++); \ util::stream_format(stream, "%c$%04X", fill, pc + pos - 1 + ofs8); \ break; \ case D_16: /* PC + 16 bit displacement */ \ - ea = oprom[pos++]; \ - ea += oprom[pos++] << 8; \ + ea = opcodes.r8(pos++); \ + ea += opcodes.r8(pos++) << 8; \ ea = ea - 1; \ util::stream_format(stream, "%c$%04X", fill, pc + pos + ea); \ break; \ case S_8: /* SP + 8 bit displacement (signed) */ \ - ea = oprom[pos++]; \ + ea = opcodes.r8(pos++); \ util::stream_format(stream, "%cSP+$%02X", fill, ea); \ break; \ case M_IHL: util::stream_format(stream, "%c[I+HL]", fill); break; \ case M_N8: /* [I+N+ofs8] */ \ - ea = oprom[pos++]; \ + ea = opcodes.r8(pos++); \ util::stream_format(stream, "%c[I+N+$%02X]", fill, ea); \ break; \ case M_I16: /* [I+ofs16] */ \ - ea = oprom[pos++]; \ - ea += oprom[pos++] << 8; \ + ea = opcodes.r8(pos++); \ + ea += opcodes.r8(pos++) << 8; \ util::stream_format(stream, "%c[I+$%04X]", fill, ea); \ break; \ case M_X: util::stream_format(stream, "%c[X]", fill); break; \ case M_Y: util::stream_format(stream, "%c[Y]", fill); break; \ case M_X8: /* [X + 8 bit displacement (signed)] */ \ - ea = oprom[pos++]; \ + ea = opcodes.r8(pos++); \ util::stream_format(stream, "%c[X+$%02X]", fill, ea); \ break; \ case M_Y8: /* [Y + 8 bit displacement (signed)] */ \ - ea = oprom[pos++]; \ + ea = opcodes.r8(pos++); \ util::stream_format(stream, "%c[Y+$%02X]", fill, ea); \ break; \ case M_XL: util::stream_format(stream, "%c[X+L]", fill); break; \ case M_YL: util::stream_format(stream, "%c[Y+L]", fill); break; \ case M_16: /* [16bit] */ \ - ea = oprom[pos++]; \ - ea += oprom[pos++] << 8; \ + ea = opcodes.r8(pos++); \ + ea += opcodes.r8(pos++) << 8; \ util::stream_format(stream, "%c[$%04X]", fill, ea); \ break; \ case M_HL: util::stream_format(stream, "%c[HL]", fill); break; \ case OP: util::stream_format(stream, "%c$%02X", fill, op); break; \ case OP1: util::stream_format(stream, "%c$%02X", fill, op1); break; -CPU_DISASSEMBLE(minx) +u32 minx_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t minx_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { const minxdasm *instr; uint8_t op, op1; int8_t ofs8; uint16_t ea; - int pos = 0; + offs_t pos = pc; - op1 = op = oprom[pos++]; + op1 = op = opcodes.r8(pos++); switch (op) { case 0xCE: - op = oprom[pos++]; + op = opcodes.r8(pos++); instr = &mnemonic_ce[op]; break; case 0xCF: - op = oprom[pos++]; + op = opcodes.r8(pos++); instr = &mnemonic_cf[op]; break; default: @@ -460,5 +405,5 @@ CPU_DISASSEMBLE(minx) HANDLE_ARGUMENT; } } - return pos | s_flags[instr->mnemonic] | DASMFLAG_SUPPORTED; + return (pos - pc) | s_flags[instr->mnemonic] | SUPPORTED; } diff --git a/src/devices/cpu/minx/minxd.h b/src/devices/cpu/minx/minxd.h new file mode 100644 index 00000000000..bb7a6da4e0d --- /dev/null +++ b/src/devices/cpu/minx/minxd.h @@ -0,0 +1,89 @@ +// license:BSD-3-Clause +// copyright-holders:Wilbert Pol +/************************************************************ + + Nintendo Minx CPU disassembly + + +************************************************************/ + +#ifndef MAME_CPU_MINX_MINXDASM_H +#define MAME_CPU_MINX_MINXDASM_H + +#pragma once + +class minx_disassembler : public util::disasm_interface +{ +public: + minx_disassembler() = default; + virtual ~minx_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum e_mnemonic { + zADD=0, zADDC, zAND, zBCDD, zBCDE, zBCDX, zCALL, zCALLC, zCALLG, zCALLGE, zCALLL, + zCALLLE, zCALLN, zCALLNC, zCALLNO, zCALLNZ, zCALLO, zCALLP, zCALLNX0, + zCALLNX1, zCALLNX2, zCALLNX3, zCALLX0, zCALLX1, zCALLX2, zCALLX3, zCALLZ, + zCMP, zCMPN, zDEC, zDIV, zEXT, zHALT, zINC, zINT, + zJC, zJDBNZ, zJG, zJGE, zJINT, zJL, zJLE, zJMP, + zJN, zJNX0, zJNX1, zJNX2, zJNX3, zJNC, zJNO, zJNZ, + zJO, zJP, zJX0, zJX1, zJX2, zJX3, zJZ, zMOV, + zMUL, zNEG, zNOP, zNOT, zOR, zPOP, zPOPA, zPOPAX, + zPOPX, zPUSH, zPUSHA, zPUSHAX, zPUSHX, zRET, zRETI, zRETSKIP, + zROL, zROLC, zROR, zRORC, zSAL, zSAR, zSHL, zSHR, zSUB, + zSUBC, zTEST, zXCHG, zXOR, zDB + }; + + enum e_operand { + R_A=1, /* A */ + R_B, /* B */ + R_L, /* L */ + R_H, /* H */ + R_N, /* N */ + R_F, /* F */ + R_SP, /* SP */ + R_BA, /* BA */ + R_HL, /* HL */ + R_X, /* X */ + R_Y, /* Y */ + R_U, /* U */ + R_V, /* V */ + R_I, /* I */ + R_XI, /* XI */ + R_YI, /* YI */ + R_PC, /* PC */ + I_8, /* 8 bit immediate */ + I_16, /* 16 bit immediate */ + D_8, /* PC + 8 bit displacement (signed) */ + D_16, /* PC + 16 bit displacement */ + S_8, /* SP + 8 bit displacement (signed) */ + M_IHL, /* [I+HL] */ + M_N8, /* [I+N+ofs8] */ + M_I16, /* [I+ofs16] */ + M_X, /* [X] */ + M_Y, /* [Y] */ + M_X8, /* [X + 8 bit displacement (signed)] */ + M_Y8, /* [Y + 8 bit displacement (signed)] */ + M_XL, /* [X + L (signed)] */ + M_YL, /* [Y + L (signed)] */ + M_16, /* [16bit] */ + M_HL, /* [HL] */ + OP, OP1 + }; + + struct minxdasm { + uint8_t mnemonic; + uint8_t argument1; + uint8_t argument2; + }; + + static const char *const s_mnemonic[]; + static const uint32_t s_flags[]; + static const minxdasm mnemonic[256]; + static const minxdasm mnemonic_ce[256]; + static const minxdasm mnemonic_cf[256]; +}; + +#endif diff --git a/src/devices/cpu/mips/mips3.cpp b/src/devices/cpu/mips/mips3.cpp index 772ee9c0464..ddb02775162 100644 --- a/src/devices/cpu/mips/mips3.cpp +++ b/src/devices/cpu/mips/mips3.cpp @@ -12,6 +12,7 @@ #include "debugger.h" #include "mips3.h" #include "mips3com.h" +#include "mips3dsm.h" #define ENABLE_OVERFLOWS 0 @@ -975,14 +976,9 @@ bool mips3_device::memory_translate(int spacenum, int intention, offs_t &address } -offs_t mips3_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *mips3_device::create_disassembler() { - uint32_t op = *(uint32_t *)oprom; - if (m_bigendian) - op = big_endianize_int32(op); - else - op = little_endianize_int32(op); - return dasmmips3(stream, pc, op); + return new mips3_disassembler; } diff --git a/src/devices/cpu/mips/mips3.h b/src/devices/cpu/mips/mips3.h index 6d763c8792b..5f4cb632743 100644 --- a/src/devices/cpu/mips/mips3.h +++ b/src/devices/cpu/mips/mips3.h @@ -312,9 +312,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 4; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: @@ -802,11 +800,4 @@ private: #define MIPS3DRC_FASTEST_OPTIONS (0) -/*************************************************************************** - DISASSEMBLING -***************************************************************************/ - -unsigned dasmmips3(std::ostream &stream, unsigned pc, uint32_t op); - - #endif // MAME_CPU_MIPS_MIPS3_H diff --git a/src/devices/cpu/mips/mips3drc.cpp b/src/devices/cpu/mips/mips3drc.cpp index ac15a2e51b7..db90d525149 100644 --- a/src/devices/cpu/mips/mips3drc.cpp +++ b/src/devices/cpu/mips/mips3drc.cpp @@ -27,6 +27,7 @@ #include "debugger.h" #include "mips3com.h" #include "mips3fe.h" +#include "mips3dsm.h" #include "cpu/drcfe.h" #include "cpu/drcuml.h" #include "cpu/drcumlsh.h" @@ -3286,8 +3287,9 @@ void mips3_device::log_add_disasm_comment(drcuml_block *block, uint32_t pc, uint { if (m_drcuml->logging()) { + mips3_disassembler mips3d; std::ostringstream stream; - dasmmips3(stream, pc, op); + mips3d.dasm_one(stream, pc, op); const std::string stream_string = stream.str(); block->append_comment("%08X: %s", pc, stream_string.c_str()); // comment } @@ -3425,7 +3427,10 @@ void mips3_device::log_opcode_desc(drcuml_state *drcuml, const opcode_desc *desc if (desclist->flags & OPFLAG_VIRTUAL_NOOP) buffer << ""; else - dasmmips3(buffer, desclist->pc, desclist->opptr.l[0]); + { + mips3_disassembler mips3d; + mips3d.dasm_one(buffer, desclist->pc, desclist->opptr.l[0]); + } } else buffer << "???"; diff --git a/src/devices/cpu/mips/mips3dsm.cpp b/src/devices/cpu/mips/mips3dsm.cpp index acc7abbcc75..5252a552b8c 100644 --- a/src/devices/cpu/mips/mips3dsm.cpp +++ b/src/devices/cpu/mips/mips3dsm.cpp @@ -9,11 +9,12 @@ ***************************************************************************/ #include "emu.h" +#include "mips3dsm.h" #define USE_ABI_REG_NAMES (1) #if USE_ABI_REG_NAMES -static const char *const reg[32] = +const char *const mips3_disassembler::reg[32] = { "$0", "$at", "$v0", "$v1", "$a0", "$a1", "$a2", "$a3", "$t0", "$t1", "$t2", "$t3", "$t4", "$t5", "$t6", "$t7", @@ -21,7 +22,7 @@ static const char *const reg[32] = "$t8", "$t9", "$k0", "$k1", "$gp", "$sp", "$fp", "$ra" }; #else -static const char *const reg[32] = +const char *const mips3_disassembler::reg[32] = { "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15", @@ -30,7 +31,7 @@ static const char *const reg[32] = }; #endif -static const char *const cacheop[32] = +const char *const mips3_disassembler::cacheop[32] = { "I_Invd", "D_WBInvd", "Unknown 2", "Unknown 3", "I_IndexLoadTag", "D_IndexLoadTag", "Unknown 6", "Unknown 7", "I_IndexStoreTag", "D_IndexStoreTag", "Unknown 10", "Unknown 11", "Unknown 12", "D_CreateDirtyExcl", "Unknown 14", "Unknown 15", @@ -39,7 +40,7 @@ static const char *const cacheop[32] = }; -static const char *const cpreg[4][32] = +const char *const mips3_disassembler::cpreg[4][32] = { { "Index","Random","EntryLo0","EntryLo1","Context","PageMask","Wired","Error", @@ -68,7 +69,7 @@ static const char *const cpreg[4][32] = }; -static const char *const ccreg[4][32] = +const char *const mips3_disassembler::ccreg[4][32] = { { "ccr0", "ccr1", "ccr2", "ccr3", "ccr4", "ccr5", "ccr6", "ccr7", @@ -101,17 +102,15 @@ static const char *const ccreg[4][32] = CODE CODE ***************************************************************************/ -static inline char *signed_16bit(int16_t val) +inline std::string mips3_disassembler::signed_16bit(int16_t val) { - static char temp[10]; if (val < 0) - sprintf(temp, "-$%x", -val); + return util::string_format("-$%x", -val); else - sprintf(temp, "$%x", val); - return temp; + return util::string_format("$%x", val); } -static uint32_t dasm_cop0(uint32_t pc, uint32_t op, std::ostream &stream) +uint32_t mips3_disassembler::dasm_cop0(uint32_t pc, uint32_t op, std::ostream &stream) { int rt = (op >> 16) & 31; int rd = (op >> 11) & 31; @@ -157,7 +156,7 @@ static uint32_t dasm_cop0(uint32_t pc, uint32_t op, std::ostream &stream) case 0x02: util::stream_format(stream, "tlbwi"); break; case 0x06: util::stream_format(stream, "tlbwr"); break; case 0x08: util::stream_format(stream, "tlbp"); break; - case 0x10: util::stream_format(stream, "rfe"); flags = DASMFLAG_STEP_OUT; break; + case 0x10: util::stream_format(stream, "rfe"); flags = STEP_OUT; break; case 0x18: util::stream_format(stream, "eret [invalid]"); break; default: util::stream_format(stream, "cop0 $%07x", op & 0x01ffffff); break; } @@ -167,9 +166,9 @@ static uint32_t dasm_cop0(uint32_t pc, uint32_t op, std::ostream &stream) return flags; } -static uint32_t dasm_cop1(uint32_t pc, uint32_t op, std::ostream &stream) +uint32_t mips3_disassembler::dasm_cop1(uint32_t pc, uint32_t op, std::ostream &stream) { - static const char *const format_table[] = + const char *const format_table[] = { "?","?","?","?","?","?","?","?","?","?","?","?","?","?","?","?", "s","d","?","?","w","l","?","?","?","?","?","?","?","?","?","?" @@ -195,8 +194,8 @@ static uint32_t dasm_cop1(uint32_t pc, uint32_t op, std::ostream &stream) { case 0x00: util::stream_format(stream, "bc1f $%08x,%d", pc + 4 + ((int16_t)op << 2), (op >> 18) & 7); break; case 0x01: util::stream_format(stream, "bc1t $%08x,%d", pc + 4 + ((int16_t)op << 2), (op >> 18) & 7); break; - case 0x02: util::stream_format(stream, "bc1fl $%08x,%d", pc + 4 + ((int16_t)op << 2), (op >> 18) & 7); flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); break; - case 0x03: util::stream_format(stream, "bc1tl $%08x,%d", pc + 4 + ((int16_t)op << 2), (op >> 18) & 7); flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); break; + case 0x02: util::stream_format(stream, "bc1fl $%08x,%d", pc + 4 + ((int16_t)op << 2), (op >> 18) & 7); flags = STEP_OVER | step_over_extra(1); break; + case 0x03: util::stream_format(stream, "bc1tl $%08x,%d", pc + 4 + ((int16_t)op << 2), (op >> 18) & 7); flags = STEP_OVER | step_over_extra(1); break; } break; default: /* COP */ @@ -250,9 +249,9 @@ static uint32_t dasm_cop1(uint32_t pc, uint32_t op, std::ostream &stream) return flags; } -static uint32_t dasm_cop1x(uint32_t pc, uint32_t op, std::ostream &stream) +uint32_t mips3_disassembler::dasm_cop1x(uint32_t pc, uint32_t op, std::ostream &stream) { - static const char *const format3_table[] = + const char *const format3_table[] = { "s","d","?","?","w","l","?","?" }; @@ -310,7 +309,7 @@ static uint32_t dasm_cop1x(uint32_t pc, uint32_t op, std::ostream &stream) return flags; } -static uint32_t dasm_cop2(uint32_t pc, uint32_t op, std::ostream &stream) +uint32_t mips3_disassembler::dasm_cop2(uint32_t pc, uint32_t op, std::ostream &stream) { int rt = (op >> 16) & 31; int rd = (op >> 11) & 31; @@ -357,7 +356,12 @@ static uint32_t dasm_cop2(uint32_t pc, uint32_t op, std::ostream &stream) return flags; } -unsigned dasmmips3(std::ostream &stream, unsigned pc, uint32_t op) +u32 mips3_disassembler::opcode_alignment() const +{ + return 4; +} + +offs_t mips3_disassembler::dasm_one(std::ostream &stream, offs_t pc, u32 op) { int rs = (op >> 21) & 31; int rt = (op >> 16) & 31; @@ -381,17 +385,17 @@ unsigned dasmmips3(std::ostream &stream, unsigned pc, uint32_t op) case 0x04: util::stream_format(stream, "sllv %s,%s,%s", reg[rd], reg[rt], reg[rs]); break; case 0x06: util::stream_format(stream, "srlv %s,%s,%s", reg[rd], reg[rt], reg[rs]); break; case 0x07: util::stream_format(stream, "srav %s,%s,%s", reg[rd], reg[rt], reg[rs]); break; - case 0x08: util::stream_format(stream, "jr %s", reg[rs]); if (rs == 31) flags = DASMFLAG_STEP_OUT; break; + case 0x08: util::stream_format(stream, "jr %s", reg[rs]); if (rs == 31) flags = STEP_OUT; break; case 0x09: if (rd == 31) util::stream_format(stream, "jalr %s", reg[rs]); else util::stream_format(stream, "jalr %s,%s", reg[rs], reg[rd]); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; case 0x0a: util::stream_format(stream, "movz %s,%s,%s", reg[rd], reg[rs], reg[rt]); break; case 0x0b: util::stream_format(stream, "movn %s,%s,%s", reg[rd], reg[rs], reg[rt]); break; - case 0x0c: util::stream_format(stream, "syscall"); flags = DASMFLAG_STEP_OVER; break; - case 0x0d: util::stream_format(stream, "break"); flags = DASMFLAG_STEP_OVER; break; + case 0x0c: util::stream_format(stream, "syscall"); flags = STEP_OVER; break; + case 0x0d: util::stream_format(stream, "break"); flags = STEP_OVER; break; case 0x0f: util::stream_format(stream, "sync"); break; case 0x10: util::stream_format(stream, "mfhi %s", reg[rd]); break; case 0x11: util::stream_format(stream, "mthi %s", reg[rs]); break; @@ -422,12 +426,12 @@ unsigned dasmmips3(std::ostream &stream, unsigned pc, uint32_t op) case 0x2d: util::stream_format(stream, "daddu %s,%s,%s", reg[rd], reg[rs], reg[rt]); break; case 0x2e: util::stream_format(stream, "dsub %s,%s,%s", reg[rd], reg[rs], reg[rt]); break; case 0x2f: util::stream_format(stream, "dsubu %s,%s,%s", reg[rd], reg[rs], reg[rt]); break; - case 0x30: util::stream_format(stream, "tge %s,%s", reg[rs], reg[rt]); flags = DASMFLAG_STEP_OVER; break; - case 0x31: util::stream_format(stream, "tgeu %s,%s", reg[rs], reg[rt]); flags = DASMFLAG_STEP_OVER; break; - case 0x32: util::stream_format(stream, "tlt %s,%s", reg[rs], reg[rt]); flags = DASMFLAG_STEP_OVER; break; - case 0x33: util::stream_format(stream, "tltu %s,%s", reg[rs], reg[rt]); flags = DASMFLAG_STEP_OVER; break; - case 0x34: util::stream_format(stream, "teq %s,%s", reg[rs], reg[rt]); flags = DASMFLAG_STEP_OVER; break; - case 0x36: util::stream_format(stream, "tne %s,%s", reg[rs], reg[rt]) ;flags = DASMFLAG_STEP_OVER; break; + case 0x30: util::stream_format(stream, "tge %s,%s", reg[rs], reg[rt]); flags = STEP_OVER; break; + case 0x31: util::stream_format(stream, "tgeu %s,%s", reg[rs], reg[rt]); flags = STEP_OVER; break; + case 0x32: util::stream_format(stream, "tlt %s,%s", reg[rs], reg[rt]); flags = STEP_OVER; break; + case 0x33: util::stream_format(stream, "tltu %s,%s", reg[rs], reg[rt]); flags = STEP_OVER; break; + case 0x34: util::stream_format(stream, "teq %s,%s", reg[rs], reg[rt]); flags = STEP_OVER; break; + case 0x36: util::stream_format(stream, "tne %s,%s", reg[rs], reg[rt]) ;flags = STEP_OVER; break; case 0x38: util::stream_format(stream, "dsll %s,%s,%d", reg[rd], reg[rt], shift); break; case 0x3a: util::stream_format(stream, "dsrl %s,%s,%d", reg[rd], reg[rt], shift); break; case 0x3b: util::stream_format(stream, "dsra %s,%s,%d", reg[rd], reg[rt], shift); break; @@ -445,22 +449,22 @@ unsigned dasmmips3(std::ostream &stream, unsigned pc, uint32_t op) case 0x01: util::stream_format(stream, "bgez %s,$%08x", reg[rs], pc + 4 + ((int16_t)op << 2)); break; case 0x02: util::stream_format(stream, "bltzl %s,$%08x", reg[rs], pc + 4 + ((int16_t)op << 2)); break; case 0x03: util::stream_format(stream, "bgezl %s,$%08x", reg[rs], pc + 4 + ((int16_t)op << 2)); break; - case 0x08: util::stream_format(stream, "tgei %s,%s", reg[rs], signed_16bit(op)); flags = DASMFLAG_STEP_OVER; break; - case 0x09: util::stream_format(stream, "tgeiu %s,%s", reg[rs], signed_16bit(op)); flags = DASMFLAG_STEP_OVER; break; - case 0x0a: util::stream_format(stream, "tlti %s,%s", reg[rs], signed_16bit(op)); flags = DASMFLAG_STEP_OVER; break; - case 0x0b: util::stream_format(stream, "tltiu %s,%s", reg[rs], signed_16bit(op)); flags = DASMFLAG_STEP_OVER; break; - case 0x0c: util::stream_format(stream, "teqi %s,%s", reg[rs], signed_16bit(op)); flags = DASMFLAG_STEP_OVER; break; - case 0x0e: util::stream_format(stream, "tnei %s,%s", reg[rs], signed_16bit(op)); flags = DASMFLAG_STEP_OVER; break; - case 0x10: util::stream_format(stream, "bltzal %s,$%08x", reg[rs], pc + 4 + ((int16_t)op << 2)); flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); break; - case 0x11: util::stream_format(stream, "bgezal %s,$%08x", reg[rs], pc + 4 + ((int16_t)op << 2)); flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); break; - case 0x12: util::stream_format(stream, "bltzall %s,$%08x", reg[rs], pc + 4 + ((int16_t)op << 2)); flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); break; - case 0x13: util::stream_format(stream, "bgezall %s,$%08x", reg[rs], pc + 4 + ((int16_t)op << 2)); flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); break; + case 0x08: util::stream_format(stream, "tgei %s,%s", reg[rs], signed_16bit(op)); flags = STEP_OVER; break; + case 0x09: util::stream_format(stream, "tgeiu %s,%s", reg[rs], signed_16bit(op)); flags = STEP_OVER; break; + case 0x0a: util::stream_format(stream, "tlti %s,%s", reg[rs], signed_16bit(op)); flags = STEP_OVER; break; + case 0x0b: util::stream_format(stream, "tltiu %s,%s", reg[rs], signed_16bit(op)); flags = STEP_OVER; break; + case 0x0c: util::stream_format(stream, "teqi %s,%s", reg[rs], signed_16bit(op)); flags = STEP_OVER; break; + case 0x0e: util::stream_format(stream, "tnei %s,%s", reg[rs], signed_16bit(op)); flags = STEP_OVER; break; + case 0x10: util::stream_format(stream, "bltzal %s,$%08x", reg[rs], pc + 4 + ((int16_t)op << 2)); flags = STEP_OVER | step_over_extra(1); break; + case 0x11: util::stream_format(stream, "bgezal %s,$%08x", reg[rs], pc + 4 + ((int16_t)op << 2)); flags = STEP_OVER | step_over_extra(1); break; + case 0x12: util::stream_format(stream, "bltzall %s,$%08x", reg[rs], pc + 4 + ((int16_t)op << 2)); flags = STEP_OVER | step_over_extra(1); break; + case 0x13: util::stream_format(stream, "bgezall %s,$%08x", reg[rs], pc + 4 + ((int16_t)op << 2)); flags = STEP_OVER | step_over_extra(1); break; default: util::stream_format(stream, "dc.l $%08x [invalid]", op); break; } break; case 0x02: util::stream_format(stream, "j $%08x", (pc & 0xf0000000) | ((op & 0x03ffffff) << 2)); break; - case 0x03: util::stream_format(stream, "jal $%08x", (pc & 0xf0000000) | ((op & 0x03ffffff) << 2)); flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); break; + case 0x03: util::stream_format(stream, "jal $%08x", (pc & 0xf0000000) | ((op & 0x03ffffff) << 2)); flags = STEP_OVER | step_over_extra(1); break; case 0x04: if (rs == 0 && rt == 0) util::stream_format(stream, "b $%08x", pc + 4 + ((int16_t)op << 2)); else @@ -532,21 +536,11 @@ unsigned dasmmips3(std::ostream &stream, unsigned pc, uint32_t op) case 0x3f: util::stream_format(stream, "sd %s,%s(%s)", reg[rt], signed_16bit(op), reg[rs]); break; default: util::stream_format(stream, "dc.l $%08x [invalid]", op); break; } - return 4 | flags | DASMFLAG_SUPPORTED; -} - - -CPU_DISASSEMBLE( mips3be ) -{ - uint32_t op = *(uint32_t *)oprom; - op = big_endianize_int32(op); - return dasmmips3(stream, pc, op); + return 4 | flags | SUPPORTED; } - -CPU_DISASSEMBLE( mips3le ) +offs_t mips3_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - uint32_t op = *(uint32_t *)oprom; - op = little_endianize_int32(op); - return dasmmips3(stream, pc, op); + u32 op = opcodes.r32(pc); + return dasm_one(stream, pc, op); } diff --git a/src/devices/cpu/mips/mips3dsm.h b/src/devices/cpu/mips/mips3dsm.h new file mode 100644 index 00000000000..a38771bbba0 --- /dev/null +++ b/src/devices/cpu/mips/mips3dsm.h @@ -0,0 +1,40 @@ +// license:BSD-3-Clause +// copyright-holders:Aaron Giles +/*************************************************************************** + + mips3dsm.c + Disassembler for the portable MIPS 3 emulator. + Written by Aaron Giles + +***************************************************************************/ + +#ifndef MAME_CPU_MIPS_MIPS3DSM_H +#define MAME_CPU_MIPS_MIPS3DSM_H + +#pragma once + +class mips3_disassembler : public util::disasm_interface +{ +public: + mips3_disassembler() = default; + virtual ~mips3_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + + offs_t dasm_one(std::ostream &stream, offs_t pc, u32 op); + +private: + static const char *const reg[32]; + static const char *const cacheop[32]; + static const char *const cpreg[4][32]; + static const char *const ccreg[4][32]; + inline std::string signed_16bit(int16_t val); + uint32_t dasm_cop0(uint32_t pc, uint32_t op, std::ostream &stream); + uint32_t dasm_cop1(uint32_t pc, uint32_t op, std::ostream &stream); + uint32_t dasm_cop1x(uint32_t pc, uint32_t op, std::ostream &stream); + uint32_t dasm_cop2(uint32_t pc, uint32_t op, std::ostream &stream); + +}; + +#endif diff --git a/src/devices/cpu/mips/r3000.cpp b/src/devices/cpu/mips/r3000.cpp index 2e29e967747..a63d04a511e 100644 --- a/src/devices/cpu/mips/r3000.cpp +++ b/src/devices/cpu/mips/r3000.cpp @@ -10,6 +10,7 @@ #include "emu.h" #include "r3000.h" +#include "r3kdasm.h" #include "debugger.h" @@ -453,41 +454,13 @@ void r3000_device::state_string_export(const device_state_entry &entry, std::str //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t r3000_device::disasm_min_opcode_bytes() const -{ - return 4; -} - - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t r3000_device::disasm_max_opcode_bytes() const -{ - return 4; -} - - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t r3000_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *r3000_device::create_disassembler() { - extern CPU_DISASSEMBLE( r3000le ); - extern CPU_DISASSEMBLE( r3000be ); - - if (m_endianness == ENDIANNESS_BIG) - return CPU_DISASSEMBLE_NAME(r3000be)(this, stream, pc, oprom, opram, options); - else - return CPU_DISASSEMBLE_NAME(r3000le)(this, stream, pc, oprom, opram, options); + return new r3000_disassembler; } diff --git a/src/devices/cpu/mips/r3000.h b/src/devices/cpu/mips/r3000.h index 1d458d93de9..088c54c26e0 100644 --- a/src/devices/cpu/mips/r3000.h +++ b/src/devices/cpu/mips/r3000.h @@ -131,9 +131,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // memory accessors struct r3000_data_accessors diff --git a/src/devices/cpu/mips/r3kdasm.cpp b/src/devices/cpu/mips/r3kdasm.cpp index 1e8a2d7a16d..7e004a95068 100644 --- a/src/devices/cpu/mips/r3kdasm.cpp +++ b/src/devices/cpu/mips/r3kdasm.cpp @@ -9,9 +9,9 @@ ***************************************************************************/ #include "emu.h" +#include "r3kdasm.h" - -static const char *const reg[32] = +const char *const r3000_disassembler::reg[32] = { "0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15", @@ -20,7 +20,7 @@ static const char *const reg[32] = }; -static const char *const cpreg[4][32] = +const char *const r3000_disassembler::cpreg[4][32] = { { "Index","Random","EntryLo","cpr3", "Context", "cpr5", "cpr6", "cpr7", @@ -49,7 +49,7 @@ static const char *const cpreg[4][32] = }; -static const char *const ccreg[4][32] = +const char *const r3000_disassembler::ccreg[4][32] = { { "ccr0", "ccr1", "ccr2", "ccr3", "ccr4", "ccr5", "ccr6", "ccr7", @@ -82,17 +82,15 @@ static const char *const ccreg[4][32] = CODE CODE ***************************************************************************/ -static inline char *signed_16bit(int16_t val) +std::string r3000_disassembler::signed_16bit(int16_t val) { - static char temp[10]; if (val < 0) - sprintf(temp, "-$%x", -val); + return util::string_format("-$%x", -val); else - sprintf(temp, "$%x", val); - return temp; + return util::string_format("$%x", val); } -static uint32_t dasm_cop(uint32_t pc, int cop, uint32_t op, std::ostream &stream) +uint32_t r3000_disassembler::dasm_cop(uint32_t pc, int cop, uint32_t op, std::ostream &stream) { int rt = (op >> 16) & 31; int rd = (op >> 11) & 31; @@ -152,7 +150,7 @@ static uint32_t dasm_cop(uint32_t pc, int cop, uint32_t op, std::ostream &stream return flags; } -static uint32_t dasm_cop1(uint32_t pc, uint32_t op, std::ostream &stream) +uint32_t r3000_disassembler::dasm_cop1(uint32_t pc, uint32_t op, std::ostream &stream) { static const char *const format_table[] = { @@ -180,8 +178,8 @@ static uint32_t dasm_cop1(uint32_t pc, uint32_t op, std::ostream &stream) { case 0x00: util::stream_format(stream, "bc1f $%08x,%d", pc + 4 + ((int16_t)op << 2), (op >> 18) & 7); break; case 0x01: util::stream_format(stream, "bc1t $%08x,%d", pc + 4 + ((int16_t)op << 2), (op >> 18) & 7); break; - case 0x02: util::stream_format(stream, "bc1fl $%08x,%d", pc + 4 + ((int16_t)op << 2), (op >> 18) & 7); flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); break; - case 0x03: util::stream_format(stream, "bc1tl $%08x,%d", pc + 4 + ((int16_t)op << 2), (op >> 18) & 7); flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); break; + case 0x02: util::stream_format(stream, "bc1fl $%08x,%d", pc + 4 + ((int16_t)op << 2), (op >> 18) & 7); flags = STEP_OVER | step_over_extra(1); break; + case 0x03: util::stream_format(stream, "bc1tl $%08x,%d", pc + 4 + ((int16_t)op << 2), (op >> 18) & 7); flags = STEP_OVER | step_over_extra(1); break; } break; default: /* COP */ @@ -235,8 +233,9 @@ static uint32_t dasm_cop1(uint32_t pc, uint32_t op, std::ostream &stream) return flags; } -static unsigned dasmr3k(std::ostream &stream, unsigned pc, uint32_t op) +offs_t r3000_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { + uint32_t op = opcodes.r32(pc); int rs = (op >> 21) & 31; int rt = (op >> 16) & 31; int rd = (op >> 11) & 31; @@ -258,15 +257,15 @@ static unsigned dasmr3k(std::ostream &stream, unsigned pc, uint32_t op) case 0x04: util::stream_format(stream, "sllv %s,%s,%s", reg[rd], reg[rt], reg[rs]); break; case 0x06: util::stream_format(stream, "srlv %s,%s,%s", reg[rd], reg[rt], reg[rs]); break; case 0x07: util::stream_format(stream, "srav %s,%s,%s", reg[rd], reg[rt], reg[rs]); break; - case 0x08: util::stream_format(stream, "jr %s", reg[rs]); if (rs == 31) flags = DASMFLAG_STEP_OUT; break; + case 0x08: util::stream_format(stream, "jr %s", reg[rs]); if (rs == 31) flags = STEP_OUT; break; case 0x09: if (rd == 31) util::stream_format(stream, "jalr %s", reg[rs]); else util::stream_format(stream, "jalr %s,%s", reg[rs], reg[rd]); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; - case 0x0c: util::stream_format(stream, "syscall"); flags = DASMFLAG_STEP_OVER; break; - case 0x0d: util::stream_format(stream, "break"); flags = DASMFLAG_STEP_OVER; break; + case 0x0c: util::stream_format(stream, "syscall"); flags = STEP_OVER; break; + case 0x0d: util::stream_format(stream, "break"); flags = STEP_OVER; break; case 0x0f: util::stream_format(stream, "sync [invalid]"); break; case 0x10: util::stream_format(stream, "mfhi %s", reg[rd]); break; case 0x11: util::stream_format(stream, "mthi %s", reg[rs]); break; @@ -309,8 +308,8 @@ static unsigned dasmr3k(std::ostream &stream, unsigned pc, uint32_t op) case 0x0b: util::stream_format(stream, "tltiu [invalid]"); break; case 0x0c: util::stream_format(stream, "teqi [invalid]"); break; case 0x0e: util::stream_format(stream, "tnei [invalid]"); break; - case 0x10: util::stream_format(stream, "bltzal %s,$%08x", reg[rs], pc + 4 + ((int16_t)op << 2)); flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); break; - case 0x11: util::stream_format(stream, "bgezal %s,$%08x", reg[rs], pc + 4 + ((int16_t)op << 2)); flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); break; + case 0x10: util::stream_format(stream, "bltzal %s,$%08x", reg[rs], pc + 4 + ((int16_t)op << 2)); flags = STEP_OVER | step_over_extra(1); break; + case 0x11: util::stream_format(stream, "bgezal %s,$%08x", reg[rs], pc + 4 + ((int16_t)op << 2)); flags = STEP_OVER | step_over_extra(1); break; case 0x12: util::stream_format(stream, "bltzall [invalid]"); break; case 0x13: util::stream_format(stream, "bgezall [invalid]"); break; default: util::stream_format(stream, "dc.l $%08x [invalid]", op); break; @@ -318,7 +317,7 @@ static unsigned dasmr3k(std::ostream &stream, unsigned pc, uint32_t op) break; case 0x02: util::stream_format(stream, "j $%08x", (pc & 0xf0000000) | ((op & 0x0fffffff) << 2)); break; - case 0x03: util::stream_format(stream, "jal $%08x", (pc & 0xf0000000) | ((op & 0x0fffffff) << 2)); flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); break; + case 0x03: util::stream_format(stream, "jal $%08x", (pc & 0xf0000000) | ((op & 0x0fffffff) << 2)); flags = STEP_OVER | step_over_extra(1); break; case 0x04: if (rs == 0 && rt == 0) util::stream_format(stream, "b $%08x", pc + 4 + ((int16_t)op << 2)); else @@ -374,21 +373,10 @@ static unsigned dasmr3k(std::ostream &stream, unsigned pc, uint32_t op) case 0x3f: util::stream_format(stream, "sdc3 [invalid]"); break; default: util::stream_format(stream, "dc.l $%08x [invalid]", op); break; } - return 4 | flags | DASMFLAG_SUPPORTED; -} - - -CPU_DISASSEMBLE( r3000be ) -{ - uint32_t op = *(uint32_t *)oprom; - op = big_endianize_int32(op); - return dasmr3k(stream, pc, op); + return 4 | flags | SUPPORTED; } - -CPU_DISASSEMBLE( r3000le ) +uint32_t r3000_disassembler::opcode_alignment() const { - uint32_t op = *(uint32_t *)oprom; - op = little_endianize_int32(op); - return dasmr3k(stream, pc, op); + return 4; } diff --git a/src/devices/cpu/mips/r3kdasm.h b/src/devices/cpu/mips/r3kdasm.h new file mode 100644 index 00000000000..7eec7e7c1f8 --- /dev/null +++ b/src/devices/cpu/mips/r3kdasm.h @@ -0,0 +1,36 @@ +// license:BSD-3-Clause +// copyright-holders:Aaron Giles +/*************************************************************************** + + r3kdasm.c + Disassembler for the portable R3000 emulator. + Written by Aaron Giles + +***************************************************************************/ + +#ifndef MAME_CPU_MIPS_R3KDASM_H +#define MAME_CPU_MIPS_R3KDASM_H + +#pragma once + +class r3000_disassembler : public util::disasm_interface +{ +public: + r3000_disassembler() = default; + virtual ~r3000_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *const reg[32]; + static const char *const cpreg[4][32]; + static const char *const ccreg[4][32]; + std::string signed_16bit(int16_t val); + uint32_t dasm_cop(uint32_t pc, int cop, uint32_t op, std::ostream &stream); + uint32_t dasm_cop1(uint32_t pc, uint32_t op, std::ostream &stream); + + +}; + +#endif diff --git a/src/devices/cpu/mn10200/mn10200.cpp b/src/devices/cpu/mn10200/mn10200.cpp index 59407b507ca..74757bd9e53 100644 --- a/src/devices/cpu/mn10200/mn10200.cpp +++ b/src/devices/cpu/mn10200/mn10200.cpp @@ -11,6 +11,7 @@ #include "emu.h" #include "debugger.h" #include "mn10200.h" +#include "mn102dis.h" #define log_write(...) #define log_event(...) @@ -88,10 +89,9 @@ void mn10200_device::state_string_export(const device_state_entry &entry, std::s } } -offs_t mn10200_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *mn10200_device::create_disassembler() { - extern CPU_DISASSEMBLE( mn10200 ); - return CPU_DISASSEMBLE_NAME(mn10200)(this, stream, pc, oprom, opram, options); + return new mn10200_disassembler; } diff --git a/src/devices/cpu/mn10200/mn10200.h b/src/devices/cpu/mn10200/mn10200.h index 307b0b4b6a9..7f3524df68c 100644 --- a/src/devices/cpu/mn10200/mn10200.h +++ b/src/devices/cpu/mn10200/mn10200.h @@ -87,9 +87,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 7; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/mn10200/mn102dis.cpp b/src/devices/cpu/mn10200/mn102dis.cpp index be3fb46c0eb..8be02ad6a58 100644 --- a/src/devices/cpu/mn10200/mn102dis.cpp +++ b/src/devices/cpu/mn10200/mn102dis.cpp @@ -5,76 +5,47 @@ */ #include "emu.h" +#include "mn102dis.h" -#include - -static const uint8_t *sOpROM; // current opROM pointer -static uint32_t sBasePC; - -static uint8_t program_read_byte(offs_t pc) -{ - return sOpROM[pc - sBasePC]; -} - -static uint32_t r16u(offs_t pc) -{ - return sOpROM[pc - sBasePC] | (sOpROM[pc - sBasePC + 1]<<8); -} - -static int32_t r16s(offs_t pc) -{ - return (int16_t)(sOpROM[pc - sBasePC] | (sOpROM[pc - sBasePC + 1]<<8)); -} - -static uint32_t r24u(offs_t pc) +u32 mn10200_disassembler::r24(const data_buffer &opcodes, offs_t pc) { - return sOpROM[pc - sBasePC] | (sOpROM[pc - sBasePC + 1]<<8) | (sOpROM[pc - sBasePC + 2]<<16); + return opcodes.r16(pc) | (opcodes.r8(pc+2) << 16); } -static int32_t r24s(offs_t pc) +std::string mn10200_disassembler::i8str(s8 v) { - return sOpROM[pc - sBasePC] | (sOpROM[pc - sBasePC + 1]<<8) | ((int8_t)sOpROM[pc - sBasePC + 2]<<16); -} - -static const char *i8str(int8_t v) -{ - static char res[0x10]; if(v>=0) - sprintf(res, "$%x", v); + return util::string_format("$%x", v); else - sprintf(res, "-$%x", (uint8_t)(-v)); - return res; + return util::string_format("-$%x", u8(-v)); } -static const char *i16str(int16_t v) +std::string mn10200_disassembler::i16str(int16_t v) { - static char res[0x10]; if(v>=0) - sprintf(res, "$%x", v); + return util::string_format("$%x", v); else - sprintf(res, "-$%x", (uint16_t)(-v)); - return res; + return util::string_format("-$%x", u16(-v)); } -static const char *i24str(int32_t v) -{ - static char res[0x10]; - if(v>=0) - sprintf(res, "$%x", v); +std::string mn10200_disassembler::i24str(u32 v) +{ + if(!(v & 0x800000)) + return util::string_format("$%x", v & 0xffffff); else - sprintf(res, "-$%x", -v); - return res; + return util::string_format("-$%x", (-v) & 0xffffff); } - -static int mn102_disassemble(std::ostream &stream, uint32_t pc, const uint8_t *oprom) +u32 mn10200_disassembler::opcode_alignment() const { - uint8_t opcode; + return 1; +} - sOpROM = oprom; - sBasePC = pc; +offs_t mn10200_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + u8 opcode; - opcode = program_read_byte(pc); + opcode = opcodes.r8(pc); switch(opcode) { case 0x00: case 0x01: case 0x02: case 0x03: case 0x04: case 0x05: case 0x06: case 0x07: @@ -99,22 +70,22 @@ static int mn102_disassemble(std::ostream &stream, uint32_t pc, const uint8_t *o case 0x40: case 0x41: case 0x42: case 0x43: case 0x44: case 0x45: case 0x46: case 0x47: case 0x48: case 0x49: case 0x4a: case 0x4b: case 0x4c: case 0x4d: case 0x4e: case 0x4f: - util::stream_format(stream, "mov d%d, (%s, a%d)", opcode & 3, i8str(program_read_byte(pc+1)), (opcode>>2) & 3); + util::stream_format(stream, "mov d%d, (%s, a%d)", opcode & 3, i8str(opcodes.r8(pc+1)), (opcode>>2) & 3); return 2; case 0x50: case 0x51: case 0x52: case 0x53: case 0x54: case 0x55: case 0x56: case 0x57: case 0x58: case 0x59: case 0x5a: case 0x5b: case 0x5c: case 0x5d: case 0x5e: case 0x5f: - util::stream_format(stream, "mov a%d, (%s, a%d)", opcode & 3, i8str(program_read_byte(pc+1)), (opcode>>2) & 3); + util::stream_format(stream, "mov a%d, (%s, a%d)", opcode & 3, i8str(opcodes.r8(pc+1)), (opcode>>2) & 3); return 2; case 0x60: case 0x61: case 0x62: case 0x63: case 0x64: case 0x65: case 0x66: case 0x67: case 0x68: case 0x69: case 0x6a: case 0x6b: case 0x6c: case 0x6d: case 0x6e: case 0x6f: - util::stream_format(stream, "mov (%s, a%d), d%d", i8str(program_read_byte(pc+1)), (opcode>>2) & 3, opcode & 3); + util::stream_format(stream, "mov (%s, a%d), d%d", i8str(opcodes.r8(pc+1)), (opcode>>2) & 3, opcode & 3); return 2; case 0x70: case 0x71: case 0x72: case 0x73: case 0x74: case 0x75: case 0x76: case 0x77: case 0x78: case 0x79: case 0x7a: case 0x7b: case 0x7c: case 0x7d: case 0x7e: case 0x7f: - util::stream_format(stream, "mov (%s, a%d), a%d", i8str(program_read_byte(pc+1)), (opcode>>2) & 3, opcode & 3); + util::stream_format(stream, "mov (%s, a%d), a%d", i8str(opcodes.r8(pc+1)), (opcode>>2) & 3, opcode & 3); return 2; case 0x81: case 0x82: case 0x83: case 0x84: case 0x86: case 0x87: @@ -123,7 +94,7 @@ static int mn102_disassemble(std::ostream &stream, uint32_t pc, const uint8_t *o return 1; case 0x80: case 0x85: case 0x8a: case 0x8f: - util::stream_format(stream, "mov %s, d%d", i8str(program_read_byte(pc+1)), opcode & 3); + util::stream_format(stream, "mov %s, d%d", i8str(opcodes.r8(pc+1)), opcode & 3); return 2; case 0x90: case 0x91: case 0x92: case 0x93: case 0x94: case 0x95: case 0x96: case 0x97: @@ -153,79 +124,79 @@ static int mn102_disassemble(std::ostream &stream, uint32_t pc, const uint8_t *o return 1; case 0xc0: case 0xc1: case 0xc2: case 0xc3: - util::stream_format(stream, "mov d%d, ($%04x)", opcode & 3, r16u(pc+1)); + util::stream_format(stream, "mov d%d, ($%04x)", opcode & 3, opcodes.r16(pc+1)); return 3; case 0xc4: case 0xc5: case 0xc6: case 0xc7: - util::stream_format(stream, "movb d%d, ($%04x)", opcode & 3, r16u(pc+1)); + util::stream_format(stream, "movb d%d, ($%04x)", opcode & 3, opcodes.r16(pc+1)); return 3; case 0xc8: case 0xc9: case 0xca: case 0xcb: - util::stream_format(stream, "mov ($%04x), d%d", r16u(pc+1), opcode & 3); + util::stream_format(stream, "mov ($%04x), d%d", opcodes.r16(pc+1), opcode & 3); return 3; case 0xcc: case 0xcd: case 0xce: case 0xcf: - util::stream_format(stream, "movbu ($%04x), d%d", r16u(pc+1), opcode & 3); + util::stream_format(stream, "movbu ($%04x), d%d", opcodes.r16(pc+1), opcode & 3); return 3; case 0xd0: case 0xd1: case 0xd2: case 0xd3: - util::stream_format(stream, "add %s, a%d", i8str(program_read_byte(pc+1)), opcode & 3); + util::stream_format(stream, "add %s, a%d", i8str(opcodes.r8(pc+1)), opcode & 3); return 2; case 0xd4: case 0xd5: case 0xd6: case 0xd7: - util::stream_format(stream, "add %s, d%d", i8str(program_read_byte(pc+1)), opcode & 3); + util::stream_format(stream, "add %s, d%d", i8str(opcodes.r8(pc+1)), opcode & 3); return 2; case 0xd8: case 0xd9: case 0xda: case 0xdb: - util::stream_format(stream, "cmp %s, d%d", i8str(program_read_byte(pc+1)), opcode & 3); + util::stream_format(stream, "cmp %s, d%d", i8str(opcodes.r8(pc+1)), opcode & 3); return 2; case 0xdc: case 0xdd: case 0xde: case 0xdf: - util::stream_format(stream, "move $%04x, a%d", r16u(pc+1), opcode & 3); + util::stream_format(stream, "move $%04x, a%d", opcodes.r16(pc+1), opcode & 3); return 3; case 0xe0: - util::stream_format(stream, "blt $%x", (pc+2+(int8_t)program_read_byte(pc+1)) & 0xffffff); + util::stream_format(stream, "blt $%x", (pc+2+(s8)opcodes.r8(pc+1)) & 0xffffff); return 2; case 0xe1: - util::stream_format(stream, "bgt $%x", (pc+2+(int8_t)program_read_byte(pc+1)) & 0xffffff); + util::stream_format(stream, "bgt $%x", (pc+2+(s8)opcodes.r8(pc+1)) & 0xffffff); return 2; case 0xe2: - util::stream_format(stream, "bge $%x", (pc+2+(int8_t)program_read_byte(pc+1)) & 0xffffff); + util::stream_format(stream, "bge $%x", (pc+2+(s8)opcodes.r8(pc+1)) & 0xffffff); return 2; case 0xe3: - util::stream_format(stream, "ble $%x", (pc+2+(int8_t)program_read_byte(pc+1)) & 0xffffff); + util::stream_format(stream, "ble $%x", (pc+2+(s8)opcodes.r8(pc+1)) & 0xffffff); return 2; case 0xe4: - util::stream_format(stream, "bcs $%x", (pc+2+(int8_t)program_read_byte(pc+1)) & 0xffffff); + util::stream_format(stream, "bcs $%x", (pc+2+(s8)opcodes.r8(pc+1)) & 0xffffff); return 2; case 0xe5: - util::stream_format(stream, "bhi $%x", (pc+2+(int8_t)program_read_byte(pc+1)) & 0xffffff); + util::stream_format(stream, "bhi $%x", (pc+2+(s8)opcodes.r8(pc+1)) & 0xffffff); return 2; case 0xe6: - util::stream_format(stream, "bcc $%x", (pc+2+(int8_t)program_read_byte(pc+1)) & 0xffffff); + util::stream_format(stream, "bcc $%x", (pc+2+(s8)opcodes.r8(pc+1)) & 0xffffff); return 2; case 0xe7: - util::stream_format(stream, "bls $%x", (pc+2+(int8_t)program_read_byte(pc+1)) & 0xffffff); + util::stream_format(stream, "bls $%x", (pc+2+(s8)opcodes.r8(pc+1)) & 0xffffff); return 2; case 0xe8: - util::stream_format(stream, "beq $%x", (pc+2+(int8_t)program_read_byte(pc+1)) & 0xffffff); + util::stream_format(stream, "beq $%x", (pc+2+(s8)opcodes.r8(pc+1)) & 0xffffff); return 2; case 0xe9: - util::stream_format(stream, "bne $%x", (pc+2+(int8_t)program_read_byte(pc+1)) & 0xffffff); + util::stream_format(stream, "bne $%x", (pc+2+(s8)opcodes.r8(pc+1)) & 0xffffff); return 2; case 0xea: - util::stream_format(stream, "bra $%x", (pc+2+(int8_t)program_read_byte(pc+1)) & 0xffffff); + util::stream_format(stream, "bra $%x", (pc+2+(s8)opcodes.r8(pc+1)) & 0xffffff); return 2; case 0xeb: @@ -233,11 +204,11 @@ static int mn102_disassemble(std::ostream &stream, uint32_t pc, const uint8_t *o return 1; case 0xec: case 0xed: case 0xee: case 0xef: - util::stream_format(stream, "cmp $%04x, a%d", r16u(pc+1), opcode & 3); + util::stream_format(stream, "cmp $%04x, a%d", opcodes.r16(pc+1), opcode & 3); return 3; case 0xf0: - opcode = program_read_byte(pc+1); + opcode = opcodes.r8(pc+1); switch(opcode) { case 0x00: case 0x04: case 0x08: case 0x0c: @@ -296,7 +267,7 @@ static int mn102_disassemble(std::ostream &stream, uint32_t pc, const uint8_t *o } case 0xf1: - opcode = program_read_byte(pc+1); + opcode = opcodes.r8(pc+1); switch(opcode&0xc0) { case 0x00: @@ -318,7 +289,7 @@ static int mn102_disassemble(std::ostream &stream, uint32_t pc, const uint8_t *o break; case 0xf2: - opcode = program_read_byte(pc+1); + opcode = opcodes.r8(pc+1); switch(opcode&0xf0) { case 0x00: @@ -382,7 +353,7 @@ static int mn102_disassemble(std::ostream &stream, uint32_t pc, const uint8_t *o } case 0xf3: - opcode = program_read_byte(pc+1); + opcode = opcodes.r8(pc+1); switch(opcode) { case 0x00: case 0x01: case 0x02: case 0x03: case 0x04: case 0x05: case 0x06: case 0x07: @@ -465,25 +436,25 @@ static int mn102_disassemble(std::ostream &stream, uint32_t pc, const uint8_t *o return 2; case 0xfe: - opcode = program_read_byte(pc+2); + opcode = opcodes.r8(pc+2); switch(opcode) { case 0xc0: case 0xc1: case 0xc2: case 0xc3: case 0xc4: case 0xc5: case 0xc6: case 0xc7: - util::stream_format(stream, "tbz ($%x) %d, $%x", r24u(pc+3), opcode & 7, - (pc+7+(int8_t)program_read_byte(pc+6)) & 0xffffff); + util::stream_format(stream, "tbz ($%x) %d, $%x", r24(opcodes, pc+3), opcode & 7, + (pc+7+(s8)opcodes.r8(pc+6)) & 0xffffff); return 7; case 0xc8: case 0xc9: case 0xca: case 0xcb: case 0xcc: case 0xcd: case 0xce: case 0xcf: - util::stream_format(stream, "tbnz ($%x) %d, $%x", r24u(pc+3), opcode & 7, - (pc+7+(int8_t)program_read_byte(pc+6)) & 0xffffff); + util::stream_format(stream, "tbnz ($%x) %d, $%x", r24(opcodes, pc+3), opcode & 7, + (pc+7+(s8)opcodes.r8(pc+6)) & 0xffffff); return 7; case 0xd0: case 0xd1: case 0xd2: case 0xd3: case 0xd4: case 0xd5: case 0xd6: case 0xd7: - util::stream_format(stream, "bset ($%x) %d", r24u(pc+2), opcode & 7); + util::stream_format(stream, "bset ($%x) %d", r24(opcodes, pc+2), opcode & 7); return 6; case 0xd8: case 0xd9: case 0xda: case 0xdb: case 0xdc: case 0xdd: case 0xde: case 0xdf: - util::stream_format(stream, "bclr ($%x) %d", r24u(pc+2), opcode & 7); + util::stream_format(stream, "bclr ($%x) %d", r24(opcodes, pc+2), opcode & 7); return 6; default: @@ -491,29 +462,29 @@ static int mn102_disassemble(std::ostream &stream, uint32_t pc, const uint8_t *o } case 0xff: - opcode = program_read_byte(pc+2); + opcode = opcodes.r8(pc+2); switch(opcode) { case 0x80: case 0x81: case 0x82: case 0x83: case 0x84: case 0x85: case 0x86: case 0x87: case 0x88: case 0x89: case 0x8a: case 0x8b: case 0x8c: case 0x8d: case 0x8e: case 0x8f: - util::stream_format(stream, "tbz (%s, a%d) %d, $%x", i8str(program_read_byte(pc+3)), 2+((opcode>>3)&1), opcode & 7, - (pc+5+(int8_t)program_read_byte(pc+4)) & 0xffffff); + util::stream_format(stream, "tbz (%s, a%d) %d, $%x", i8str(opcodes.r8(pc+3)), 2+((opcode>>3)&1), opcode & 7, + (pc+5+(s8)opcodes.r8(pc+4)) & 0xffffff); return 5; case 0x90: case 0x91: case 0x92: case 0x93: case 0x94: case 0x95: case 0x96: case 0x97: case 0x98: case 0x99: case 0x9a: case 0x9b: case 0x9c: case 0x9d: case 0x9e: case 0x9f: - util::stream_format(stream, "bset (%s, a%d) %d", i8str(program_read_byte(pc+3)), 2+((opcode>>3)&1), opcode & 7); + util::stream_format(stream, "bset (%s, a%d) %d", i8str(opcodes.r8(pc+3)), 2+((opcode>>3)&1), opcode & 7); return 4; case 0xa0: case 0xa1: case 0xa2: case 0xa3: case 0xa4: case 0xa5: case 0xa6: case 0xa7: case 0xa8: case 0xa9: case 0xaa: case 0xab: case 0xac: case 0xad: case 0xae: case 0xaf: - util::stream_format(stream, "tbnz (%s, a%d) %d, $%x", i8str(program_read_byte(pc+3)), 2+((opcode>>3)&1), opcode & 7, - (pc+5+(int8_t)program_read_byte(pc+4)) & 0xffffff); + util::stream_format(stream, "tbnz (%s, a%d) %d, $%x", i8str(opcodes.r8(pc+3)), 2+((opcode>>3)&1), opcode & 7, + (pc+5+(s8)opcodes.r8(pc+4)) & 0xffffff); return 5; case 0xb0: case 0xb1: case 0xb2: case 0xb3: case 0xb4: case 0xb5: case 0xb6: case 0xb7: case 0xb8: case 0xb9: case 0xba: case 0xbb: case 0xbc: case 0xbd: case 0xbe: case 0xbf: - util::stream_format(stream, "bclr (%s, a%d) %d", i8str(program_read_byte(pc+3)), 2+((opcode>>3)&1), opcode & 7); + util::stream_format(stream, "bclr (%s, a%d) %d", i8str(opcodes.r8(pc+3)), 2+((opcode>>3)&1), opcode & 7); return 4; default: @@ -525,144 +496,144 @@ static int mn102_disassemble(std::ostream &stream, uint32_t pc, const uint8_t *o } case 0xf4: - opcode = program_read_byte(pc+1); + opcode = opcodes.r8(pc+1); switch(opcode) { case 0x00: case 0x01: case 0x02: case 0x03: case 0x04: case 0x05: case 0x06: case 0x07: case 0x08: case 0x09: case 0x0a: case 0x0b: case 0x0c: case 0x0d: case 0x0e: case 0x0f: - util::stream_format(stream, "mov d%d, (%s, a%d)", opcode & 3, i24str(r24s(pc+2)), (opcode>>2) & 3); + util::stream_format(stream, "mov d%d, (%s, a%d)", opcode & 3, i24str(r24(opcodes, pc+2)), (opcode>>2) & 3); return 5; case 0x10: case 0x11: case 0x12: case 0x13: case 0x14: case 0x15: case 0x16: case 0x17: case 0x18: case 0x19: case 0x1a: case 0x1b: case 0x1c: case 0x1d: case 0x1e: case 0x1f: - util::stream_format(stream, "mov a%d, (%s, a%d)", opcode & 3, i24str(r24s(pc+2)), (opcode>>2) & 3); + util::stream_format(stream, "mov a%d, (%s, a%d)", opcode & 3, i24str(r24(opcodes, pc+2)), (opcode>>2) & 3); return 5; case 0x20: case 0x21: case 0x22: case 0x23: case 0x24: case 0x25: case 0x26: case 0x27: case 0x28: case 0x29: case 0x2a: case 0x2b: case 0x2c: case 0x2d: case 0x2e: case 0x2f: - util::stream_format(stream, "movb d%d, (%s, a%d)", opcode & 3, i24str(r24s(pc+2)), (opcode>>2) & 3); + util::stream_format(stream, "movb d%d, (%s, a%d)", opcode & 3, i24str(r24(opcodes, pc+2)), (opcode>>2) & 3); return 5; case 0x30: case 0x31: case 0x32: case 0x33: case 0x34: case 0x35: case 0x36: case 0x37: case 0x38: case 0x39: case 0x3a: case 0x3b: case 0x3c: case 0x3d: case 0x3e: case 0x3f: - util::stream_format(stream, "movx d%d, (%s, a%d)", opcode & 3, i24str(r24s(pc+2)), (opcode>>2) & 3); + util::stream_format(stream, "movx d%d, (%s, a%d)", opcode & 3, i24str(r24(opcodes, pc+2)), (opcode>>2) & 3); return 5; case 0x40: case 0x41: case 0x42: case 0x43: - util::stream_format(stream, "mov d%d, ($%06x)", opcode & 3, r24u(pc+2)); + util::stream_format(stream, "mov d%d, ($%06x)", opcode & 3, r24(opcodes, pc+2)); return 5; case 0x44: case 0x45: case 0x46: case 0x47: - util::stream_format(stream, "movb d%d, ($%06x)", opcode & 3, r24u(pc+2)); + util::stream_format(stream, "movb d%d, ($%06x)", opcode & 3, r24(opcodes, pc+2)); return 5; case 0x4b: - util::stream_format(stream, "bset %02x, ($%06x)", program_read_byte(pc+5), r24u(pc+2)); + util::stream_format(stream, "bset %02x, ($%06x)", opcodes.r8(pc+5), r24(opcodes, pc+2)); return 6; case 0x4f: - util::stream_format(stream, "bclr %02x, ($%06x)", program_read_byte(pc+5), r24u(pc+2)); + util::stream_format(stream, "bclr %02x, ($%06x)", opcodes.r8(pc+5), r24(opcodes, pc+2)); return 6; case 0x50: case 0x51: case 0x52: case 0x53: - util::stream_format(stream, "mov a%d, ($%06x)", opcode & 3, r24u(pc+2)); + util::stream_format(stream, "mov a%d, ($%06x)", opcode & 3, r24(opcodes, pc+2)); return 5; case 0x60: case 0x61: case 0x62: case 0x63: - util::stream_format(stream, "add %s, d%d", i24str(r24s(pc+2)), opcode & 3); + util::stream_format(stream, "add %s, d%d", i24str(r24(opcodes, pc+2)), opcode & 3); return 5; case 0x64: case 0x65: case 0x66: case 0x67: - util::stream_format(stream, "add %s, a%d", i24str(r24s(pc+2)), opcode & 3); + util::stream_format(stream, "add %s, a%d", i24str(r24(opcodes, pc+2)), opcode & 3); return 5; case 0x68: case 0x69: case 0x6a: case 0x6b: - util::stream_format(stream, "sub %s, d%d", i24str(r24s(pc+2)), opcode & 3); + util::stream_format(stream, "sub %s, d%d", i24str(r24(opcodes, pc+2)), opcode & 3); return 5; case 0x6c: case 0x6d: case 0x6e: case 0x6f: - util::stream_format(stream, "sub %s, a%d", i24str(r24s(pc+2)), opcode & 3); + util::stream_format(stream, "sub %s, a%d", i24str(r24(opcodes, pc+2)), opcode & 3); return 5; case 0x70: case 0x71: case 0x72: case 0x73: - util::stream_format(stream, "mov %s, d%d", i24str(r24s(pc+2)), opcode & 3); + util::stream_format(stream, "mov %s, d%d", i24str(r24(opcodes, pc+2)), opcode & 3); return 5; case 0x74: case 0x75: case 0x76: case 0x77: - util::stream_format(stream, "mov $%06x, a%d", r24u(pc+2), opcode & 3); + util::stream_format(stream, "mov $%06x, a%d", r24(opcodes, pc+2), opcode & 3); return 5; case 0x78: case 0x79: case 0x7a: case 0x7b: - util::stream_format(stream, "cmp %s, d%d", i24str(r24s(pc+2)), opcode & 3); + util::stream_format(stream, "cmp %s, d%d", i24str(r24(opcodes, pc+2)), opcode & 3); return 5; case 0x7c: case 0x7d: case 0x7e: case 0x7f: - util::stream_format(stream, "cmp $%06x, a%d", r24u(pc+2), opcode & 3); + util::stream_format(stream, "cmp $%06x, a%d", r24(opcodes, pc+2), opcode & 3); return 5; case 0x80: case 0x81: case 0x82: case 0x83: case 0x84: case 0x85: case 0x86: case 0x87: case 0x88: case 0x89: case 0x8a: case 0x8b: case 0x8c: case 0x8d: case 0x8e: case 0x8f: - util::stream_format(stream, "mov (%s, a%d), d%d", i24str(r24s(pc+2)), (opcode>>2) & 3, opcode & 3); + util::stream_format(stream, "mov (%s, a%d), d%d", i24str(r24(opcodes, pc+2)), (opcode>>2) & 3, opcode & 3); return 5; case 0x90: case 0x91: case 0x92: case 0x93: case 0x94: case 0x95: case 0x96: case 0x97: case 0x98: case 0x99: case 0x9a: case 0x9b: case 0x9c: case 0x9d: case 0x9e: case 0x9f: - util::stream_format(stream, "movbu (%s, a%d), d%d", i24str(r24s(pc+2)), (opcode>>2) & 3, opcode & 3); + util::stream_format(stream, "movbu (%s, a%d), d%d", i24str(r24(opcodes, pc+2)), (opcode>>2) & 3, opcode & 3); return 5; case 0xa0: case 0xa1: case 0xa2: case 0xa3: case 0xa4: case 0xa5: case 0xa6: case 0xa7: case 0xa8: case 0xa9: case 0xaa: case 0xab: case 0xac: case 0xad: case 0xae: case 0xaf: - util::stream_format(stream, "movb (%s, a%d), d%d", i24str(r24s(pc+2)), (opcode>>2) & 3, opcode & 3); + util::stream_format(stream, "movb (%s, a%d), d%d", i24str(r24(opcodes, pc+2)), (opcode>>2) & 3, opcode & 3); return 5; case 0xb0: case 0xb1: case 0xb2: case 0xb3: case 0xb4: case 0xb5: case 0xb6: case 0xb7: case 0xb8: case 0xb9: case 0xba: case 0xbb: case 0xbc: case 0xbd: case 0xbe: case 0xbf: - util::stream_format(stream, "movx (%s, a%d), d%d", i24str(r24s(pc+2)), (opcode>>2) & 3, opcode & 3); + util::stream_format(stream, "movx (%s, a%d), d%d", i24str(r24(opcodes, pc+2)), (opcode>>2) & 3, opcode & 3); return 5; case 0xc0: case 0xc1: case 0xc2: case 0xc3: - util::stream_format(stream, "mov ($%06x), d%d", r24u(pc+2), opcode & 3); + util::stream_format(stream, "mov ($%06x), d%d", r24(opcodes, pc+2), opcode & 3); return 5; case 0xc4: case 0xc5: case 0xc6: case 0xc7: - util::stream_format(stream, "movb ($%06x), d%d", r24u(pc+2), opcode & 3); + util::stream_format(stream, "movb ($%06x), d%d", r24(opcodes, pc+2), opcode & 3); return 5; case 0xc8: case 0xc9: case 0xca: case 0xcb: - util::stream_format(stream, "movbu ($%06x), d%d", r24u(pc+2), opcode & 3); + util::stream_format(stream, "movbu ($%06x), d%d", r24(opcodes, pc+2), opcode & 3); return 5; case 0xd0: case 0xd1: case 0xd2: case 0xd3: - util::stream_format(stream, "mov ($%06x), a%d", r24u(pc+2), opcode & 3); + util::stream_format(stream, "mov ($%06x), a%d", r24(opcodes, pc+2), opcode & 3); return 5; case 0xe0: - util::stream_format(stream, "jmp $%x", (pc+5+r24s(pc+2)) & 0xffffff); + util::stream_format(stream, "jmp $%x", (pc+5+r24(opcodes, pc+2)) & 0xffffff); return 5; case 0xe1: - util::stream_format(stream, "jsr $%x", (pc+5+r24s(pc+2)) & 0xffffff); + util::stream_format(stream, "jsr $%x", (pc+5+r24(opcodes, pc+2)) & 0xffffff); return 5; case 0xe3: - util::stream_format(stream, "bset $%02x, ($%x)", program_read_byte(pc+4), r16u(pc+2)); + util::stream_format(stream, "bset $%02x, ($%x)", opcodes.r8(pc+4), opcodes.r16(pc+2)); return 6; case 0xe7: - util::stream_format(stream, "bclr $%02x, ($%x)", program_read_byte(pc+4), r16u(pc+2)); + util::stream_format(stream, "bclr $%02x, ($%x)", opcodes.r8(pc+4), opcodes.r16(pc+2)); return 6; case 0xe8: case 0xe9: case 0xea: case 0xeb: - util::stream_format(stream, "bset $%02x, (%s, a%d)", program_read_byte(pc+3), i8str(program_read_byte(pc+2)), opcode & 3); + util::stream_format(stream, "bset $%02x, (%s, a%d)", opcodes.r8(pc+3), i8str(opcodes.r8(pc+2)), opcode & 3); return 4; case 0xec: case 0xed: case 0xee: case 0xef: - util::stream_format(stream, "bclr $%02x, (%s, a%d)", program_read_byte(pc+3), i8str(program_read_byte(pc+2)), opcode & 3); + util::stream_format(stream, "bclr $%02x, (%s, a%d)", opcodes.r8(pc+3), i8str(opcodes.r8(pc+2)), opcode & 3); return 4; case 0xf0: case 0xf1: case 0xf2: case 0xf3: case 0xf4: case 0xf5: case 0xf6: case 0xf7: case 0xf8: case 0xf9: case 0xfa: case 0xfb: case 0xfc: case 0xfd: case 0xfe: case 0xff: - util::stream_format(stream, "mov (%s, a%d), a%d", i24str(r24s(pc+2)), (opcode>>2) & 3, opcode & 3); + util::stream_format(stream, "mov (%s, a%d), a%d", i24str(r24(opcodes, pc+2)), (opcode>>2) & 3, opcode & 3); return 5; default: @@ -670,44 +641,44 @@ static int mn102_disassemble(std::ostream &stream, uint32_t pc, const uint8_t *o } case 0xf5: - opcode = program_read_byte(pc+1); + opcode = opcodes.r8(pc+1); switch(opcode) { case 0x00: case 0x01: case 0x02: case 0x03: - util::stream_format(stream, "and $%02x, d%d", program_read_byte(pc+2), opcode & 3); + util::stream_format(stream, "and $%02x, d%d", opcodes.r8(pc+2), opcode & 3); return 3; case 0x04: case 0x05: case 0x06: case 0x07: - util::stream_format(stream, "btst $%02x, d%d", program_read_byte(pc+2), opcode & 3); + util::stream_format(stream, "btst $%02x, d%d", opcodes.r8(pc+2), opcode & 3); return 3; case 0x08: case 0x09: case 0x0a: case 0x0b: - util::stream_format(stream, "or $%02x, d%d", program_read_byte(pc+2), opcode & 3); + util::stream_format(stream, "or $%02x, d%d", opcodes.r8(pc+2), opcode & 3); return 3; case 0x0c: case 0x0d: case 0x0e: case 0x0f: - util::stream_format(stream, "addnf %s, a%d", i8str(program_read_byte(pc+2)), opcode & 3); + util::stream_format(stream, "addnf %s, a%d", i8str(opcodes.r8(pc+2)), opcode & 3); return 3; case 0x10: case 0x11: case 0x12: case 0x13: case 0x14: case 0x15: case 0x16: case 0x17: case 0x18: case 0x19: case 0x1a: case 0x1b: case 0x1c: case 0x1d: case 0x1e: case 0x1f: - util::stream_format(stream, "movb d%d, (%s, a%d)", opcode & 3, i8str(program_read_byte(pc+2)), (opcode>>2) & 3); + util::stream_format(stream, "movb d%d, (%s, a%d)", opcode & 3, i8str(opcodes.r8(pc+2)), (opcode>>2) & 3); return 3; case 0x20: case 0x21: case 0x22: case 0x23: case 0x24: case 0x25: case 0x26: case 0x27: case 0x28: case 0x29: case 0x2a: case 0x2b: case 0x2c: case 0x2d: case 0x2e: case 0x2f: - util::stream_format(stream, "movb (%s, a%d), d%d", i8str(program_read_byte(pc+2)), (opcode>>2) & 3, opcode & 3); + util::stream_format(stream, "movb (%s, a%d), d%d", i8str(opcodes.r8(pc+2)), (opcode>>2) & 3, opcode & 3); return 3; case 0x30: case 0x31: case 0x32: case 0x33: case 0x34: case 0x35: case 0x36: case 0x37: case 0x38: case 0x39: case 0x3a: case 0x3b: case 0x3c: case 0x3d: case 0x3e: case 0x3f: - util::stream_format(stream, "movbu (%s, a%d), d%d", i8str(program_read_byte(pc+2)), (opcode>>2) & 3, opcode & 3); + util::stream_format(stream, "movbu (%s, a%d), d%d", i8str(opcodes.r8(pc+2)), (opcode>>2) & 3, opcode & 3); return 3; case 0x40: case 0x41: case 0x42: case 0x43: case 0x44: case 0x45: case 0x46: case 0x47: case 0x48: case 0x49: case 0x4a: case 0x4b: case 0x4c: case 0x4d: case 0x4e: case 0x4f: { - uint8_t opcode2 = program_read_byte(pc+2); + u8 opcode2 = opcodes.r8(pc+2); switch(opcode2) { case 0x00: @@ -725,13 +696,13 @@ static int mn102_disassemble(std::ostream &stream, uint32_t pc, const uint8_t *o case 0x50: case 0x51: case 0x52: case 0x53: case 0x54: case 0x55: case 0x56: case 0x57: case 0x58: case 0x59: case 0x5a: case 0x5b: case 0x5c: case 0x5d: case 0x5e: case 0x5f: - util::stream_format(stream, "movx d%d, (%s, a%d)", opcode & 3, i8str(program_read_byte(pc+2)), (opcode>>2) & 3); + util::stream_format(stream, "movx d%d, (%s, a%d)", opcode & 3, i8str(opcodes.r8(pc+2)), (opcode>>2) & 3); return 3; case 0x60: case 0x61: case 0x62: case 0x63: case 0x64: case 0x65: case 0x66: case 0x67: case 0x68: case 0x69: case 0x6a: case 0x6b: case 0x6c: case 0x6d: case 0x6e: case 0x6f: { - uint8_t opcode2 = program_read_byte(pc+2); + u8 opcode2 = opcodes.r8(pc+2); switch(opcode2) { case 0x10: @@ -745,124 +716,124 @@ static int mn102_disassemble(std::ostream &stream, uint32_t pc, const uint8_t *o case 0x70: case 0x71: case 0x72: case 0x73: case 0x74: case 0x75: case 0x76: case 0x77: case 0x78: case 0x79: case 0x7a: case 0x7b: case 0x7c: case 0x7d: case 0x7e: case 0x7f: - util::stream_format(stream, "movx (%s, a%d), d%d", i8str(program_read_byte(pc+2)), (opcode>>2) & 3, opcode & 3); + util::stream_format(stream, "movx (%s, a%d), d%d", i8str(opcodes.r8(pc+2)), (opcode>>2) & 3, opcode & 3); return 3; case 0x80: case 0x81: case 0x82: case 0x83: case 0x84: case 0x85: case 0x86: case 0x87: case 0x88: case 0x89: case 0x8a: case 0x8b: case 0x8c: case 0x8d: case 0x8e: case 0x8f: - util::stream_format(stream, "tbz (%s, a%d) %d, $%x", i8str(program_read_byte(pc+2)), (opcode>>3)&1, opcode & 7, - (pc+4+(int8_t)program_read_byte(pc+3)) & 0xffffff); + util::stream_format(stream, "tbz (%s, a%d) %d, $%x", i8str(opcodes.r8(pc+2)), (opcode>>3)&1, opcode & 7, + (pc+4+(s8)opcodes.r8(pc+3)) & 0xffffff); return 4; case 0x90: case 0x91: case 0x92: case 0x93: case 0x94: case 0x95: case 0x96: case 0x97: case 0x98: case 0x99: case 0x9a: case 0x9b: case 0x9c: case 0x9d: case 0x9e: case 0x9f: - util::stream_format(stream, "bset (%s, a%d) %d", i8str(program_read_byte(pc+2)), (opcode>>3)&1, opcode & 7); + util::stream_format(stream, "bset (%s, a%d) %d", i8str(opcodes.r8(pc+2)), (opcode>>3)&1, opcode & 7); return 3; case 0xa0: case 0xa1: case 0xa2: case 0xa3: case 0xa4: case 0xa5: case 0xa6: case 0xa7: case 0xa8: case 0xa9: case 0xaa: case 0xab: case 0xac: case 0xad: case 0xae: case 0xaf: - util::stream_format(stream, "tbnz (%s, a%d) %d, $%x", i8str(program_read_byte(pc+2)), (opcode>>3)&1, opcode & 7, - (pc+4+(int8_t)program_read_byte(pc+3)) & 0xffffff); + util::stream_format(stream, "tbnz (%s, a%d) %d, $%x", i8str(opcodes.r8(pc+2)), (opcode>>3)&1, opcode & 7, + (pc+4+(s8)opcodes.r8(pc+3)) & 0xffffff); return 4; case 0xb0: case 0xb1: case 0xb2: case 0xb3: case 0xb4: case 0xb5: case 0xb6: case 0xb7: case 0xb8: case 0xb9: case 0xba: case 0xbb: case 0xbc: case 0xbd: case 0xbe: case 0xbf: - util::stream_format(stream, "bclr (%s, a%d) %d", i8str(program_read_byte(pc+2)), (opcode>>3)&1, opcode & 7); + util::stream_format(stream, "bclr (%s, a%d) %d", i8str(opcodes.r8(pc+2)), (opcode>>3)&1, opcode & 7); return 3; case 0xc0: case 0xc1: case 0xc2: case 0xc3: case 0xc4: case 0xc5: case 0xc6: case 0xc7: - util::stream_format(stream, "tbz ($%x) %d, $%x", r16u(pc+2), opcode & 7, - (pc+5+(int8_t)program_read_byte(pc+4)) & 0xffffff); + util::stream_format(stream, "tbz ($%x) %d, $%x", opcodes.r16(pc+2), opcode & 7, + (pc+5+(s8)opcodes.r8(pc+4)) & 0xffffff); return 5; case 0xc8: case 0xc9: case 0xca: case 0xcb: case 0xcc: case 0xcd: case 0xce: case 0xcf: - util::stream_format(stream, "tbnz ($%x) %d, $%x", r16u(pc+2), opcode & 7, - (pc+5+(int8_t)program_read_byte(pc+4)) & 0xffffff); + util::stream_format(stream, "tbnz ($%x) %d, $%x", opcodes.r16(pc+2), opcode & 7, + (pc+5+(s8)opcodes.r8(pc+4)) & 0xffffff); return 5; case 0xd0: case 0xd1: case 0xd2: case 0xd3: case 0xd4: case 0xd5: case 0xd6: case 0xd7: - util::stream_format(stream, "bset ($%x) %d", r16u(pc+2), opcode & 7); + util::stream_format(stream, "bset ($%x) %d", opcodes.r16(pc+2), opcode & 7); return 4; case 0xd8: case 0xd9: case 0xda: case 0xdb: case 0xdc: case 0xdd: case 0xde: case 0xdf: - util::stream_format(stream, "bclr ($%x) %d", r16u(pc+2), opcode & 7); + util::stream_format(stream, "bclr ($%x) %d", opcodes.r16(pc+2), opcode & 7); return 4; case 0xe0: - util::stream_format(stream, "bltx $%x", (pc+3+(int8_t)program_read_byte(pc+2)) & 0xffffff); + util::stream_format(stream, "bltx $%x", (pc+3+s8(opcodes.r8(pc+2))) & 0xffffff); return 3; case 0xe1: - util::stream_format(stream, "bgtx $%x", (pc+3+(int8_t)program_read_byte(pc+2)) & 0xffffff); + util::stream_format(stream, "bgtx $%x", (pc+3+s8(opcodes.r8(pc+2))) & 0xffffff); return 3; case 0xe2: - util::stream_format(stream, "bgex $%x", (pc+3+(int8_t)program_read_byte(pc+2)) & 0xffffff); + util::stream_format(stream, "bgex $%x", (pc+3+s8(opcodes.r8(pc+2))) & 0xffffff); return 3; case 0xe3: - util::stream_format(stream, "blex $%x", (pc+3+(int8_t)program_read_byte(pc+2)) & 0xffffff); + util::stream_format(stream, "blex $%x", (pc+3+s8(opcodes.r8(pc+2))) & 0xffffff); return 3; case 0xe4: - util::stream_format(stream, "bcsx $%x", (pc+3+(int8_t)program_read_byte(pc+2)) & 0xffffff); + util::stream_format(stream, "bcsx $%x", (pc+3+s8(opcodes.r8(pc+2))) & 0xffffff); return 3; case 0xe5: - util::stream_format(stream, "bhix $%x", (pc+3+(int8_t)program_read_byte(pc+2)) & 0xffffff); + util::stream_format(stream, "bhix $%x", (pc+3+s8(opcodes.r8(pc+2))) & 0xffffff); return 3; case 0xe6: - util::stream_format(stream, "bccx $%x", (pc+3+(int8_t)program_read_byte(pc+2)) & 0xffffff); + util::stream_format(stream, "bccx $%x", (pc+3+s8(opcodes.r8(pc+2))) & 0xffffff); return 3; case 0xe7: - util::stream_format(stream, "blsx $%x", (pc+3+(int8_t)program_read_byte(pc+2)) & 0xffffff); + util::stream_format(stream, "blsx $%x", (pc+3+s8(opcodes.r8(pc+2))) & 0xffffff); return 3; case 0xe8: - util::stream_format(stream, "beqx $%x", (pc+3+(int8_t)program_read_byte(pc+2)) & 0xffffff); + util::stream_format(stream, "beqx $%x", (pc+3+s8(opcodes.r8(pc+2))) & 0xffffff); return 3; case 0xe9: - util::stream_format(stream, "bnex $%x", (pc+3+(int8_t)program_read_byte(pc+2)) & 0xffffff); + util::stream_format(stream, "bnex $%x", (pc+3+s8(opcodes.r8(pc+2))) & 0xffffff); return 3; case 0xec: - util::stream_format(stream, "bvcx $%x", (pc+3+(int8_t)program_read_byte(pc+2)) & 0xffffff); + util::stream_format(stream, "bvcx $%x", (pc+3+s8(opcodes.r8(pc+2))) & 0xffffff); return 3; case 0xed: - util::stream_format(stream, "bvsx $%x", (pc+3+(int8_t)program_read_byte(pc+2)) & 0xffffff); + util::stream_format(stream, "bvsx $%x", (pc+3+s8(opcodes.r8(pc+2))) & 0xffffff); return 3; case 0xee: - util::stream_format(stream, "bncx $%x", (pc+3+(int8_t)program_read_byte(pc+2)) & 0xffffff); + util::stream_format(stream, "bncx $%x", (pc+3+s8(opcodes.r8(pc+2))) & 0xffffff); return 3; case 0xef: - util::stream_format(stream, "bnsx $%x", (pc+3+(int8_t)program_read_byte(pc+2)) & 0xffffff); + util::stream_format(stream, "bnsx $%x", (pc+3+s8(opcodes.r8(pc+2))) & 0xffffff); return 3; case 0xf0: case 0xf1: case 0xf2: case 0xf3: case 0xf4: case 0xf5: case 0xf6: case 0xf7: { - uint8_t opcode2 = program_read_byte(pc+2); + u8 opcode2 = opcodes.r8(pc+2); switch(opcode2) { case 0x04: - util::stream_format(stream, "mulql %s, d%d", i8str(program_read_byte(pc+3)), opcode & 3); + util::stream_format(stream, "mulql %s, d%d", i8str(opcodes.r8(pc+3)), opcode & 3); return 4; case 0x05: - util::stream_format(stream, "mulqh %s, d%d", i8str(program_read_byte(pc+3)), opcode & 3); + util::stream_format(stream, "mulqh %s, d%d", i8str(opcodes.r8(pc+3)), opcode & 3); return 4; case 0x08: - util::stream_format(stream, "mulql %s, d%d", i16str(r16s(pc+3)), opcode & 3); + util::stream_format(stream, "mulql %s, d%d", i16str(opcodes.r16(pc+3)), opcode & 3); return 5; case 0x09: - util::stream_format(stream, "mulqh %s, d%d", i16str(r16s(pc+3)), opcode & 3); + util::stream_format(stream, "mulqh %s, d%d", i16str(opcodes.r16(pc+3)), opcode & 3); return 5; default: @@ -871,19 +842,19 @@ static int mn102_disassemble(std::ostream &stream, uint32_t pc, const uint8_t *o } case 0xfc: - util::stream_format(stream, "bvc $%x", (pc+3+(int8_t)program_read_byte(pc+2)) & 0xffffff); + util::stream_format(stream, "bvc $%x", (pc+3+s8(opcodes.r8(pc+2))) & 0xffffff); return 3; case 0xfd: - util::stream_format(stream, "bvs $%x", (pc+3+(int8_t)program_read_byte(pc+2)) & 0xffffff); + util::stream_format(stream, "bvs $%x", (pc+3+s8(opcodes.r8(pc+2))) & 0xffffff); return 3; case 0xfe: - util::stream_format(stream, "bnc $%x", (pc+3+(int8_t)program_read_byte(pc+2)) & 0xffffff); + util::stream_format(stream, "bnc $%x", (pc+3+s8(opcodes.r8(pc+2))) & 0xffffff); return 3; case 0xff: - util::stream_format(stream, "bns $%x", (pc+3+(int8_t)program_read_byte(pc+2)) & 0xffffff); + util::stream_format(stream, "bns $%x", (pc+3+s8(opcodes.r8(pc+2))) & 0xffffff); return 3; default: @@ -895,104 +866,104 @@ static int mn102_disassemble(std::ostream &stream, uint32_t pc, const uint8_t *o return 1; case 0xf7: - opcode = program_read_byte(pc+1); + opcode = opcodes.r8(pc+1); switch(opcode) { case 0x00: case 0x01: case 0x02: case 0x03: - util::stream_format(stream, "and $%04x, d%d", r16u(pc+2), opcode & 3); + util::stream_format(stream, "and $%04x, d%d", opcodes.r16(pc+2), opcode & 3); return 4; case 0x04: case 0x05: case 0x06: case 0x07: - util::stream_format(stream, "btst $%04x, d%d", r16u(pc+2), opcode & 3); + util::stream_format(stream, "btst $%04x, d%d", opcodes.r16(pc+2), opcode & 3); return 4; case 0x08: case 0x09: case 0x0a: case 0x0b: - util::stream_format(stream, "add %s, a%d", i16str(r16s(pc+2)), opcode & 3); + util::stream_format(stream, "add %s, a%d", i16str(opcodes.r16(pc+2)), opcode & 3); return 4; case 0x0c: case 0x0d: case 0x0e: case 0x0f: - util::stream_format(stream, "sub %s, a%d", i16str(r16s(pc+2)), opcode & 3); + util::stream_format(stream, "sub %s, a%d", i16str(opcodes.r16(pc+2)), opcode & 3); return 4; case 0x10: - util::stream_format(stream, "and $%04x, psw", r16u(pc+2)); + util::stream_format(stream, "and $%04x, psw", opcodes.r16(pc+2)); return 4; case 0x14: - util::stream_format(stream, "or $%04x, psw", r16u(pc+2)); + util::stream_format(stream, "or $%04x, psw", opcodes.r16(pc+2)); return 4; case 0x18: case 0x19: case 0x1a: case 0x1b: - util::stream_format(stream, "add %s, d%d", i16str(r16u(pc+2)), opcode & 3); + util::stream_format(stream, "add %s, d%d", i16str(opcodes.r16(pc+2)), opcode & 3); return 4; case 0x1c: case 0x1d: case 0x1e: case 0x1f: - util::stream_format(stream, "sub %s, d%d", i16str(r16s(pc+2)), opcode & 3); + util::stream_format(stream, "sub %s, d%d", i16str(opcodes.r16(pc+2)), opcode & 3); return 4; case 0x20: case 0x21: case 0x22: case 0x23: - util::stream_format(stream, "mov a%d, ($%04x)", opcode & 3, r16u(pc+2)); + util::stream_format(stream, "mov a%d, ($%04x)", opcode & 3, opcodes.r16(pc+2)); return 4; case 0x30: case 0x31: case 0x32: case 0x33: - util::stream_format(stream, "mov ($%04x), a%d", r16u(pc+2), opcode & 3); + util::stream_format(stream, "mov ($%04x), a%d", opcodes.r16(pc+2), opcode & 3); return 4; case 0x40: case 0x41: case 0x42: case 0x43: - util::stream_format(stream, "or $%04x, d%d", r16u(pc+2), opcode & 3); + util::stream_format(stream, "or $%04x, d%d", opcodes.r16(pc+2), opcode & 3); return 4; case 0x48: case 0x49: case 0x4a: case 0x4b: - util::stream_format(stream, "cmp %s, d%d", i16str(r16u(pc+2)), opcode & 3); + util::stream_format(stream, "cmp %s, d%d", i16str(opcodes.r16(pc+2)), opcode & 3); return 4; case 0x4c: case 0x4d: case 0x4e: case 0x4f: - util::stream_format(stream, "xor $%04x, d%d", r16u(pc+2), opcode & 3); + util::stream_format(stream, "xor $%04x, d%d", opcodes.r16(pc+2), opcode & 3); return 4; case 0x50: case 0x51: case 0x52: case 0x53: case 0x54: case 0x55: case 0x56: case 0x57: case 0x58: case 0x59: case 0x5a: case 0x5b: case 0x5c: case 0x5d: case 0x5e: case 0x5f: - util::stream_format(stream, "movbu (%s, a%d), d%d", i16str(r16s(pc+2)), (opcode>>2) & 3, opcode & 3); + util::stream_format(stream, "movbu (%s, a%d), d%d", i16str(opcodes.r16(pc+2)), (opcode>>2) & 3, opcode & 3); return 4; case 0x60: case 0x61: case 0x62: case 0x63: case 0x64: case 0x65: case 0x66: case 0x67: case 0x68: case 0x69: case 0x6a: case 0x6b: case 0x6c: case 0x6d: case 0x6e: case 0x6f: - util::stream_format(stream, "movx d%d, (%s, a%d)", opcode & 3, i16str(r16s(pc+2)), (opcode>>2) & 3); + util::stream_format(stream, "movx d%d, (%s, a%d)", opcode & 3, i16str(opcodes.r16(pc+2)), (opcode>>2) & 3); return 4; case 0x70: case 0x71: case 0x72: case 0x73: case 0x74: case 0x75: case 0x76: case 0x77: case 0x78: case 0x79: case 0x7a: case 0x7b: case 0x7c: case 0x7d: case 0x7e: case 0x7f: - util::stream_format(stream, "movx (%s, a%d), d%d", i16str(r16s(pc+2)), (opcode>>2) & 3, opcode & 3); + util::stream_format(stream, "movx (%s, a%d), d%d", i16str(opcodes.r16(pc+2)), (opcode>>2) & 3, opcode & 3); return 4; case 0x80: case 0x81: case 0x82: case 0x83: case 0x84: case 0x85: case 0x86: case 0x87: case 0x88: case 0x89: case 0x8a: case 0x8b: case 0x8c: case 0x8d: case 0x8e: case 0x8f: - util::stream_format(stream, "mov d%d, (%s, a%d)", opcode & 3, i16str(r16s(pc+2)), (opcode>>2) & 3); + util::stream_format(stream, "mov d%d, (%s, a%d)", opcode & 3, i16str(opcodes.r16(pc+2)), (opcode>>2) & 3); return 4; case 0x90: case 0x91: case 0x92: case 0x93: case 0x94: case 0x95: case 0x96: case 0x97: case 0x98: case 0x99: case 0x9a: case 0x9b: case 0x9c: case 0x9d: case 0x9e: case 0x9f: - util::stream_format(stream, "movb d%d, (%s, a%d)", opcode & 3, i16str(r16s(pc+2)), (opcode>>2) & 3); + util::stream_format(stream, "movb d%d, (%s, a%d)", opcode & 3, i16str(opcodes.r16(pc+2)), (opcode>>2) & 3); return 4; case 0xa0: case 0xa1: case 0xa2: case 0xa3: case 0xa4: case 0xa5: case 0xa6: case 0xa7: case 0xa8: case 0xa9: case 0xaa: case 0xab: case 0xac: case 0xad: case 0xae: case 0xaf: - util::stream_format(stream, "mov a%d, (%s, a%d)", opcode & 3, i16str(r16s(pc+2)), (opcode>>2) & 3); + util::stream_format(stream, "mov a%d, (%s, a%d)", opcode & 3, i16str(opcodes.r16(pc+2)), (opcode>>2) & 3); return 4; case 0xb0: case 0xb1: case 0xb2: case 0xb3: case 0xb4: case 0xb5: case 0xb6: case 0xb7: case 0xb8: case 0xb9: case 0xba: case 0xbb: case 0xbc: case 0xbd: case 0xbe: case 0xbf: - util::stream_format(stream, "mov (%s, a%d), a%d", i16str(r16s(pc+2)), (opcode>>2) & 3, opcode & 3); + util::stream_format(stream, "mov (%s, a%d), a%d", i16str(opcodes.r16(pc+2)), (opcode>>2) & 3, opcode & 3); return 4; case 0xc0: case 0xc1: case 0xc2: case 0xc3: case 0xc4: case 0xc5: case 0xc6: case 0xc7: case 0xc8: case 0xc9: case 0xca: case 0xcb: case 0xcc: case 0xcd: case 0xce: case 0xcf: - util::stream_format(stream, "mov (%s, a%d), d%d", i16str(r16s(pc+2)), (opcode>>2) & 3, opcode & 3); + util::stream_format(stream, "mov (%s, a%d), d%d", i16str(opcodes.r16(pc+2)), (opcode>>2) & 3, opcode & 3); return 4; case 0xd0: case 0xd1: case 0xd2: case 0xd3: case 0xd4: case 0xd5: case 0xd6: case 0xd7: case 0xd8: case 0xd9: case 0xda: case 0xdb: case 0xdc: case 0xdd: case 0xde: case 0xdf: - util::stream_format(stream, "movb (%s, a%d), d%d", i16str(r16s(pc+2)), (opcode>>2) & 3, opcode & 3); + util::stream_format(stream, "movb (%s, a%d), d%d", i16str(opcodes.r16(pc+2)), (opcode>>2) & 3, opcode & 3); return 4; default: @@ -1000,15 +971,15 @@ static int mn102_disassemble(std::ostream &stream, uint32_t pc, const uint8_t *o } case 0xf8: case 0xf9: case 0xfa: case 0xfb: - util::stream_format(stream, "mov %s, d%d", i16str(r16s(pc+1)), opcode & 3); + util::stream_format(stream, "mov %s, d%d", i16str(opcodes.r16(pc+1)), opcode & 3); return 3; case 0xfc: - util::stream_format(stream, "jmp $%x", (pc+3+r16s(pc+1)) & 0xffffff); + util::stream_format(stream, "jmp $%x", (pc+3+s16(opcodes.r16(pc+1))) & 0xffffff); return 3; case 0xfd: - util::stream_format(stream, "jsr $%x", (pc+3+r16s(pc+1)) & 0xffffff); + util::stream_format(stream, "jsr $%x", (pc+3+s16(opcodes.r16(pc+1))) & 0xffffff); return 3; case 0xfe: @@ -1020,19 +991,14 @@ static int mn102_disassemble(std::ostream &stream, uint32_t pc, const uint8_t *o }; illegal1: - util::stream_format(stream, "dc.b $%02x", program_read_byte(pc)); + util::stream_format(stream, "dc.b $%02x", opcodes.r8(pc)); return 1; illegal2: - util::stream_format(stream, "dc.b $%02x $%02x", program_read_byte(pc), program_read_byte(pc+1)); + util::stream_format(stream, "dc.b $%02x $%02x", opcodes.r8(pc), opcodes.r8(pc+1)); return 2; illegal3: - util::stream_format(stream, "dc.b $%02x $%02x $%02x", program_read_byte(pc), program_read_byte(pc+1), program_read_byte(pc+2)); + util::stream_format(stream, "dc.b $%02x $%02x $%02x", opcodes.r8(pc), opcodes.r8(pc+1), opcodes.r8(pc+2)); return 3; } - -CPU_DISASSEMBLE( mn10200 ) -{ - return mn102_disassemble(stream, pc, oprom); -} diff --git a/src/devices/cpu/mn10200/mn102dis.h b/src/devices/cpu/mn10200/mn102dis.h new file mode 100644 index 00000000000..4fa8e932812 --- /dev/null +++ b/src/devices/cpu/mn10200/mn102dis.h @@ -0,0 +1,28 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert, R. Belmont, hap +/* + Panasonic MN10200 disassembler +*/ + +#ifndef MAME_CPU_MN10200_MN102DIS_H +#define MAME_CPU_MN10200_MN102DIS_H + +#pragma once + +class mn10200_disassembler : public util::disasm_interface +{ +public: + mn10200_disassembler() = default; + virtual ~mn10200_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + u32 r24(const data_buffer &opcodes, offs_t pc); + std::string i8str(s8 v); + std::string i16str(int16_t v); + std::string i24str(u32 v); +}; + +#endif diff --git a/src/devices/cpu/nanoprocessor/nanoprocessor.cpp b/src/devices/cpu/nanoprocessor/nanoprocessor.cpp index 655dfdb6af2..37966d77168 100644 --- a/src/devices/cpu/nanoprocessor/nanoprocessor.cpp +++ b/src/devices/cpu/nanoprocessor/nanoprocessor.cpp @@ -3,6 +3,7 @@ #include "emu.h" #include "nanoprocessor.h" +#include "nanoprocessor_dasm.h" #include "debugger.h" // Index of state variables @@ -33,8 +34,8 @@ enum { #define BIT_MASK(n) (1U << (n)) // Macros to clear/set single bits -#define BIT_CLR(w , n) ((w) &= ~BIT_MASK(n)) -#define BIT_SET(w , n) ((w) |= BIT_MASK(n)) +#define BIT_CLR(w, n) ((w) &= ~BIT_MASK(n)) +#define BIT_SET(w, n) ((w) |= BIT_MASK(n)) // Bits in m_flags #define NANO_DC0_BIT 0 // DC0 @@ -44,39 +45,39 @@ enum { DEFINE_DEVICE_TYPE(HP_NANOPROCESSOR, hp_nanoprocessor_device, "nanoprocessor", "HP-Nanoprocessor") hp_nanoprocessor_device::hp_nanoprocessor_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) : - cpu_device(mconfig , HP_NANOPROCESSOR , tag , owner , clock), + cpu_device(mconfig, HP_NANOPROCESSOR, tag, owner, clock), m_dc_changed_func(*this), m_read_dc_func(*this), - m_program_config("program" , ENDIANNESS_BIG , 8 , 11), - m_io_config("io" , ENDIANNESS_BIG , 8 , 4) + m_program_config("program", ENDIANNESS_BIG, 8, 11), + m_io_config("io", ENDIANNESS_BIG, 8, 4) { } void hp_nanoprocessor_device::device_start() { - state_add(NANO_REG_A , "A" , m_reg_A); - state_add(NANO_REG_R0 , "R0" , m_reg_R[ 0 ]); - state_add(NANO_REG_R1 , "R1" , m_reg_R[ 1 ]); - state_add(NANO_REG_R2 , "R2" , m_reg_R[ 2 ]); - state_add(NANO_REG_R3 , "R3" , m_reg_R[ 3 ]); - state_add(NANO_REG_R4 , "R4" , m_reg_R[ 4 ]); - state_add(NANO_REG_R5 , "R5" , m_reg_R[ 5 ]); - state_add(NANO_REG_R6 , "R6" , m_reg_R[ 6 ]); - state_add(NANO_REG_R7 , "R7" , m_reg_R[ 7 ]); - state_add(NANO_REG_R8 , "R8" , m_reg_R[ 8 ]); - state_add(NANO_REG_R9 , "R9" , m_reg_R[ 9 ]); - state_add(NANO_REG_R10 , "R10" , m_reg_R[ 10 ]); - state_add(NANO_REG_R11 , "R11" , m_reg_R[ 11 ]); - state_add(NANO_REG_R12 , "R12" , m_reg_R[ 12 ]); - state_add(NANO_REG_R13 , "R13" , m_reg_R[ 13 ]); - state_add(NANO_REG_R14 , "R14" , m_reg_R[ 14 ]); - state_add(NANO_REG_R15 , "R15" , m_reg_R[ 15 ]); - state_add(NANO_REG_PA , "PA" , m_reg_PA).formatstr("%03X"); - state_add(STATE_GENPC , "GENPC" , m_reg_PA).noshow(); - state_add(STATE_GENPCBASE , "GENPCBASE" , m_reg_PA).noshow(); - state_add(NANO_REG_SSR , "SSR" , m_reg_SSR).formatstr("%03X"); - state_add(NANO_REG_ISR , "ISR" , m_reg_ISR).formatstr("%03X"); - state_add(STATE_GENFLAGS , "GENFLAGS" , m_flags).noshow().formatstr("%10s"); + state_add(NANO_REG_A, "A", m_reg_A); + state_add(NANO_REG_R0, "R0", m_reg_R[ 0 ]); + state_add(NANO_REG_R1, "R1", m_reg_R[ 1 ]); + state_add(NANO_REG_R2, "R2", m_reg_R[ 2 ]); + state_add(NANO_REG_R3, "R3", m_reg_R[ 3 ]); + state_add(NANO_REG_R4, "R4", m_reg_R[ 4 ]); + state_add(NANO_REG_R5, "R5", m_reg_R[ 5 ]); + state_add(NANO_REG_R6, "R6", m_reg_R[ 6 ]); + state_add(NANO_REG_R7, "R7", m_reg_R[ 7 ]); + state_add(NANO_REG_R8, "R8", m_reg_R[ 8 ]); + state_add(NANO_REG_R9, "R9", m_reg_R[ 9 ]); + state_add(NANO_REG_R10, "R10", m_reg_R[ 10 ]); + state_add(NANO_REG_R11, "R11", m_reg_R[ 11 ]); + state_add(NANO_REG_R12, "R12", m_reg_R[ 12 ]); + state_add(NANO_REG_R13, "R13", m_reg_R[ 13 ]); + state_add(NANO_REG_R14, "R14", m_reg_R[ 14 ]); + state_add(NANO_REG_R15, "R15", m_reg_R[ 15 ]); + state_add(NANO_REG_PA, "PA", m_reg_PA).formatstr("%03X"); + state_add(STATE_GENPC, "GENPC", m_reg_PA).noshow(); + state_add(STATE_GENPCBASE, "GENPCBASE", m_reg_PA).noshow(); + state_add(NANO_REG_SSR, "SSR", m_reg_SSR).formatstr("%03X"); + state_add(NANO_REG_ISR, "ISR", m_reg_ISR).formatstr("%03X"); + state_add(STATE_GENFLAGS, "GENFLAGS", m_flags).noshow().formatstr("%10s"); m_program = &space(AS_PROGRAM); m_direct = &m_program->direct(); @@ -122,7 +123,7 @@ void hp_nanoprocessor_device::execute_run() // Check for interrupts (interrupt line is always enabled. Masking is done // outside of the NP, usually by ANDing the DC7 line with the interrupt // request signal) - if (BIT(m_flags , NANO_I_BIT)) { + if (BIT(m_flags, NANO_I_BIT)) { m_reg_ISR = m_reg_PA; m_reg_PA = (uint16_t)(standard_irq_callback(0) & 0xff); // Vector fetching takes 1 cycle @@ -131,7 +132,7 @@ void hp_nanoprocessor_device::execute_run() // Need this to propagate the clearing of DC7 to the clearing of int. line yield(); } else { - debugger_instruction_hook(this , m_reg_PA); + debugger_instruction_hook(this, m_reg_PA); uint8_t opcode = fetch(); execute_one(opcode); @@ -156,23 +157,22 @@ void hp_nanoprocessor_device::state_string_export(const device_state_entry &entr { if (entry.index() == STATE_GENFLAGS) { // DC7 is reported as "I" because it is usually used as interrupt enable - str = string_format("%c %c%c%c%c%c%c%c%c" , BIT(m_flags , NANO_E_BIT) ? 'E' : ' ', - BIT(m_flags , NANO_DC0_BIT + 7) ? 'I' : ' ', - BIT(m_flags , NANO_DC0_BIT + 6) ? '6' : ' ', - BIT(m_flags , NANO_DC0_BIT + 5) ? '5' : ' ', - BIT(m_flags , NANO_DC0_BIT + 4) ? '4' : ' ', - BIT(m_flags , NANO_DC0_BIT + 3) ? '3' : ' ', - BIT(m_flags , NANO_DC0_BIT + 2) ? '2' : ' ', - BIT(m_flags , NANO_DC0_BIT + 1) ? '1' : ' ', - BIT(m_flags , NANO_DC0_BIT + 0) ? '0' : ' '); + str = string_format("%c %c%c%c%c%c%c%c%c", BIT(m_flags, NANO_E_BIT) ? 'E' : ' ', + BIT(m_flags, NANO_DC0_BIT + 7) ? 'I' : ' ', + BIT(m_flags, NANO_DC0_BIT + 6) ? '6' : ' ', + BIT(m_flags, NANO_DC0_BIT + 5) ? '5' : ' ', + BIT(m_flags, NANO_DC0_BIT + 4) ? '4' : ' ', + BIT(m_flags, NANO_DC0_BIT + 3) ? '3' : ' ', + BIT(m_flags, NANO_DC0_BIT + 2) ? '2' : ' ', + BIT(m_flags, NANO_DC0_BIT + 1) ? '1' : ' ', + BIT(m_flags, NANO_DC0_BIT + 0) ? '0' : ' '); } } -offs_t hp_nanoprocessor_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *hp_nanoprocessor_device::create_disassembler() { - extern CPU_DISASSEMBLE(hp_nanoprocessor); - return CPU_DISASSEMBLE_NAME(hp_nanoprocessor)(this , stream , pc , oprom , opram , options); + return new hp_nanoprocessor_disassembler; } void hp_nanoprocessor_device::execute_one(uint8_t opcode) @@ -299,14 +299,14 @@ void hp_nanoprocessor_device::execute_one(uint8_t opcode) case 0x1f: // SES - if (BIT(m_flags , NANO_E_BIT)) { + if (BIT(m_flags, NANO_E_BIT)) { skip(); } break; case 0x3f: // SEZ - if (!BIT(m_flags , NANO_E_BIT)) { + if (!BIT(m_flags, NANO_E_BIT)) { skip(); } break; @@ -359,7 +359,7 @@ void hp_nanoprocessor_device::execute_one(uint8_t opcode) switch (opcode & 0xf8) { case 0x10: // SBS - if (BIT(m_reg_A , opcode & 7)) { + if (BIT(m_reg_A, opcode & 7)) { skip(); } break; @@ -369,7 +369,7 @@ void hp_nanoprocessor_device::execute_one(uint8_t opcode) { uint8_t tmp = m_read_dc_func(); tmp &= (uint8_t)(m_flags >> NANO_DC0_BIT); - if (BIT(tmp , opcode & 7)) { + if (BIT(tmp, opcode & 7)) { skip(); } } @@ -387,7 +387,7 @@ void hp_nanoprocessor_device::execute_one(uint8_t opcode) case 0x30: // SBZ - if (!BIT(m_reg_A , opcode & 7)) { + if (!BIT(m_reg_A, opcode & 7)) { skip(); } break; @@ -397,7 +397,7 @@ void hp_nanoprocessor_device::execute_one(uint8_t opcode) { uint8_t tmp = m_read_dc_func(); tmp &= (uint8_t)(m_flags >> NANO_DC0_BIT); - if (!BIT(tmp , opcode & 7)) { + if (!BIT(tmp, opcode & 7)) { skip(); } } @@ -459,7 +459,7 @@ void hp_nanoprocessor_device::execute_one(uint8_t opcode) case 0x50: // OTA - m_io->write_byte(opcode & 0xf , m_reg_A); + m_io->write_byte(opcode & 0xf, m_reg_A); break; case 0x60: @@ -474,7 +474,7 @@ void hp_nanoprocessor_device::execute_one(uint8_t opcode) case 0xc0: // OTR - m_io->write_byte(opcode & 0xf , fetch()); + m_io->write_byte(opcode & 0xf, fetch()); break; case 0xd0: @@ -493,7 +493,7 @@ void hp_nanoprocessor_device::execute_one(uint8_t opcode) break; default: - logerror("Unknown opcode %02x @ 0x03x\n" , opcode , m_reg_PA); + logerror("Unknown opcode %02x @ 0x03x\n", opcode, m_reg_PA); break; } } diff --git a/src/devices/cpu/nanoprocessor/nanoprocessor.h b/src/devices/cpu/nanoprocessor/nanoprocessor.h index 3518d80810b..52f4cb3943f 100644 --- a/src/devices/cpu/nanoprocessor/nanoprocessor.h +++ b/src/devices/cpu/nanoprocessor/nanoprocessor.h @@ -91,9 +91,7 @@ public: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 2; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: static constexpr unsigned HP_NANO_REGS = 16; // Number of GP registers diff --git a/src/devices/cpu/nanoprocessor/nanoprocessor_dasm.cpp b/src/devices/cpu/nanoprocessor/nanoprocessor_dasm.cpp index 6ec1239dbc6..352c8fcbcf2 100644 --- a/src/devices/cpu/nanoprocessor/nanoprocessor_dasm.cpp +++ b/src/devices/cpu/nanoprocessor/nanoprocessor_dasm.cpp @@ -5,126 +5,118 @@ // ******************************* #include "emu.h" -#include "debugger.h" -#include "nanoprocessor.h" +#include "nanoprocessor_dasm.h" -typedef void (*fn_dis_param)(std::ostream& stream , uint8_t opcode , const uint8_t* opram); - -typedef struct { - uint8_t m_op_mask; - uint8_t m_opcode; - const char *m_mnemonic; - fn_dis_param m_param_fn; - uint32_t m_dasm_flags; -} dis_entry_t; - -static void param_bitno(std::ostream& stream , uint8_t opcode , const uint8_t* opram) +void hp_nanoprocessor_disassembler::param_bitno(std::ostream& stream, uint8_t opcode, offs_t pc, const data_buffer ¶ms) { stream << (char)('0' + (opcode & 7)); } -static void param_ds(std::ostream& stream , uint8_t opcode , const uint8_t* opram) +void hp_nanoprocessor_disassembler::param_ds(std::ostream& stream, uint8_t opcode, offs_t pc, const data_buffer ¶ms) { - util::stream_format(stream , "DS%u" , opcode & 0xf); + util::stream_format(stream, "DS%u", opcode & 0xf); } -static void param_reg(std::ostream& stream , uint8_t opcode , const uint8_t* opram) +void hp_nanoprocessor_disassembler::param_reg(std::ostream& stream, uint8_t opcode, offs_t pc, const data_buffer ¶ms) { - util::stream_format(stream , "R%u" , opcode & 0xf); + util::stream_format(stream, "R%u", opcode & 0xf); } -static void param_11bit(std::ostream& stream , uint8_t opcode , const uint8_t* opram) +void hp_nanoprocessor_disassembler::param_11bit(std::ostream& stream, uint8_t opcode, offs_t pc, const data_buffer ¶ms) { - unsigned tmp = ((unsigned)(opcode & 7) << 8) | *opram; - util::stream_format(stream , "$%03x" , tmp); + unsigned tmp = ((unsigned)(opcode & 7) << 8) | params.r8(pc); + util::stream_format(stream, "$%03x", tmp); } -static void param_page_no(std::ostream& stream , uint8_t opcode , const uint8_t* opram) +void hp_nanoprocessor_disassembler::param_page_no(std::ostream& stream, uint8_t opcode, offs_t pc, const data_buffer ¶ms) { stream << (char)('0' + (opcode & 7)); } -static void param_byte(std::ostream& stream , uint8_t opcode , const uint8_t* opram) +void hp_nanoprocessor_disassembler::param_byte(std::ostream& stream, uint8_t opcode, offs_t pc, const data_buffer ¶ms) { - util::stream_format(stream , "$%02x" , *opram); + util::stream_format(stream, "$%02x", params.r8(pc)); } -static void param_ds_byte(std::ostream& stream , uint8_t opcode , const uint8_t* opram) +void hp_nanoprocessor_disassembler::param_ds_byte(std::ostream& stream, uint8_t opcode, offs_t pc, const data_buffer ¶ms) { - util::stream_format(stream , "DS%u,$%02x" , opcode & 0xf , *opram); + util::stream_format(stream, "DS%u,$%02x", opcode & 0xf, params.r8(pc)); } -static void param_reg_byte(std::ostream& stream , uint8_t opcode , const uint8_t* opram) +void hp_nanoprocessor_disassembler::param_reg_byte(std::ostream& stream, uint8_t opcode, offs_t pc, const data_buffer ¶ms) { - util::stream_format(stream , "R%u,$%02x" , opcode & 0xf , *opram); + util::stream_format(stream, "R%u,$%02x", opcode & 0xf, params.r8(pc)); } -static const dis_entry_t dis_table[] = { - {0xff , 0x00 , "INB" , nullptr , 1}, - {0xff , 0x01 , "DEB" , nullptr , 1}, - {0xff , 0x02 , "IND" , nullptr , 1}, - {0xff , 0x03 , "DED" , nullptr , 1}, - {0xff , 0x04 , "CLA" , nullptr , 1}, - {0xff , 0x05 , "CMA" , nullptr , 1}, - {0xff , 0x06 , "RSA" , nullptr , 1}, - {0xff , 0x07 , "LSA" , nullptr , 1}, - {0xff , 0x08 , "SGT" , nullptr , 1}, - {0xff , 0x09 , "SLT" , nullptr , 1}, - {0xff , 0x0a , "SEQ" , nullptr , 1}, - {0xff , 0x0b , "SAZ" , nullptr , 1}, - {0xff , 0x0c , "SLE" , nullptr , 1}, - {0xff , 0x0d , "SGE" , nullptr , 1}, - {0xff , 0x0e , "SNE" , nullptr , 1}, - {0xff , 0x0f , "SAN" , nullptr , 1}, - {0xf8 , 0x10 , "SBS" , param_bitno , 1}, - {0xff , 0x1f , "SES" , nullptr , 1}, - {0xf8 , 0x18 , "SFS" , param_bitno , 1}, - {0xf8 , 0x20 , "SBN" , param_bitno , 1}, - {0xff , 0x2f , "ENI" , nullptr , 1}, - {0xf8 , 0x28 , "STC" , param_bitno , 1}, - {0xf8 , 0x30 , "SBZ" , param_bitno , 1}, - {0xff , 0x3f , "SEZ" , nullptr , 1}, - {0xf8 , 0x38 , "SFZ" , param_bitno , 1}, - {0xf0 , 0x40 , "INA" , param_ds , 1}, - {0xff , 0x5f , "NOP" , nullptr , 1}, - {0xf0 , 0x50 , "OTA" , param_ds , 1}, - {0xf0 , 0x60 , "LDA" , param_reg , 1}, - {0xf0 , 0x70 , "STA" , param_reg , 1}, - {0xf8 , 0x80 , "JMP" , param_11bit , 2}, - {0xf8 , 0x88 , "JSB" , param_11bit , 2 | DASMFLAG_STEP_OVER}, - {0xf8 , 0x90 , "JAI" , param_page_no , 1}, - {0xf8 , 0x98 , "JAS" , param_page_no , 1 | DASMFLAG_STEP_OVER}, - {0xf8 , 0xa0 , "CBN" , param_bitno , 1}, - {0xff , 0xaf , "DSI" , nullptr , 1}, - {0xf8 , 0xa8 , "CLC" , param_bitno , 1}, - {0xff , 0xb0 , "RTI" , nullptr , 1 | DASMFLAG_STEP_OUT}, - {0xff , 0xb1 , "RTE" , nullptr , 1 | DASMFLAG_STEP_OUT}, - {0xff , 0xb4 , "STE" , nullptr , 1}, - {0xff , 0xb5 , "CLE" , nullptr , 1}, - {0xff , 0xb8 , "RTS" , nullptr , 1 | DASMFLAG_STEP_OUT}, - {0xff , 0xb9 , "RSE" , nullptr , 1 | DASMFLAG_STEP_OUT}, - {0xff , 0xcf , "LDR" , param_byte , 2}, - {0xf0 , 0xc0 , "OTR" , param_ds_byte , 2}, - {0xf0 , 0xd0 , "STR" , param_reg_byte , 2}, - {0xf0 , 0xe0 , "LDI" , param_reg , 1}, - {0xf0 , 0xf0 , "STI" , param_reg , 1}, +const hp_nanoprocessor_disassembler::dis_entry_t hp_nanoprocessor_disassembler::dis_table[] = { + {0xff, 0x00, "INB", nullptr, 1}, + {0xff, 0x01, "DEB", nullptr, 1}, + {0xff, 0x02, "IND", nullptr, 1}, + {0xff, 0x03, "DED", nullptr, 1}, + {0xff, 0x04, "CLA", nullptr, 1}, + {0xff, 0x05, "CMA", nullptr, 1}, + {0xff, 0x06, "RSA", nullptr, 1}, + {0xff, 0x07, "LSA", nullptr, 1}, + {0xff, 0x08, "SGT", nullptr, 1}, + {0xff, 0x09, "SLT", nullptr, 1}, + {0xff, 0x0a, "SEQ", nullptr, 1}, + {0xff, 0x0b, "SAZ", nullptr, 1}, + {0xff, 0x0c, "SLE", nullptr, 1}, + {0xff, 0x0d, "SGE", nullptr, 1}, + {0xff, 0x0e, "SNE", nullptr, 1}, + {0xff, 0x0f, "SAN", nullptr, 1}, + {0xf8, 0x10, "SBS", &hp_nanoprocessor_disassembler::param_bitno, 1}, + {0xff, 0x1f, "SES", nullptr, 1}, + {0xf8, 0x18, "SFS", &hp_nanoprocessor_disassembler::param_bitno, 1}, + {0xf8, 0x20, "SBN", &hp_nanoprocessor_disassembler::param_bitno, 1}, + {0xff, 0x2f, "ENI", nullptr, 1}, + {0xf8, 0x28, "STC", &hp_nanoprocessor_disassembler::param_bitno, 1}, + {0xf8, 0x30, "SBZ", &hp_nanoprocessor_disassembler::param_bitno, 1}, + {0xff, 0x3f, "SEZ", nullptr, 1}, + {0xf8, 0x38, "SFZ", &hp_nanoprocessor_disassembler::param_bitno, 1}, + {0xf0, 0x40, "INA", &hp_nanoprocessor_disassembler::param_ds, 1}, + {0xff, 0x5f, "NOP", nullptr, 1}, + {0xf0, 0x50, "OTA", &hp_nanoprocessor_disassembler::param_ds, 1}, + {0xf0, 0x60, "LDA", &hp_nanoprocessor_disassembler::param_reg, 1}, + {0xf0, 0x70, "STA", &hp_nanoprocessor_disassembler::param_reg, 1}, + {0xf8, 0x80, "JMP", &hp_nanoprocessor_disassembler::param_11bit, 2}, + {0xf8, 0x88, "JSB", &hp_nanoprocessor_disassembler::param_11bit, 2 | STEP_OVER}, + {0xf8, 0x90, "JAI", &hp_nanoprocessor_disassembler::param_page_no, 1}, + {0xf8, 0x98, "JAS", &hp_nanoprocessor_disassembler::param_page_no, 1 | STEP_OVER}, + {0xf8, 0xa0, "CBN", &hp_nanoprocessor_disassembler::param_bitno, 1}, + {0xff, 0xaf, "DSI", nullptr, 1}, + {0xf8, 0xa8, "CLC", &hp_nanoprocessor_disassembler::param_bitno, 1}, + {0xff, 0xb0, "RTI", nullptr, 1 | STEP_OUT}, + {0xff, 0xb1, "RTE", nullptr, 1 | STEP_OUT}, + {0xff, 0xb4, "STE", nullptr, 1}, + {0xff, 0xb5, "CLE", nullptr, 1}, + {0xff, 0xb8, "RTS", nullptr, 1 | STEP_OUT}, + {0xff, 0xb9, "RSE", nullptr, 1 | STEP_OUT}, + {0xff, 0xcf, "LDR", &hp_nanoprocessor_disassembler::param_byte, 2}, + {0xf0, 0xc0, "OTR", &hp_nanoprocessor_disassembler::param_ds_byte, 2}, + {0xf0, 0xd0, "STR", &hp_nanoprocessor_disassembler::param_reg_byte, 2}, + {0xf0, 0xe0, "LDI", &hp_nanoprocessor_disassembler::param_reg, 1}, + {0xf0, 0xf0, "STI", &hp_nanoprocessor_disassembler::param_reg, 1}, // Catchall for undefined opcodes - {0x00 , 0x00 , "???" , nullptr , 1} + {0x00, 0x00, "???", nullptr, 1} }; -CPU_DISASSEMBLE(hp_nanoprocessor) +u32 hp_nanoprocessor_disassembler::opcode_alignment() const { - const uint8_t opcode = *oprom; + return 1; +} - opram++; +offs_t hp_nanoprocessor_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + const uint8_t opcode = opcodes.r8(pc); for (const dis_entry_t& ent : dis_table) { if ((opcode & ent.m_op_mask) == ent.m_opcode) { stream << ent.m_mnemonic << ' '; if (ent.m_param_fn != nullptr) { - ent.m_param_fn(stream , opcode , opram); + (this->*ent.m_param_fn)(stream, opcode, pc+1, params); } - return ent.m_dasm_flags | DASMFLAG_SUPPORTED; + return ent.m_dasm_flags | SUPPORTED; } } // Should never ever happen diff --git a/src/devices/cpu/nanoprocessor/nanoprocessor_dasm.h b/src/devices/cpu/nanoprocessor/nanoprocessor_dasm.h new file mode 100644 index 00000000000..1287e0db605 --- /dev/null +++ b/src/devices/cpu/nanoprocessor/nanoprocessor_dasm.h @@ -0,0 +1,44 @@ +// license:BSD-3-Clause +// copyright-holders:F. Ulivi +// ******************************* +// * HP nanoprocessor disassembler +// ******************************* + +#ifndef MAME_CPU_NANOPROCESSOR_NANOPROCESSOR_DASM_H +#define MAME_CPU_NANOPROCESSOR_NANOPROCESSOR_DASM_H + +#pragma once + +class hp_nanoprocessor_disassembler : public util::disasm_interface +{ +public: + hp_nanoprocessor_disassembler() = default; + virtual ~hp_nanoprocessor_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + typedef void (hp_nanoprocessor_disassembler::*fn_dis_param)(std::ostream& stream, uint8_t opcode, offs_t pc, const data_buffer ¶ms); + + typedef struct { + uint8_t m_op_mask; + uint8_t m_opcode; + const char *m_mnemonic; + fn_dis_param m_param_fn; + uint32_t m_dasm_flags; + } dis_entry_t; + + void param_bitno(std::ostream& stream, uint8_t opcode, offs_t pc, const data_buffer ¶ms); + void param_ds(std::ostream& stream, uint8_t opcode, offs_t pc, const data_buffer ¶ms); + void param_reg(std::ostream& stream, uint8_t opcode, offs_t pc, const data_buffer ¶ms); + void param_11bit(std::ostream& stream, uint8_t opcode, offs_t pc, const data_buffer ¶ms); + void param_page_no(std::ostream& stream, uint8_t opcode, offs_t pc, const data_buffer ¶ms); + void param_byte(std::ostream& stream, uint8_t opcode, offs_t pc, const data_buffer ¶ms); + void param_ds_byte(std::ostream& stream, uint8_t opcode, offs_t pc, const data_buffer ¶ms); + void param_reg_byte(std::ostream& stream, uint8_t opcode, offs_t pc, const data_buffer ¶ms); + + static const dis_entry_t dis_table[]; +}; + +#endif diff --git a/src/devices/cpu/nec/nec.cpp b/src/devices/cpu/nec/nec.cpp index a4410cc12e8..d36a2bfdd04 100644 --- a/src/devices/cpu/nec/nec.cpp +++ b/src/devices/cpu/nec/nec.cpp @@ -106,6 +106,7 @@ #include "emu.h" #include "nec.h" +#include "necdasm.h" #include "debugger.h" typedef uint8_t BOOLEAN; @@ -169,10 +170,9 @@ v33a_device::v33a_device(const machine_config &mconfig, const char *tag, device_ } -offs_t nec_common_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *nec_common_device::create_disassembler() { - extern CPU_DISASSEMBLE( nec ); - return CPU_DISASSEMBLE_NAME(nec)(this, stream, pc, oprom, opram, options); + return new nec_disassembler; } @@ -223,8 +223,8 @@ uint8_t nec_common_device::fetch() uint16_t nec_common_device::fetchword() { - uint16_t r = FETCH(); - r |= (FETCH()<<8); + uint16_t r = fetch(); + r |= (fetch()<<8); return r; } diff --git a/src/devices/cpu/nec/nec.h b/src/devices/cpu/nec/nec.h index 4ec9e02459d..fee1806c066 100644 --- a/src/devices/cpu/nec/nec.h +++ b/src/devices/cpu/nec/nec.h @@ -48,9 +48,7 @@ protected: virtual void state_export(const device_state_entry &entry) override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 8; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/nec/nec_common.h b/src/devices/cpu/nec/nec_common.h deleted file mode 100644 index 4356214a302..00000000000 --- a/src/devices/cpu/nec/nec_common.h +++ /dev/null @@ -1,9 +0,0 @@ -#ifndef NEC_COMMON_H -#define NEC_COMMON_H - -#include - -extern int necv_dasm_one(std::ostream &stream, uint32_t eip, const uint8_t *oprom, const uint8_t *decryption_table); -extern int necv_dasm_one(char *buffer, uint32_t eip, const uint8_t *oprom, const uint8_t *decryption_table); - -#endif // NEC_COMMON_H diff --git a/src/devices/cpu/nec/necdasm.cpp b/src/devices/cpu/nec/necdasm.cpp index d313eeaf531..36f155d2527 100644 --- a/src/devices/cpu/nec/necdasm.cpp +++ b/src/devices/cpu/nec/necdasm.cpp @@ -8,82 +8,9 @@ */ #include "emu.h" -#include "nec_common.h" +#include "necdasm.h" -static const uint8_t *Iconfig; - -enum -{ - PARAM_REG8 = 1, /* 8-bit register */ - PARAM_REG16, /* 16-bit register */ - PARAM_REG2_8, /* 8-bit register */ - PARAM_REG2_16, /* 16-bit register */ - PARAM_RM8, /* 8-bit memory or register */ - PARAM_RM16, /* 16-bit memory or register */ - PARAM_RMPTR8, /* 8-bit memory or register */ - PARAM_RMPTR16, /* 16-bit memory or register */ - PARAM_I3, /* 3-bit immediate */ - PARAM_I4, /* 4-bit immediate */ - PARAM_I8, /* 8-bit signed immediate */ - PARAM_I16, /* 16-bit signed immediate */ - PARAM_UI8, /* 8-bit unsigned immediate */ - PARAM_IMM, /* 16-bit immediate */ - PARAM_ADDR, /* 16:16 address */ - PARAM_REL8, /* 8-bit PC-relative displacement */ - PARAM_REL16, /* 16-bit PC-relative displacement */ - PARAM_MEM_OFFS, /* 16-bit mem offset */ - PARAM_SREG, /* segment register */ - PARAM_SFREG, /* V25/V35 special function register */ - PARAM_1, /* used by shift/rotate instructions */ - PARAM_AL, - PARAM_CL, - PARAM_DL, - PARAM_BL, - PARAM_AH, - PARAM_CH, - PARAM_DH, - PARAM_BH, - PARAM_AW, - PARAM_CW, - PARAM_DW, - PARAM_BW, - PARAM_SP, - PARAM_BP, - PARAM_IX, - PARAM_IY -}; - -enum -{ - MODRM = 1, - GROUP, - FPU, - TWO_BYTE, - PREFIX, - SEG_PS, - SEG_DS0, - SEG_DS1, - SEG_SS -}; - -struct NEC_I386_OPCODE { - char mnemonic[32]; - uint32_t flags; - uint32_t param1; - uint32_t param2; - uint32_t param3; - offs_t dasm_flags; -}; - -struct NEC_GROUP_OP { - char mnemonic[32]; - const NEC_I386_OPCODE *opcode; -}; - -static const uint8_t *opcode_ptr; -static const uint8_t *opcode_ptr_base; - -static const NEC_I386_OPCODE necv_opcode_table1[256] = +const nec_disassembler::NEC_I386_OPCODE nec_disassembler::necv_opcode_table1[256] = { // 0x00 {"add", MODRM, PARAM_RM8, PARAM_REG8, 0 }, @@ -191,7 +118,7 @@ static const NEC_I386_OPCODE necv_opcode_table1[256] = {"push r", 0, 0, 0, 0 }, {"pop r", 0, 0, 0, 0 }, {"chkind", MODRM, PARAM_REG16, PARAM_RM16, 0 }, - {"brkn", 0, PARAM_UI8, 0, 0, DASMFLAG_STEP_OVER}, /* V25S/V35S only */ + {"brkn", 0, PARAM_UI8, 0, 0, STEP_OVER}, /* V25S/V35S only */ {"repnc", PREFIX, 0, 0, 0 }, {"repc", PREFIX, 0, 0, 0 }, {"fpo2 0", 0, 0, 0, 0 }, /* for a coprocessor that was never made */ @@ -249,7 +176,7 @@ static const NEC_I386_OPCODE necv_opcode_table1[256] = {"xch", 0, PARAM_AW, PARAM_IY, 0 }, {"cvtbw", 0, 0, 0, 0 }, {"cvtwl", 0, 0, 0, 0 }, - {"call", 0, PARAM_ADDR, 0, 0, DASMFLAG_STEP_OVER}, + {"call", 0, PARAM_ADDR, 0, 0, STEP_OVER}, {"poll", 0, 0, 0, 0 }, {"push psw", 0, 0, 0, 0 }, {"pop psw", 0, 0, 0, 0 }, @@ -292,20 +219,20 @@ static const NEC_I386_OPCODE necv_opcode_table1[256] = // 0xc0 {"shiftbi", GROUP, 0, 0, 0 }, {"shiftwi", GROUP, 0, 0, 0 }, - {"ret", 0, PARAM_I16, 0, 0, DASMFLAG_STEP_OUT}, - {"ret", 0, 0, 0, 0, DASMFLAG_STEP_OUT}, + {"ret", 0, PARAM_I16, 0, 0, STEP_OUT}, + {"ret", 0, 0, 0, 0, STEP_OUT}, {"mov ds1,", MODRM, PARAM_REG16, PARAM_RM16, 0 }, {"mov ds0,", MODRM, PARAM_REG16, PARAM_RM16, 0 }, {"mov", MODRM, PARAM_RMPTR8, PARAM_UI8, 0 }, {"mov", MODRM, PARAM_RMPTR16, PARAM_IMM, 0 }, {"prepare", 0, PARAM_I16, PARAM_UI8, 0 }, {"dispose", 0, 0, 0, 0 }, - {"retf", 0, PARAM_I16, 0, 0, DASMFLAG_STEP_OUT}, - {"retf", 0, 0, 0, 0, DASMFLAG_STEP_OUT}, - {"brk 3", 0, 0, 0, 0, DASMFLAG_STEP_OVER}, - {"brk", 0, PARAM_UI8, 0, 0, DASMFLAG_STEP_OVER}, + {"retf", 0, PARAM_I16, 0, 0, STEP_OUT}, + {"retf", 0, 0, 0, 0, STEP_OUT}, + {"brk 3", 0, 0, 0, 0, STEP_OVER}, + {"brk", 0, PARAM_UI8, 0, 0, STEP_OVER}, {"brkv", 0, 0, 0, 0 }, - {"reti", 0, 0, 0, 0, DASMFLAG_STEP_OUT}, + {"reti", 0, 0, 0, 0, STEP_OUT}, // 0xd0 {"shiftb", GROUP, 0, 0, 0 }, {"shiftw", GROUP, 0, 0, 0 }, @@ -324,15 +251,15 @@ static const NEC_I386_OPCODE necv_opcode_table1[256] = {"escape", FPU, 0, 0, 0 }, {"escape", FPU, 0, 0, 0 }, // 0xe0 - {"dbnzne", 0, PARAM_REL8, 0, 0, DASMFLAG_STEP_OVER}, - {"dbnze", 0, PARAM_REL8, 0, 0, DASMFLAG_STEP_OVER}, - {"dbnz", 0, PARAM_REL8, 0, 0, DASMFLAG_STEP_OVER}, + {"dbnzne", 0, PARAM_REL8, 0, 0, STEP_OVER}, + {"dbnze", 0, PARAM_REL8, 0, 0, STEP_OVER}, + {"dbnz", 0, PARAM_REL8, 0, 0, STEP_OVER}, {"bcwz", 0, PARAM_REL8, 0, 0 }, {"in", 0, PARAM_AL, PARAM_UI8, 0 }, {"in", 0, PARAM_AW, PARAM_UI8, 0 }, {"out", 0, PARAM_UI8, PARAM_AL, 0 }, {"out", 0, PARAM_UI8, PARAM_AW, 0 }, - {"call", 0, PARAM_REL16, 0, 0, DASMFLAG_STEP_OVER}, + {"call", 0, PARAM_REL16, 0, 0, STEP_OVER}, {"br", 0, PARAM_REL16, 0, 0 }, {"br", 0, PARAM_ADDR, 0, 0 }, {"br", 0, PARAM_REL8, 0, 0 }, @@ -342,7 +269,7 @@ static const NEC_I386_OPCODE necv_opcode_table1[256] = {"out", 0, PARAM_DW, PARAM_AW, 0 }, // 0xf0 {"buslock", PREFIX, 0, 0, 0 }, - {"brks", 0, PARAM_UI8, 0, 0, DASMFLAG_STEP_OVER}, /* V25S/V35S only */ + {"brks", 0, PARAM_UI8, 0, 0, STEP_OVER}, /* V25S/V35S only */ {"repne", PREFIX, 0, 0, 0 }, {"rep", PREFIX, 0, 0, 0 }, {"halt", 0, 0, 0, 0 }, @@ -359,7 +286,7 @@ static const NEC_I386_OPCODE necv_opcode_table1[256] = {"group2w", GROUP, 0, 0, 0 } }; -static const NEC_I386_OPCODE necv_opcode_table2[256] = +const nec_disassembler::NEC_I386_OPCODE nec_disassembler::necv_opcode_table2[256] = { // 0x00 {"???", 0, 0, 0, 0 }, @@ -409,7 +336,7 @@ static const NEC_I386_OPCODE necv_opcode_table2[256] = {"ror4", MODRM, PARAM_RMPTR8, 0, 0 }, {"???", 0, 0, 0, 0 }, {"???", 0, 0, 0, 0 }, - {"brkcs", MODRM, PARAM_REG2_16, 0, 0, DASMFLAG_STEP_OVER}, /* V25/V35 only */ + {"brkcs", MODRM, PARAM_REG2_16, 0, 0, STEP_OVER}, /* V25/V35 only */ {"???", 0, 0, 0, 0 }, {"???", 0, 0, 0, 0 }, // 0x30 @@ -635,7 +562,7 @@ static const NEC_I386_OPCODE necv_opcode_table2[256] = {"brkem", 0, PARAM_UI8, 0, 0 } /* V20,30,40,50 only */ }; -static const NEC_I386_OPCODE immb_table[8] = +const nec_disassembler::NEC_I386_OPCODE nec_disassembler::immb_table[8] = { {"add", 0, PARAM_RMPTR8, PARAM_UI8, 0 }, {"or", 0, PARAM_RMPTR8, PARAM_UI8, 0 }, @@ -647,7 +574,7 @@ static const NEC_I386_OPCODE immb_table[8] = {"cmp", 0, PARAM_RMPTR8, PARAM_UI8, 0 } }; -static const NEC_I386_OPCODE immw_table[8] = +const nec_disassembler::NEC_I386_OPCODE nec_disassembler::immw_table[8] = { {"add", 0, PARAM_RMPTR16, PARAM_IMM, 0 }, {"or", 0, PARAM_RMPTR16, PARAM_IMM, 0 }, @@ -659,7 +586,7 @@ static const NEC_I386_OPCODE immw_table[8] = {"cmp", 0, PARAM_RMPTR16, PARAM_IMM, 0 } }; -static const NEC_I386_OPCODE immws_table[8] = +const nec_disassembler::NEC_I386_OPCODE nec_disassembler::immws_table[8] = { {"add", 0, PARAM_RMPTR16, PARAM_I8, 0 }, {"or", 0, PARAM_RMPTR16, PARAM_I8, 0 }, @@ -671,7 +598,7 @@ static const NEC_I386_OPCODE immws_table[8] = {"cmp", 0, PARAM_RMPTR16, PARAM_I8, 0 } }; -static const NEC_I386_OPCODE shiftbi_table[8] = +const nec_disassembler::NEC_I386_OPCODE nec_disassembler::shiftbi_table[8] = { {"rol", 0, PARAM_RMPTR8, PARAM_I8, 0 }, {"ror", 0, PARAM_RMPTR8, PARAM_I8, 0 }, @@ -683,7 +610,7 @@ static const NEC_I386_OPCODE shiftbi_table[8] = {"shra", 0, PARAM_RMPTR8, PARAM_I8, 0 } }; -static const NEC_I386_OPCODE shiftwi_table[8] = +const nec_disassembler::NEC_I386_OPCODE nec_disassembler::shiftwi_table[8] = { {"rol", 0, PARAM_RMPTR16, PARAM_I8, 0 }, {"ror", 0, PARAM_RMPTR16, PARAM_I8, 0 }, @@ -695,7 +622,7 @@ static const NEC_I386_OPCODE shiftwi_table[8] = {"shra", 0, PARAM_RMPTR16, PARAM_I8, 0 } }; -static const NEC_I386_OPCODE shiftb_table[8] = +const nec_disassembler::NEC_I386_OPCODE nec_disassembler::shiftb_table[8] = { {"rol", 0, PARAM_RMPTR8, PARAM_1, 0 }, {"ror", 0, PARAM_RMPTR8, PARAM_1, 0 }, @@ -707,7 +634,7 @@ static const NEC_I386_OPCODE shiftb_table[8] = {"shra", 0, PARAM_RMPTR8, PARAM_1, 0 } }; -static const NEC_I386_OPCODE shiftw_table[8] = +const nec_disassembler::NEC_I386_OPCODE nec_disassembler::shiftw_table[8] = { {"rol", 0, PARAM_RMPTR16, PARAM_1, 0 }, {"ror", 0, PARAM_RMPTR16, PARAM_1, 0 }, @@ -719,7 +646,7 @@ static const NEC_I386_OPCODE shiftw_table[8] = {"shra", 0, PARAM_RMPTR16, PARAM_1, 0 } }; -static const NEC_I386_OPCODE shiftbv_table[8] = +const nec_disassembler::NEC_I386_OPCODE nec_disassembler::shiftbv_table[8] = { {"rol", 0, PARAM_RMPTR8, PARAM_CL, 0 }, {"ror", 0, PARAM_RMPTR8, PARAM_CL, 0 }, @@ -731,7 +658,7 @@ static const NEC_I386_OPCODE shiftbv_table[8] = {"shra", 0, PARAM_RMPTR8, PARAM_CL, 0 } }; -static const NEC_I386_OPCODE shiftwv_table[8] = +const nec_disassembler::NEC_I386_OPCODE nec_disassembler::shiftwv_table[8] = { {"rol", 0, PARAM_RMPTR16, PARAM_CL, 0 }, {"ror", 0, PARAM_RMPTR16, PARAM_CL, 0 }, @@ -743,7 +670,7 @@ static const NEC_I386_OPCODE shiftwv_table[8] = {"shra", 0, PARAM_RMPTR16, PARAM_CL, 0 } }; -static const NEC_I386_OPCODE group1b_table[8] = +const nec_disassembler::NEC_I386_OPCODE nec_disassembler::group1b_table[8] = { {"test", 0, PARAM_RMPTR8, PARAM_UI8, 0 }, {"???", 0, 0, 0, 0 }, @@ -755,7 +682,7 @@ static const NEC_I386_OPCODE group1b_table[8] = {"div", 0, PARAM_RMPTR8, 0, 0 } }; -static const NEC_I386_OPCODE group1w_table[8] = +const nec_disassembler::NEC_I386_OPCODE nec_disassembler::group1w_table[8] = { {"test", 0, PARAM_RMPTR16, PARAM_IMM, 0 }, {"???", 0, 0, 0, 0 }, @@ -767,7 +694,7 @@ static const NEC_I386_OPCODE group1w_table[8] = {"div", 0, PARAM_RMPTR16, 0, 0 } }; -static const NEC_I386_OPCODE group2b_table[8] = +const nec_disassembler::NEC_I386_OPCODE nec_disassembler::group2b_table[8] = { {"inc", 0, PARAM_RMPTR8, 0, 0 }, {"dec", 0, PARAM_RMPTR8, 0, 0 }, @@ -779,19 +706,19 @@ static const NEC_I386_OPCODE group2b_table[8] = {"???", 0, 0, 0, 0 } }; -static const NEC_I386_OPCODE group2w_table[8] = +const nec_disassembler::NEC_I386_OPCODE nec_disassembler::group2w_table[8] = { {"inc", 0, PARAM_RMPTR16, 0, 0 }, {"dec", 0, PARAM_RMPTR16, 0, 0 }, - {"call", 0, PARAM_RMPTR16, 0, 0, DASMFLAG_STEP_OVER}, - {"call far ptr ",0, PARAM_RM16, 0, 0, DASMFLAG_STEP_OVER}, + {"call", 0, PARAM_RMPTR16, 0, 0, STEP_OVER}, + {"call far ptr ",0, PARAM_RM16, 0, 0, STEP_OVER}, {"br", 0, PARAM_RMPTR16, 0, 0 }, {"br far ptr ",0, PARAM_RM16, 0, 0 }, {"push", 0, PARAM_RMPTR16, 0, 0 }, {"???", 0, 0, 0, 0 } }; -static const NEC_GROUP_OP group_op_table[] = +const nec_disassembler::NEC_GROUP_OP nec_disassembler::group_op_table[] = { { "immb", immb_table }, { "immw", immw_table }, @@ -810,10 +737,10 @@ static const NEC_GROUP_OP group_op_table[] = -static const char *const nec_reg[8] = { "aw", "cw", "dw", "bw", "sp", "bp", "ix", "iy" }; -static const char *const nec_reg8[8] = { "al", "cl", "dl", "bl", "ah", "ch", "dh", "bh" }; -static const char *const nec_sreg[8] = { "ds1", "ps", "ss", "ds0", "???", "???", "???", "???" }; -static const char *const nec_sfreg[256] = +const char *const nec_disassembler::nec_reg[8] = { "aw", "cw", "dw", "bw", "sp", "bp", "ix", "iy" }; +const char *const nec_disassembler::nec_reg8[8] = { "al", "cl", "dl", "bl", "ah", "ch", "dh", "bh" }; +const char *const nec_disassembler::nec_sreg[8] = { "ds1", "ps", "ss", "ds0", "???", "???", "???", "???" }; +const char *const nec_disassembler::nec_sfreg[256] = { /* 0x00 */ "p0", "pm0", "pmc0", "???", "???", "???", "???", "???", @@ -865,130 +792,88 @@ static const char *const nec_sfreg[256] = "???", "???", "???", "???", "ispr", "???", "???", "idb" }; -static uint32_t pc; -static uint8_t modrm; -static uint32_t segment; -static offs_t dasm_flags; -static char modrm_string[256]; - -#define MODRM_REG1 ((modrm >> 3) & 0x7) -#define MODRM_REG2 (modrm & 0x7) +#define MODRM_REG1 ((m_modrm >> 3) & 0x7) +#define MODRM_REG2 (m_modrm & 0x7) #define MAX_LENGTH 8 -static inline uint8_t FETCH(void) +uint8_t nec_disassembler::FETCH(offs_t pc_base, offs_t &pc, const data_buffer &opcodes) { - if ((opcode_ptr - opcode_ptr_base) + 1 > MAX_LENGTH) + if ((pc - pc_base) + 1 > MAX_LENGTH) return 0xff; + u8 r = opcodes.r8(pc); pc++; - return *opcode_ptr++; -} - -#if 0 -static inline uint16_t FETCH16(void) -{ - uint16_t d; - if ((opcode_ptr - opcode_ptr_base) + 2 > MAX_LENGTH) - return 0xffff; - d = opcode_ptr[0] | (opcode_ptr[1] << 8); - opcode_ptr += 2; - pc += 2; - return d; + return r; } -#endif -static inline uint8_t FETCHD(void) +uint16_t nec_disassembler::FETCH16(offs_t pc_base, offs_t &pc, const data_buffer &opcodes) { - if ((opcode_ptr - opcode_ptr_base) + 1 > MAX_LENGTH) + if ((pc - pc_base) + 1 > MAX_LENGTH) return 0xff; - pc++; - return *opcode_ptr++; -} - -static inline uint16_t FETCHD16(void) -{ - uint16_t d; - if ((opcode_ptr - opcode_ptr_base) + 2 > MAX_LENGTH) - return 0xffff; - d = opcode_ptr[0] | (opcode_ptr[1] << 8); - opcode_ptr += 2; + u16 r = opcodes.r16(pc); pc += 2; - return d; + return r; } -static char *hexstring(uint32_t value, int digits) +std::string nec_disassembler::hexstring(uint32_t value, int digits) { - static char buffer[20]; - buffer[0] = '0'; + std::string buffer; if (digits) - sprintf(&buffer[1], "%0*Xh", digits, value); + buffer = string_format("%0*Xh", digits, value); else - sprintf(&buffer[1], "%Xh", value); - return (buffer[1] >= '0' && buffer[1] <= '9') ? &buffer[1] : &buffer[0]; + buffer = string_format("%Xh", value); + return buffer[0] > '9' ? '0' + buffer : buffer; } -static char *shexstring(uint32_t value, int digits, bool always) +std::string nec_disassembler::shexstring(uint32_t value, int digits, bool always) { - static char buffer[20]; if (value >= 0x80000000) - sprintf(buffer, "-%s", hexstring(-value, digits)); + return '-' + hexstring(-value, digits); else if (always) - sprintf(buffer, "+%s", hexstring(value, digits)); + return '+' + hexstring(value, digits); else return hexstring(value, digits); - return buffer; } -static void handle_modrm(char* s) +void nec_disassembler::handle_modrm(offs_t pc_base, offs_t &pc, const data_buffer ¶ms) { - int8_t disp8; - int16_t disp16; - uint8_t mod, rm; + m_modrm_string = ""; - modrm = FETCHD(); - mod = (modrm >> 6) & 0x3; - rm = (modrm & 0x7); + m_modrm = FETCH(pc_base, pc, params); + u8 mod = (m_modrm >> 6) & 0x3; + u8 rm = (m_modrm & 0x7); - if( modrm >= 0xc0 ) + if( m_modrm >= 0xc0 ) return; - switch(segment) + switch(m_segment) { - case SEG_PS: s += sprintf( s, "ps:" ); break; - case SEG_DS0: s += sprintf( s, "ds0:" ); break; - case SEG_DS1: s += sprintf( s, "ds1:" ); break; - case SEG_SS: s += sprintf( s, "ss:" ); break; + case SEG_PS: m_modrm_string += "ps:"; break; + case SEG_DS0: m_modrm_string += "ds0:"; break; + case SEG_DS1: m_modrm_string += "ds1:"; break; + case SEG_SS: m_modrm_string += "ss:"; break; } - s += sprintf( s, "[" ); + m_modrm_string += '['; switch( rm ) { - case 0: s += sprintf( s, "bw+ix" ); break; - case 1: s += sprintf( s, "bw+iy" ); break; - case 2: s += sprintf( s, "bp+ix" ); break; - case 3: s += sprintf( s, "bp+iy" ); break; - case 4: s += sprintf( s, "ix" ); break; - case 5: s += sprintf( s, "iy" ); break; - case 6: - if( mod == 0 ) { - disp16 = FETCHD16(); - s += sprintf( s, "%s", hexstring((unsigned) (uint16_t) disp16, 0) ); - } else { - s += sprintf( s, "bp" ); - } - break; - case 7: s += sprintf( s, "bw" ); break; - } - if( mod == 1 ) { - disp8 = FETCHD(); - s += sprintf( s, "%s", shexstring((int32_t)disp8, 0, true) ); - } else if( mod == 2 ) { - disp16 = FETCHD16(); - s += sprintf( s, "%s", shexstring((int32_t)disp16, 0, true) ); + case 0: m_modrm_string += "bw+ix"; break; + case 1: m_modrm_string += "bw+iy"; break; + case 2: m_modrm_string += "bp+ix"; break; + case 3: m_modrm_string += "bp+iy"; break; + case 4: m_modrm_string += "ix"; break; + case 5: m_modrm_string += "iy"; break; + case 6: m_modrm_string += mod == 0 ? hexstring(u16(FETCH16(pc_base, pc, params)), 0) : "bp"; break; + case 7: m_modrm_string += "bw"; break; } - s += sprintf( s, "]" );} + if( mod == 1 ) + m_modrm_string += shexstring(s8(FETCH(pc_base, pc, params)), 0, true); + else if( mod == 2 ) + m_modrm_string += shexstring(s16(FETCH16(pc_base, pc, params)), 0, true); + m_modrm_string += ']'; +} -static void handle_param(std::ostream &stream, uint32_t param) +void nec_disassembler::handle_param(std::ostream &stream, uint32_t param, offs_t pc_base, offs_t &pc, const data_buffer ¶ms) { uint8_t i8; uint16_t i16; @@ -1017,76 +902,76 @@ static void handle_param(std::ostream &stream, uint32_t param) case PARAM_RM8: case PARAM_RMPTR8: - if( modrm >= 0xc0 ) { + if( m_modrm >= 0xc0 ) { util::stream_format( stream, "%s", nec_reg8[MODRM_REG2] ); } else { if (param == PARAM_RMPTR8) util::stream_format( stream, "byte ptr " ); - util::stream_format( stream, "%s", modrm_string ); + util::stream_format( stream, "%s", m_modrm_string ); } break; case PARAM_RM16: case PARAM_RMPTR16: - if( modrm >= 0xc0 ) { + if( m_modrm >= 0xc0 ) { util::stream_format( stream, "%s", nec_reg[MODRM_REG2] ); } else { if (param == PARAM_RMPTR16) util::stream_format( stream, "word ptr " ); - util::stream_format( stream, "%s", modrm_string ); + util::stream_format( stream, "%s", m_modrm_string ); } break; case PARAM_I3: - i8 = FETCHD(); + i8 = FETCH(pc_base, pc, params); util::stream_format( stream, "%d", i8 & 0x07 ); break; case PARAM_I4: - i8 = FETCHD(); + i8 = FETCH(pc_base, pc, params); util::stream_format( stream, "%d", i8 & 0x0f ); break; case PARAM_I8: - i8 = FETCHD(); + i8 = FETCH(pc_base, pc, params); util::stream_format( stream, "%s", shexstring((int8_t)i8, 0, false) ); break; case PARAM_I16: - i16 = FETCHD16(); + i16 = FETCH16(pc_base, pc, params); util::stream_format( stream, "%s", shexstring((int16_t)i16, 0, false) ); break; case PARAM_UI8: - i8 = FETCHD(); + i8 = FETCH(pc_base, pc, params); util::stream_format( stream, "%s", shexstring((uint8_t)i8, 0, false) ); break; case PARAM_IMM: - i16 = FETCHD16(); + i16 = FETCH16(pc_base, pc, params); util::stream_format( stream, "%s", hexstring(i16, 0) ); break; case PARAM_ADDR: - addr = FETCHD16(); - ptr = FETCHD16(); + addr = FETCH16(pc_base, pc, params); + ptr = FETCH16(pc_base, pc, params); util::stream_format( stream, "%s:", hexstring(ptr, 4) ); util::stream_format( stream, "%s", hexstring(addr, 0) ); break; case PARAM_REL16: /* make sure to keep the relative offset within the segment */ - d16 = FETCHD16(); + d16 = FETCH16(pc_base, pc, params); util::stream_format( stream, "%s", hexstring((pc & 0xFFFF0000) | ((pc + d16) & 0x0000FFFF), 0) ); break; case PARAM_REL8: - d8 = FETCHD(); + d8 = FETCH(pc_base, pc, params); util::stream_format( stream, "%s", hexstring(pc + d8, 0) ); break; case PARAM_MEM_OFFS: - switch(segment) + switch(m_segment) { case SEG_PS: util::stream_format( stream, "ps:" ); break; case SEG_DS0: util::stream_format( stream, "ds0:" ); break; @@ -1094,7 +979,7 @@ static void handle_param(std::ostream &stream, uint32_t param) case SEG_SS: util::stream_format( stream, "ss:" ); break; } - i16 = FETCHD16(); + i16 = FETCH16(pc_base, pc, params); util::stream_format( stream, "[%s]", hexstring(i16, 0) ); break; @@ -1103,7 +988,7 @@ static void handle_param(std::ostream &stream, uint32_t param) break; case PARAM_SFREG: - i8 = FETCHD(); + i8 = FETCH(pc_base, pc, params); util::stream_format( stream, "%s", nec_sfreg[i8] ); break; @@ -1131,7 +1016,7 @@ static void handle_param(std::ostream &stream, uint32_t param) } } -static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) +void nec_disassembler::handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2, offs_t pc_base, offs_t &pc, const data_buffer ¶ms) { switch (op1 & 0x7) { @@ -1140,18 +1025,17 @@ static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) if (op2 < 0xc0) { pc--; // adjust fetch pointer, so modrm byte read again - opcode_ptr--; - handle_modrm( modrm_string ); + handle_modrm( pc_base, pc, params ); switch ((op2 >> 3) & 0x7) { - case 0: util::stream_format(stream, "fadd dword ptr %s", modrm_string); break; - case 1: util::stream_format(stream, "fmul dword ptr %s", modrm_string); break; - case 2: util::stream_format(stream, "fcom dword ptr %s", modrm_string); break; - case 3: util::stream_format(stream, "fcomp dword ptr %s", modrm_string); break; - case 4: util::stream_format(stream, "fsub dword ptr %s", modrm_string); break; - case 5: util::stream_format(stream, "fsubr dword ptr %s", modrm_string); break; - case 6: util::stream_format(stream, "fdiv dword ptr %s", modrm_string); break; - case 7: util::stream_format(stream, "fdivr dword ptr %s", modrm_string); break; + case 0: util::stream_format(stream, "fadd dword ptr %s", m_modrm_string); break; + case 1: util::stream_format(stream, "fmul dword ptr %s", m_modrm_string); break; + case 2: util::stream_format(stream, "fcom dword ptr %s", m_modrm_string); break; + case 3: util::stream_format(stream, "fcomp dword ptr %s", m_modrm_string); break; + case 4: util::stream_format(stream, "fsub dword ptr %s", m_modrm_string); break; + case 5: util::stream_format(stream, "fsubr dword ptr %s", m_modrm_string); break; + case 6: util::stream_format(stream, "fdiv dword ptr %s", m_modrm_string); break; + case 7: util::stream_format(stream, "fdivr dword ptr %s", m_modrm_string); break; } } else @@ -1176,18 +1060,17 @@ static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) if (op2 < 0xc0) { pc--; // adjust fetch pointer, so modrm byte read again - opcode_ptr--; - handle_modrm( modrm_string ); + handle_modrm( pc_base, pc, params ); switch ((op2 >> 3) & 0x7) { - case 0: util::stream_format(stream, "fld dword ptr %s", modrm_string); break; + case 0: util::stream_format(stream, "fld dword ptr %s", m_modrm_string); break; case 1: util::stream_format(stream, "??? (FPU)"); break; - case 2: util::stream_format(stream, "fst dword ptr %s", modrm_string); break; - case 3: util::stream_format(stream, "fstp dword ptr %s", modrm_string); break; - case 4: util::stream_format(stream, "fldenv word ptr %s", modrm_string); break; - case 5: util::stream_format(stream, "fldcw word ptr %s", modrm_string); break; - case 6: util::stream_format(stream, "fstenv word ptr %s", modrm_string); break; - case 7: util::stream_format(stream, "fstcw word ptr %s", modrm_string); break; + case 2: util::stream_format(stream, "fst dword ptr %s", m_modrm_string); break; + case 3: util::stream_format(stream, "fstp dword ptr %s", m_modrm_string); break; + case 4: util::stream_format(stream, "fldenv word ptr %s", m_modrm_string); break; + case 5: util::stream_format(stream, "fldcw word ptr %s", m_modrm_string); break; + case 6: util::stream_format(stream, "fstenv word ptr %s", m_modrm_string); break; + case 7: util::stream_format(stream, "fstcw word ptr %s", m_modrm_string); break; } } else @@ -1240,18 +1123,17 @@ static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) if (op2 < 0xc0) { pc--; // adjust fetch pointer, so modrm byte read again - opcode_ptr--; - handle_modrm( modrm_string ); + handle_modrm( pc_base, pc, params ); switch ((op2 >> 3) & 0x7) { - case 0: util::stream_format(stream, "fiadd dword ptr %s", modrm_string); break; - case 1: util::stream_format(stream, "fimul dword ptr %s", modrm_string); break; - case 2: util::stream_format(stream, "ficom dword ptr %s", modrm_string); break; - case 3: util::stream_format(stream, "ficomp dword ptr %s", modrm_string); break; - case 4: util::stream_format(stream, "fisub dword ptr %s", modrm_string); break; - case 5: util::stream_format(stream, "fisubr dword ptr %s", modrm_string); break; - case 6: util::stream_format(stream, "fidiv dword ptr %s", modrm_string); break; - case 7: util::stream_format(stream, "fidivr dword ptr %s", modrm_string); break; + case 0: util::stream_format(stream, "fiadd dword ptr %s", m_modrm_string); break; + case 1: util::stream_format(stream, "fimul dword ptr %s", m_modrm_string); break; + case 2: util::stream_format(stream, "ficom dword ptr %s", m_modrm_string); break; + case 3: util::stream_format(stream, "ficomp dword ptr %s", m_modrm_string); break; + case 4: util::stream_format(stream, "fisub dword ptr %s", m_modrm_string); break; + case 5: util::stream_format(stream, "fisubr dword ptr %s", m_modrm_string); break; + case 6: util::stream_format(stream, "fidiv dword ptr %s", m_modrm_string); break; + case 7: util::stream_format(stream, "fidivr dword ptr %s", m_modrm_string); break; } } else @@ -1282,18 +1164,17 @@ static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) if (op2 < 0xc0) { pc--; // adjust fetch pointer, so modrm byte read again - opcode_ptr--; - handle_modrm( modrm_string ); + handle_modrm( pc_base, pc, params ); switch ((op2 >> 3) & 0x7) { - case 0: util::stream_format(stream, "fild dword ptr %s", modrm_string); break; + case 0: util::stream_format(stream, "fild dword ptr %s", m_modrm_string); break; case 1: util::stream_format(stream, "??? (FPU)"); break; - case 2: util::stream_format(stream, "fist dword ptr %s", modrm_string); break; - case 3: util::stream_format(stream, "fistp dword ptr %s", modrm_string); break; + case 2: util::stream_format(stream, "fist dword ptr %s", m_modrm_string); break; + case 3: util::stream_format(stream, "fistp dword ptr %s", m_modrm_string); break; case 4: util::stream_format(stream, "??? (FPU)"); break; - case 5: util::stream_format(stream, "fld tword ptr %s", modrm_string); break; + case 5: util::stream_format(stream, "fld tword ptr %s", m_modrm_string); break; case 6: util::stream_format(stream, "??? (FPU)"); break; - case 7: util::stream_format(stream, "fstp tword ptr %s", modrm_string); break; + case 7: util::stream_format(stream, "fstp tword ptr %s", m_modrm_string); break; } } else @@ -1332,18 +1213,17 @@ static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) if (op2 < 0xc0) { pc--; // adjust fetch pointer, so modrm byte read again - opcode_ptr--; - handle_modrm( modrm_string ); + handle_modrm( pc_base, pc, params ); switch ((op2 >> 3) & 0x7) { - case 0: util::stream_format(stream, "fadd qword ptr %s", modrm_string); break; - case 1: util::stream_format(stream, "fmul qword ptr %s", modrm_string); break; - case 2: util::stream_format(stream, "fcom qword ptr %s", modrm_string); break; - case 3: util::stream_format(stream, "fcomp qword ptr %s", modrm_string); break; - case 4: util::stream_format(stream, "fsub qword ptr %s", modrm_string); break; - case 5: util::stream_format(stream, "fsubr qword ptr %s", modrm_string); break; - case 6: util::stream_format(stream, "fdiv qword ptr %s", modrm_string); break; - case 7: util::stream_format(stream, "fdivr qword ptr %s", modrm_string); break; + case 0: util::stream_format(stream, "fadd qword ptr %s", m_modrm_string); break; + case 1: util::stream_format(stream, "fmul qword ptr %s", m_modrm_string); break; + case 2: util::stream_format(stream, "fcom qword ptr %s", m_modrm_string); break; + case 3: util::stream_format(stream, "fcomp qword ptr %s", m_modrm_string); break; + case 4: util::stream_format(stream, "fsub qword ptr %s", m_modrm_string); break; + case 5: util::stream_format(stream, "fsubr qword ptr %s", m_modrm_string); break; + case 6: util::stream_format(stream, "fdiv qword ptr %s", m_modrm_string); break; + case 7: util::stream_format(stream, "fdivr qword ptr %s", m_modrm_string); break; } } else @@ -1379,18 +1259,17 @@ static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) if (op2 < 0xc0) { pc--; // adjust fetch pointer, so modrm byte read again - opcode_ptr--; - handle_modrm( modrm_string ); + handle_modrm( pc_base, pc, params ); switch ((op2 >> 3) & 0x7) { - case 0: util::stream_format(stream, "fld qword ptr %s", modrm_string); break; + case 0: util::stream_format(stream, "fld qword ptr %s", m_modrm_string); break; case 1: util::stream_format(stream, "??? (FPU)"); break; - case 2: util::stream_format(stream, "fst qword ptr %s", modrm_string); break; - case 3: util::stream_format(stream, "fstp qword ptr %s", modrm_string); break; - case 4: util::stream_format(stream, "frstor %s", modrm_string); break; + case 2: util::stream_format(stream, "fst qword ptr %s", m_modrm_string); break; + case 3: util::stream_format(stream, "fstp qword ptr %s", m_modrm_string); break; + case 4: util::stream_format(stream, "frstor %s", m_modrm_string); break; case 5: util::stream_format(stream, "??? (FPU)"); break; - case 6: util::stream_format(stream, "fsave %s", modrm_string); break; - case 7: util::stream_format(stream, "fstsw word ptr %s", modrm_string); break; + case 6: util::stream_format(stream, "fsave %s", m_modrm_string); break; + case 7: util::stream_format(stream, "fstsw word ptr %s", m_modrm_string); break; } } else @@ -1423,18 +1302,17 @@ static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) if (op2 < 0xc0) { pc--; // adjust fetch pointer, so modrm byte read again - opcode_ptr--; - handle_modrm( modrm_string ); + handle_modrm( pc_base, pc, params ); switch ((op2 >> 3) & 0x7) { - case 0: util::stream_format(stream, "fiadd word ptr %s", modrm_string); break; - case 1: util::stream_format(stream, "fimul word ptr %s", modrm_string); break; - case 2: util::stream_format(stream, "ficom word ptr %s", modrm_string); break; - case 3: util::stream_format(stream, "ficomp word ptr %s", modrm_string); break; - case 4: util::stream_format(stream, "fisub word ptr %s", modrm_string); break; - case 5: util::stream_format(stream, "fisubr word ptr %s", modrm_string); break; - case 6: util::stream_format(stream, "fidiv word ptr %s", modrm_string); break; - case 7: util::stream_format(stream, "fidivr word ptr %s", modrm_string); break; + case 0: util::stream_format(stream, "fiadd word ptr %s", m_modrm_string); break; + case 1: util::stream_format(stream, "fimul word ptr %s", m_modrm_string); break; + case 2: util::stream_format(stream, "ficom word ptr %s", m_modrm_string); break; + case 3: util::stream_format(stream, "ficomp word ptr %s", m_modrm_string); break; + case 4: util::stream_format(stream, "fisub word ptr %s", m_modrm_string); break; + case 5: util::stream_format(stream, "fisubr word ptr %s", m_modrm_string); break; + case 6: util::stream_format(stream, "fidiv word ptr %s", m_modrm_string); break; + case 7: util::stream_format(stream, "fidivr word ptr %s", m_modrm_string); break; } } else @@ -1472,18 +1350,17 @@ static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) if (op2 < 0xc0) { pc--; // adjust fetch pointer, so modrm byte read again - opcode_ptr--; - handle_modrm( modrm_string ); + handle_modrm( pc_base, pc, params ); switch ((op2 >> 3) & 0x7) { - case 0: util::stream_format(stream, "fild word ptr %s", modrm_string); break; + case 0: util::stream_format(stream, "fild word ptr %s", m_modrm_string); break; case 1: util::stream_format(stream, "??? (FPU)"); break; - case 2: util::stream_format(stream, "fist word ptr %s", modrm_string); break; - case 3: util::stream_format(stream, "fistp word ptr %s", modrm_string); break; - case 4: util::stream_format(stream, "fbld %s", modrm_string); break; - case 5: util::stream_format(stream, "fild qword ptr %s", modrm_string); break; - case 6: util::stream_format(stream, "fbstp %s", modrm_string); break; - case 7: util::stream_format(stream, "fistp qword ptr %s", modrm_string); break; + case 2: util::stream_format(stream, "fist word ptr %s", m_modrm_string); break; + case 3: util::stream_format(stream, "fistp word ptr %s", m_modrm_string); break; + case 4: util::stream_format(stream, "fbld %s", m_modrm_string); break; + case 5: util::stream_format(stream, "fild qword ptr %s", m_modrm_string); break; + case 6: util::stream_format(stream, "fbstp %s", m_modrm_string); break; + case 7: util::stream_format(stream, "fistp qword ptr %s", m_modrm_string); break; } } else @@ -1506,7 +1383,7 @@ static void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2) } } -static void decode_opcode(std::ostream &stream, const NEC_I386_OPCODE *op, uint8_t op1 ) +void nec_disassembler::decode_opcode(std::ostream &stream, const NEC_I386_OPCODE *op, uint8_t op1, offs_t pc_base, offs_t &pc, const data_buffer &opcodes, const data_buffer ¶ms) { int i; uint8_t op2; @@ -1514,63 +1391,63 @@ static void decode_opcode(std::ostream &stream, const NEC_I386_OPCODE *op, uint8 switch( op->flags ) { case TWO_BYTE: - op2 = FETCHD(); - decode_opcode( stream, &necv_opcode_table2[op2], op1 ); + op2 = FETCH(pc_base, pc, params); + decode_opcode( stream, &necv_opcode_table2[op2], op1, pc_base, pc, opcodes, params ); return; case SEG_PS: case SEG_DS0: case SEG_DS1: case SEG_SS: - segment = op->flags; - op2 = FETCH(); - if (Iconfig) op2 = Iconfig[op2]; - decode_opcode( stream, &necv_opcode_table1[op2], op1 ); + m_segment = op->flags; + op2 = FETCH(pc_base, pc, opcodes); + if (m_decryption_table) op2 = m_decryption_table[op2]; + decode_opcode( stream, &necv_opcode_table1[op2], op1, pc_base, pc, opcodes, params ); return; case PREFIX: util::stream_format( stream, "%-8s", op->mnemonic ); - op2 = FETCH(); - if (Iconfig) op2 = Iconfig[op2]; - decode_opcode( stream, &necv_opcode_table1[op2], op1 ); + op2 = FETCH(pc_base, pc, opcodes); + if (m_decryption_table) op2 = m_decryption_table[op2]; + decode_opcode( stream, &necv_opcode_table1[op2], op1, pc_base, pc, opcodes, params ); return; case GROUP: - handle_modrm( modrm_string ); + handle_modrm( pc_base, pc, params ); for( i=0; i < ARRAY_LENGTH(group_op_table); i++ ) { if( strcmp(op->mnemonic, group_op_table[i].mnemonic) == 0 ) { - decode_opcode( stream, &group_op_table[i].opcode[MODRM_REG1], op1 ); + decode_opcode( stream, &group_op_table[i].opcode[MODRM_REG1], op1, pc_base, pc, opcodes, params ); return; } } goto handle_unknown; case FPU: - op2 = FETCHD(); - handle_fpu( stream, op1, op2); + op2 = FETCH(pc_base, pc, params); + handle_fpu( stream, op1, op2, pc_base, pc, params); return; case MODRM: - handle_modrm( modrm_string ); + handle_modrm( pc_base, pc, params ); break; } util::stream_format( stream, "%-8s", op->mnemonic ); - dasm_flags = op->dasm_flags; + m_dasm_flags = op->dasm_flags; if( op->param1 != 0 ) { - handle_param(stream, op->param1); + handle_param(stream, op->param1, pc_base, pc, params); } if( op->param2 != 0 ) { util::stream_format( stream, "," ); - handle_param(stream, op->param2); + handle_param(stream, op->param2, pc_base, pc, params); } if( op->param3 != 0 ) { util::stream_format( stream, "," ); - handle_param(stream, op->param3); + handle_param(stream, op->param3, pc_base, pc, params); } return; @@ -1578,25 +1455,29 @@ handle_unknown: util::stream_format(stream, "???"); } -int necv_dasm_one(std::ostream &stream, uint32_t eip, const uint8_t *oprom, const uint8_t *decryption_table) +offs_t nec_disassembler::disassemble(std::ostream &stream, offs_t eip, const data_buffer &opcodes, const data_buffer ¶ms) { uint8_t op; - Iconfig = decryption_table; - opcode_ptr = opcode_ptr_base = oprom; - pc = eip; - dasm_flags = 0; - segment = 0; + offs_t pc = eip; + m_dasm_flags = 0; + m_segment = 0; - op = FETCH(); + op = FETCH(eip, pc, opcodes); - if (Iconfig) op = Iconfig[op]; + if (m_decryption_table) + op = m_decryption_table[op]; - decode_opcode( stream, &necv_opcode_table1[op], op ); - return (pc-eip) | dasm_flags | DASMFLAG_SUPPORTED; + decode_opcode( stream, &necv_opcode_table1[op], op, eip, pc, opcodes, params ); + return (pc-eip) | m_dasm_flags | SUPPORTED; } -CPU_DISASSEMBLE( nec ) +nec_disassembler::nec_disassembler(const u8 *decryption_table) : m_decryption_table(decryption_table) { - return necv_dasm_one(stream, pc, oprom, nullptr); } + +u32 nec_disassembler::opcode_alignment() const +{ + return 1; +} + diff --git a/src/devices/cpu/nec/necdasm.h b/src/devices/cpu/nec/necdasm.h new file mode 100644 index 00000000000..9b243ffe66f --- /dev/null +++ b/src/devices/cpu/nec/necdasm.h @@ -0,0 +1,129 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert + +// NEC disassembler interface + +#ifndef MAME_CPU_NEC_NECDASM_H +#define MAME_CPU_NEC_NECDASM_H + +#pragma once + +class nec_disassembler : public util::disasm_interface +{ +public: + nec_disassembler(const u8 *decryption_table = nullptr); + virtual ~nec_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum + { + PARAM_REG8 = 1, /* 8-bit register */ + PARAM_REG16, /* 16-bit register */ + PARAM_REG2_8, /* 8-bit register */ + PARAM_REG2_16, /* 16-bit register */ + PARAM_RM8, /* 8-bit memory or register */ + PARAM_RM16, /* 16-bit memory or register */ + PARAM_RMPTR8, /* 8-bit memory or register */ + PARAM_RMPTR16, /* 16-bit memory or register */ + PARAM_I3, /* 3-bit immediate */ + PARAM_I4, /* 4-bit immediate */ + PARAM_I8, /* 8-bit signed immediate */ + PARAM_I16, /* 16-bit signed immediate */ + PARAM_UI8, /* 8-bit unsigned immediate */ + PARAM_IMM, /* 16-bit immediate */ + PARAM_ADDR, /* 16:16 address */ + PARAM_REL8, /* 8-bit PC-relative displacement */ + PARAM_REL16, /* 16-bit PC-relative displacement */ + PARAM_MEM_OFFS, /* 16-bit mem offset */ + PARAM_SREG, /* segment register */ + PARAM_SFREG, /* V25/V35 special function register */ + PARAM_1, /* used by shift/rotate instructions */ + PARAM_AL, + PARAM_CL, + PARAM_DL, + PARAM_BL, + PARAM_AH, + PARAM_CH, + PARAM_DH, + PARAM_BH, + PARAM_AW, + PARAM_CW, + PARAM_DW, + PARAM_BW, + PARAM_SP, + PARAM_BP, + PARAM_IX, + PARAM_IY + }; + + enum + { + MODRM = 1, + GROUP, + FPU, + TWO_BYTE, + PREFIX, + SEG_PS, + SEG_DS0, + SEG_DS1, + SEG_SS + }; + + struct NEC_I386_OPCODE { + char mnemonic[32]; + uint32_t flags; + uint32_t param1; + uint32_t param2; + uint32_t param3; + offs_t dasm_flags; + }; + + struct NEC_GROUP_OP { + char mnemonic[32]; + const NEC_I386_OPCODE *opcode; + }; + + static const NEC_I386_OPCODE necv_opcode_table1[256]; + static const NEC_I386_OPCODE necv_opcode_table2[256]; + static const NEC_I386_OPCODE immb_table[8]; + static const NEC_I386_OPCODE immw_table[8]; + static const NEC_I386_OPCODE immws_table[8]; + static const NEC_I386_OPCODE shiftbi_table[8]; + static const NEC_I386_OPCODE shiftwi_table[8]; + static const NEC_I386_OPCODE shiftb_table[8]; + static const NEC_I386_OPCODE shiftw_table[8]; + static const NEC_I386_OPCODE shiftbv_table[8]; + static const NEC_I386_OPCODE shiftwv_table[8]; + static const NEC_I386_OPCODE group1b_table[8]; + static const NEC_I386_OPCODE group1w_table[8]; + static const NEC_I386_OPCODE group2b_table[8]; + static const NEC_I386_OPCODE group2w_table[8]; + static const NEC_GROUP_OP group_op_table[]; + static const char *const nec_reg[8]; + static const char *const nec_reg8[8]; + static const char *const nec_sreg[8]; + static const char *const nec_sfreg[256]; + + const u8 *m_decryption_table; + + u8 m_modrm; + u32 m_segment; + offs_t m_dasm_flags; + std::string m_modrm_string; + + inline u8 FETCH(offs_t pc_base, offs_t &pc, const data_buffer &opcodes); + inline u16 FETCH16(offs_t pc_base, offs_t &pc, const data_buffer &opcodes); + std::string hexstring(uint32_t value, int digits); + std::string shexstring(uint32_t value, int digits, bool always); + void handle_modrm(offs_t pc_base, offs_t &pc, const data_buffer ¶ms); + void handle_param(std::ostream &stream, uint32_t param, offs_t pc_base, offs_t &pc, const data_buffer ¶ms); + void handle_fpu(std::ostream &stream, uint8_t op1, uint8_t op2, offs_t pc_base, offs_t &pc, const data_buffer ¶ms); + + void decode_opcode(std::ostream &stream, const NEC_I386_OPCODE *op, uint8_t op1, offs_t pc_base, offs_t &pc, const data_buffer &opcodes, const data_buffer ¶ms); +}; + + +#endif diff --git a/src/devices/cpu/nec/necea.h b/src/devices/cpu/nec/necea.h index 1a20c0cdf54..a8b42329233 100644 --- a/src/devices/cpu/nec/necea.h +++ b/src/devices/cpu/nec/necea.h @@ -7,26 +7,26 @@ uint32_t nec_common_device::EA_002() { m_EO=Wreg(BP)+Wreg(IX); m_EA=DefaultBase( uint32_t nec_common_device::EA_003() { m_EO=Wreg(BP)+Wreg(IY); m_EA=DefaultBase(SS)+m_EO; return m_EA; } uint32_t nec_common_device::EA_004() { m_EO=Wreg(IX); m_EA=DefaultBase(DS0)+m_EO; return m_EA; } uint32_t nec_common_device::EA_005() { m_EO=Wreg(IY); m_EA=DefaultBase(DS0)+m_EO; return m_EA; } -uint32_t nec_common_device::EA_006() { m_EO=FETCH(); m_EO+=FETCH()<<8; m_EA=DefaultBase(DS0)+m_EO; return m_EA; } +uint32_t nec_common_device::EA_006() { m_EO=fetch(); m_EO+=fetch()<<8; m_EA=DefaultBase(DS0)+m_EO; return m_EA; } uint32_t nec_common_device::EA_007() { m_EO=Wreg(BW); m_EA=DefaultBase(DS0)+m_EO; return m_EA; } -uint32_t nec_common_device::EA_100() { m_EO=(Wreg(BW)+Wreg(IX)+(int8_t)FETCH()); m_EA=DefaultBase(DS0)+m_EO; return m_EA; } -uint32_t nec_common_device::EA_101() { m_EO=(Wreg(BW)+Wreg(IY)+(int8_t)FETCH()); m_EA=DefaultBase(DS0)+m_EO; return m_EA; } -uint32_t nec_common_device::EA_102() { m_EO=(Wreg(BP)+Wreg(IX)+(int8_t)FETCH()); m_EA=DefaultBase(SS)+m_EO; return m_EA; } -uint32_t nec_common_device::EA_103() { m_EO=(Wreg(BP)+Wreg(IY)+(int8_t)FETCH()); m_EA=DefaultBase(SS)+m_EO; return m_EA; } -uint32_t nec_common_device::EA_104() { m_EO=(Wreg(IX)+(int8_t)FETCH()); m_EA=DefaultBase(DS0)+m_EO; return m_EA; } -uint32_t nec_common_device::EA_105() { m_EO=(Wreg(IY)+(int8_t)FETCH()); m_EA=DefaultBase(DS0)+m_EO; return m_EA; } -uint32_t nec_common_device::EA_106() { m_EO=(Wreg(BP)+(int8_t)FETCH()); m_EA=DefaultBase(SS)+m_EO; return m_EA; } -uint32_t nec_common_device::EA_107() { m_EO=(Wreg(BW)+(int8_t)FETCH()); m_EA=DefaultBase(DS0)+m_EO; return m_EA; } +uint32_t nec_common_device::EA_100() { m_EO=(Wreg(BW)+Wreg(IX)+(int8_t)fetch()); m_EA=DefaultBase(DS0)+m_EO; return m_EA; } +uint32_t nec_common_device::EA_101() { m_EO=(Wreg(BW)+Wreg(IY)+(int8_t)fetch()); m_EA=DefaultBase(DS0)+m_EO; return m_EA; } +uint32_t nec_common_device::EA_102() { m_EO=(Wreg(BP)+Wreg(IX)+(int8_t)fetch()); m_EA=DefaultBase(SS)+m_EO; return m_EA; } +uint32_t nec_common_device::EA_103() { m_EO=(Wreg(BP)+Wreg(IY)+(int8_t)fetch()); m_EA=DefaultBase(SS)+m_EO; return m_EA; } +uint32_t nec_common_device::EA_104() { m_EO=(Wreg(IX)+(int8_t)fetch()); m_EA=DefaultBase(DS0)+m_EO; return m_EA; } +uint32_t nec_common_device::EA_105() { m_EO=(Wreg(IY)+(int8_t)fetch()); m_EA=DefaultBase(DS0)+m_EO; return m_EA; } +uint32_t nec_common_device::EA_106() { m_EO=(Wreg(BP)+(int8_t)fetch()); m_EA=DefaultBase(SS)+m_EO; return m_EA; } +uint32_t nec_common_device::EA_107() { m_EO=(Wreg(BW)+(int8_t)fetch()); m_EA=DefaultBase(DS0)+m_EO; return m_EA; } -uint32_t nec_common_device::EA_200() { m_E16=FETCH(); m_E16+=FETCH()<<8; m_EO=Wreg(BW)+Wreg(IX)+(int16_t)m_E16; m_EA=DefaultBase(DS0)+m_EO; return m_EA; } -uint32_t nec_common_device::EA_201() { m_E16=FETCH(); m_E16+=FETCH()<<8; m_EO=Wreg(BW)+Wreg(IY)+(int16_t)m_E16; m_EA=DefaultBase(DS0)+m_EO; return m_EA; } -uint32_t nec_common_device::EA_202() { m_E16=FETCH(); m_E16+=FETCH()<<8; m_EO=Wreg(BP)+Wreg(IX)+(int16_t)m_E16; m_EA=DefaultBase(SS)+m_EO; return m_EA; } -uint32_t nec_common_device::EA_203() { m_E16=FETCH(); m_E16+=FETCH()<<8; m_EO=Wreg(BP)+Wreg(IY)+(int16_t)m_E16; m_EA=DefaultBase(SS)+m_EO; return m_EA; } -uint32_t nec_common_device::EA_204() { m_E16=FETCH(); m_E16+=FETCH()<<8; m_EO=Wreg(IX)+(int16_t)m_E16; m_EA=DefaultBase(DS0)+m_EO; return m_EA; } -uint32_t nec_common_device::EA_205() { m_E16=FETCH(); m_E16+=FETCH()<<8; m_EO=Wreg(IY)+(int16_t)m_E16; m_EA=DefaultBase(DS0)+m_EO; return m_EA; } -uint32_t nec_common_device::EA_206() { m_E16=FETCH(); m_E16+=FETCH()<<8; m_EO=Wreg(BP)+(int16_t)m_E16; m_EA=DefaultBase(SS)+m_EO; return m_EA; } -uint32_t nec_common_device::EA_207() { m_E16=FETCH(); m_E16+=FETCH()<<8; m_EO=Wreg(BW)+(int16_t)m_E16; m_EA=DefaultBase(DS0)+m_EO; return m_EA; } +uint32_t nec_common_device::EA_200() { m_E16=fetch(); m_E16+=fetch()<<8; m_EO=Wreg(BW)+Wreg(IX)+(int16_t)m_E16; m_EA=DefaultBase(DS0)+m_EO; return m_EA; } +uint32_t nec_common_device::EA_201() { m_E16=fetch(); m_E16+=fetch()<<8; m_EO=Wreg(BW)+Wreg(IY)+(int16_t)m_E16; m_EA=DefaultBase(DS0)+m_EO; return m_EA; } +uint32_t nec_common_device::EA_202() { m_E16=fetch(); m_E16+=fetch()<<8; m_EO=Wreg(BP)+Wreg(IX)+(int16_t)m_E16; m_EA=DefaultBase(SS)+m_EO; return m_EA; } +uint32_t nec_common_device::EA_203() { m_E16=fetch(); m_E16+=fetch()<<8; m_EO=Wreg(BP)+Wreg(IY)+(int16_t)m_E16; m_EA=DefaultBase(SS)+m_EO; return m_EA; } +uint32_t nec_common_device::EA_204() { m_E16=fetch(); m_E16+=fetch()<<8; m_EO=Wreg(IX)+(int16_t)m_E16; m_EA=DefaultBase(DS0)+m_EO; return m_EA; } +uint32_t nec_common_device::EA_205() { m_E16=fetch(); m_E16+=fetch()<<8; m_EO=Wreg(IY)+(int16_t)m_E16; m_EA=DefaultBase(DS0)+m_EO; return m_EA; } +uint32_t nec_common_device::EA_206() { m_E16=fetch(); m_E16+=fetch()<<8; m_EO=Wreg(BP)+(int16_t)m_E16; m_EA=DefaultBase(SS)+m_EO; return m_EA; } +uint32_t nec_common_device::EA_207() { m_E16=fetch(); m_E16+=fetch()<<8; m_EO=Wreg(BW)+(int16_t)m_E16; m_EA=DefaultBase(DS0)+m_EO; return m_EA; } const nec_common_device::nec_eahandler nec_common_device::s_GetEA[192]= { diff --git a/src/devices/cpu/nec/necinstr.hxx b/src/devices/cpu/nec/necinstr.hxx index 98863c4c431..0499c49c65b 100644 --- a/src/devices/cpu/nec/necinstr.hxx +++ b/src/devices/cpu/nec/necinstr.hxx @@ -19,7 +19,7 @@ OP( 0x0c, i_or_ald8 ) { DEF_ald8; ORB; Breg(AL)=dst; CLKS(4,4,2); OP( 0x0d, i_or_axd16 ) { DEF_axd16; ORW; Wreg(AW)=dst; CLKS(4,4,2); } OP( 0x0e, i_push_cs ) { PUSH(Sreg(PS)); CLKS(12,8,3); } OP( 0x0f, i_pre_nec ) { uint32_t ModRM, tmp, tmp2; - switch (FETCH()) { + switch (fetch()) { case 0x10 : BITOP_BYTE; CLKS(3,3,4); tmp2 = Breg(CL) & 0x7; m_ZeroVal = (tmp & (1<>8)&0xf); tmp &= 0xff; PutbackRMByte(ModRM,tmp); CLKM(13,13,9,28,28,15); break; - case 0x2a : ModRM = FETCH(); tmp = GetRMByte(ModRM); tmp2 = (Breg(AL) & 0xf)<<4; Breg(AL) = (Breg(AL) & 0xf0) | (tmp&0xf); tmp = tmp2 | (tmp>>4); PutbackRMByte(ModRM,tmp); CLKM(17,17,13,32,32,19); break; - case 0x31 : ModRM = FETCH(); ModRM=0; logerror("%06x: Unimplemented bitfield INS\n",PC()); break; - case 0x33 : ModRM = FETCH(); ModRM=0; logerror("%06x: Unimplemented bitfield EXT\n",PC()); break; - case 0xe0 : ModRM = FETCH(); ModRM=0; logerror("%06x: V33 unimplemented BRKXA (break to expansion address)\n",PC()); break; - case 0xf0 : ModRM = FETCH(); ModRM=0; logerror("%06x: V33 unimplemented RETXA (return from expansion address)\n",PC()); break; - case 0xff : ModRM = FETCH(); ModRM=0; logerror("%06x: unimplemented BRKEM (break to 8080 emulation mode)\n",PC()); break; + case 0x28 : ModRM = fetch(); tmp = GetRMByte(ModRM); tmp <<= 4; tmp |= Breg(AL) & 0xf; Breg(AL) = (Breg(AL) & 0xf0) | ((tmp>>8)&0xf); tmp &= 0xff; PutbackRMByte(ModRM,tmp); CLKM(13,13,9,28,28,15); break; + case 0x2a : ModRM = fetch(); tmp = GetRMByte(ModRM); tmp2 = (Breg(AL) & 0xf)<<4; Breg(AL) = (Breg(AL) & 0xf0) | (tmp&0xf); tmp = tmp2 | (tmp>>4); PutbackRMByte(ModRM,tmp); CLKM(17,17,13,32,32,19); break; + case 0x31 : ModRM = fetch(); ModRM=0; logerror("%06x: Unimplemented bitfield INS\n",PC()); break; + case 0x33 : ModRM = fetch(); ModRM=0; logerror("%06x: Unimplemented bitfield EXT\n",PC()); break; + case 0xe0 : ModRM = fetch(); ModRM=0; logerror("%06x: V33 unimplemented BRKXA (break to expansion address)\n",PC()); break; + case 0xf0 : ModRM = fetch(); ModRM=0; logerror("%06x: V33 unimplemented RETXA (return from expansion address)\n",PC()); break; + case 0xff : ModRM = fetch(); ModRM=0; logerror("%06x: unimplemented BRKEM (break to 8080 emulation mode)\n",PC()); break; default: logerror("%06x: Unknown V20 instruction\n",PC()); break; } } @@ -234,10 +234,10 @@ OP( 0x65, i_repc ) { uint32_t next = fetchop(); uint16_t c = Wreg(CW); m_seg_prefix=false; } -OP( 0x68, i_push_d16 ) { uint32_t tmp; tmp = FETCHWORD(); PUSH(tmp); CLKW(12,12,5,12,8,5,Wreg(SP)); } -OP( 0x69, i_imul_d16 ) { uint32_t tmp; DEF_r16w; tmp = FETCHWORD(); dst = (int32_t)((int16_t)src)*(int32_t)((int16_t)tmp); m_CarryVal = m_OverVal = (((int32_t)dst) >> 15 != 0) && (((int32_t)dst) >> 15 != -1); RegWord(ModRM)=(WORD)dst; m_icount-=(ModRM >=0xc0 )?38:47;} -OP( 0x6a, i_push_d8 ) { uint32_t tmp = (WORD)((int16_t)((int8_t)FETCH())); PUSH(tmp); CLKW(11,11,5,11,7,3,Wreg(SP)); } -OP( 0x6b, i_imul_d8 ) { uint32_t src2; DEF_r16w; src2= (WORD)((int16_t)((int8_t)FETCH())); dst = (int32_t)((int16_t)src)*(int32_t)((int16_t)src2); m_CarryVal = m_OverVal = (((int32_t)dst) >> 15 != 0) && (((int32_t)dst) >> 15 != -1); RegWord(ModRM)=(WORD)dst; m_icount-=(ModRM >=0xc0 )?31:39; } +OP( 0x68, i_push_d16 ) { uint32_t tmp; tmp = fetchword(); PUSH(tmp); CLKW(12,12,5,12,8,5,Wreg(SP)); } +OP( 0x69, i_imul_d16 ) { uint32_t tmp; DEF_r16w; tmp = fetchword(); dst = (int32_t)((int16_t)src)*(int32_t)((int16_t)tmp); m_CarryVal = m_OverVal = (((int32_t)dst) >> 15 != 0) && (((int32_t)dst) >> 15 != -1); RegWord(ModRM)=(WORD)dst; m_icount-=(ModRM >=0xc0 )?38:47;} +OP( 0x6a, i_push_d8 ) { uint32_t tmp = (WORD)((int16_t)((int8_t)fetch())); PUSH(tmp); CLKW(11,11,5,11,7,3,Wreg(SP)); } +OP( 0x6b, i_imul_d8 ) { uint32_t src2; DEF_r16w; src2= (WORD)((int16_t)((int8_t)fetch())); dst = (int32_t)((int16_t)src)*(int32_t)((int16_t)src2); m_CarryVal = m_OverVal = (((int32_t)dst) >> 15 != 0) && (((int32_t)dst) >> 15 != -1); RegWord(ModRM)=(WORD)dst; m_icount-=(ModRM >=0xc0 )?31:39; } OP( 0x6c, i_insb ) { PutMemB(DS1,Wreg(IY),read_port_byte(Wreg(DW))); Wreg(IY)+= -2 * m_DF + 1; CLK(8); } OP( 0x6d, i_insw ) { PutMemW(DS1,Wreg(IY),read_port_word(Wreg(DW))); Wreg(IY)+= -4 * m_DF + 2; CLKS(18,10,8); } OP( 0x6e, i_outsb ) { write_port_byte(Wreg(DW),GetMemB(DS0,Wreg(IX))); Wreg(IX)+= -2 * m_DF + 1; CLK(8); } @@ -260,7 +260,7 @@ OP( 0x7d, i_jnl ) { JMP((ZF)||(SF==OF)); CLKS(4,4,3); } OP( 0x7e, i_jle ) { JMP((ZF)||(SF!=OF)); CLKS(4,4,3); } OP( 0x7f, i_jnle ) { JMP((SF==OF)&&(!ZF)); CLKS(4,4,3); } -OP( 0x80, i_80pre ) { uint32_t dst, src; GetModRM; dst = GetRMByte(ModRM); src = FETCH(); +OP( 0x80, i_80pre ) { uint32_t dst, src; GetModRM; dst = GetRMByte(ModRM); src = fetch(); if (ModRM >=0xc0 ) CLKS(4,4,2) else if ((ModRM & 0x38)==0x38) CLKS(13,13,6) else CLKS(18,18,7) switch (ModRM & 0x38) { case 0x00: ADDB; PutbackRMByte(ModRM,dst); break; @@ -274,7 +274,7 @@ OP( 0x80, i_80pre ) { uint32_t dst, src; GetModRM; dst = GetRMByte(ModRM); src } } -OP( 0x81, i_81pre ) { uint32_t dst, src; GetModRM; dst = GetRMWord(ModRM); src = FETCH(); src+= (FETCH() << 8); +OP( 0x81, i_81pre ) { uint32_t dst, src; GetModRM; dst = GetRMWord(ModRM); src = fetch(); src+= (fetch() << 8); if (ModRM >=0xc0 ) CLKS(4,4,2) else if ((ModRM & 0x38)==0x38) CLKW(17,17,8,17,13,6,m_EA) else CLKW(26,26,11,26,18,7,m_EA) switch (ModRM & 0x38) { case 0x00: ADDW; PutbackRMWord(ModRM,dst); break; @@ -288,7 +288,7 @@ OP( 0x81, i_81pre ) { uint32_t dst, src; GetModRM; dst = GetRMWord(ModRM); src } } -OP( 0x82, i_82pre ) { uint32_t dst, src; GetModRM; dst = GetRMByte(ModRM); src = (BYTE)((int8_t)FETCH()); +OP( 0x82, i_82pre ) { uint32_t dst, src; GetModRM; dst = GetRMByte(ModRM); src = (BYTE)((int8_t)fetch()); if (ModRM >=0xc0 ) CLKS(4,4,2) else if ((ModRM & 0x38)==0x38) CLKS(13,13,6) else CLKS(18,18,7) switch (ModRM & 0x38) { case 0x00: ADDB; PutbackRMByte(ModRM,dst); break; @@ -302,7 +302,7 @@ OP( 0x82, i_82pre ) { uint32_t dst, src; GetModRM; dst = GetRMByte(ModRM); src } } -OP( 0x83, i_83pre ) { uint32_t dst, src; GetModRM; dst = GetRMWord(ModRM); src = (WORD)((int16_t)((int8_t)FETCH())); +OP( 0x83, i_83pre ) { uint32_t dst, src; GetModRM; dst = GetRMWord(ModRM); src = (WORD)((int16_t)((int8_t)fetch())); if (ModRM >=0xc0 ) CLKS(4,4,2) else if ((ModRM & 0x38)==0x38) CLKW(17,17,8,17,13,6,m_EA) else CLKW(26,26,11,26,18,7,m_EA) switch (ModRM & 0x38) { case 0x00: ADDW; PutbackRMWord(ModRM,dst); break; @@ -334,7 +334,7 @@ OP( 0x8c, i_mov_wsreg ) { GetModRM; default: logerror("%06x: MOV Sreg - Invalid register\n",PC()); } } -OP( 0x8d, i_lea ) { uint16_t ModRM = FETCH(); (void)(this->*s_GetEA[ModRM])(); RegWord(ModRM)=m_EO; CLKS(4,4,2); } +OP( 0x8d, i_lea ) { uint16_t ModRM = fetch(); (void)(this->*s_GetEA[ModRM])(); RegWord(ModRM)=m_EO; CLKS(4,4,2); } OP( 0x8e, i_mov_sregw ) { uint16_t src; GetModRM; src = GetRMWord(ModRM); CLKR(15,15,7,15,11,5,2,m_EA); switch (ModRM & 0x38) { case 0x00: Sreg(DS1) = src; break; /* mov es,ew */ @@ -357,17 +357,17 @@ OP( 0x97, i_xchg_axdi ) { XchgAWReg(IY); CLK(3); } OP( 0x98, i_cbw ) { Breg(AH) = (Breg(AL) & 0x80) ? 0xff : 0; CLK(2); } OP( 0x99, i_cwd ) { Wreg(DW) = (Breg(AH) & 0x80) ? 0xffff : 0; CLK(4); } -OP( 0x9a, i_call_far ) { uint32_t tmp, tmp2; tmp = FETCHWORD(); tmp2 = FETCHWORD(); PUSH(Sreg(PS)); PUSH(m_ip); m_ip = (WORD)tmp; Sreg(PS) = (WORD)tmp2; CHANGE_PC; CLKW(29,29,13,29,21,9,Wreg(SP)); } +OP( 0x9a, i_call_far ) { uint32_t tmp, tmp2; tmp = fetchword(); tmp2 = fetchword(); PUSH(Sreg(PS)); PUSH(m_ip); m_ip = (WORD)tmp; Sreg(PS) = (WORD)tmp2; CHANGE_PC; CLKW(29,29,13,29,21,9,Wreg(SP)); } OP( 0x9b, i_wait ) { if (!m_poll_state) m_ip--; CLK(5); } OP( 0x9c, i_pushf ) { uint16_t tmp = CompressFlags(); PUSH( tmp ); CLKS(12,8,3); } OP( 0x9d, i_popf ) { uint32_t tmp; POP(tmp); ExpandFlags(tmp); CLKS(12,8,5); if (m_TF) nec_trap(); } OP( 0x9e, i_sahf ) { uint32_t tmp = (CompressFlags() & 0xff00) | (Breg(AH) & 0xd5); ExpandFlags(tmp); CLKS(3,3,2); } OP( 0x9f, i_lahf ) { Breg(AH) = CompressFlags() & 0xff; CLKS(3,3,2); } -OP( 0xa0, i_mov_aldisp ) { uint32_t addr; addr = FETCHWORD(); Breg(AL) = GetMemB(DS0, addr); CLKS(10,10,5); } -OP( 0xa1, i_mov_axdisp ) { uint32_t addr; addr = FETCHWORD(); Wreg(AW) = GetMemW(DS0, addr); CLKW(14,14,7,14,10,5,addr); } -OP( 0xa2, i_mov_dispal ) { uint32_t addr; addr = FETCHWORD(); PutMemB(DS0, addr, Breg(AL)); CLKS(9,9,3); } -OP( 0xa3, i_mov_dispax ) { uint32_t addr; addr = FETCHWORD(); PutMemW(DS0, addr, Wreg(AW)); CLKW(13,13,5,13,9,3,addr); } +OP( 0xa0, i_mov_aldisp ) { uint32_t addr; addr = fetchword(); Breg(AL) = GetMemB(DS0, addr); CLKS(10,10,5); } +OP( 0xa1, i_mov_axdisp ) { uint32_t addr; addr = fetchword(); Wreg(AW) = GetMemW(DS0, addr); CLKW(14,14,7,14,10,5,addr); } +OP( 0xa2, i_mov_dispal ) { uint32_t addr; addr = fetchword(); PutMemB(DS0, addr, Breg(AL)); CLKS(9,9,3); } +OP( 0xa3, i_mov_dispax ) { uint32_t addr; addr = fetchword(); PutMemW(DS0, addr, Wreg(AW)); CLKW(13,13,5,13,9,3,addr); } OP( 0xa4, i_movsb ) { uint32_t tmp = GetMemB(DS0,Wreg(IX)); PutMemB(DS1,Wreg(IY), tmp); Wreg(IY) += -2 * m_DF + 1; Wreg(IX) += -2 * m_DF + 1; CLKS(8,8,6); } OP( 0xa5, i_movsw ) { uint32_t tmp = GetMemW(DS0,Wreg(IX)); PutMemW(DS1,Wreg(IY), tmp); Wreg(IY) += -4 * m_DF + 2; Wreg(IX) += -4 * m_DF + 2; CLKS(16,16,10); } OP( 0xa6, i_cmpsb ) { uint32_t src = GetMemB(DS1, Wreg(IY)); uint32_t dst = GetMemB(DS0, Wreg(IX)); SUBB; Wreg(IY) += -2 * m_DF + 1; Wreg(IX) += -2 * m_DF + 1; CLKS(14,14,14); } @@ -382,28 +382,28 @@ OP( 0xad, i_lodsw ) { Wreg(AW) = GetMemW(DS0,Wreg(IX)); Wreg(IX) += -4 * m_ OP( 0xae, i_scasb ) { uint32_t src = GetMemB(DS1, Wreg(IY)); uint32_t dst = Breg(AL); SUBB; Wreg(IY) += -2 * m_DF + 1; CLKS(4,4,3); } OP( 0xaf, i_scasw ) { uint32_t src = GetMemW(DS1, Wreg(IY)); uint32_t dst = Wreg(AW); SUBW; Wreg(IY) += -4 * m_DF + 2; CLKW(8,8,5,8,4,3,Wreg(IY)); } -OP( 0xb0, i_mov_ald8 ) { Breg(AL) = FETCH(); CLKS(4,4,2); } -OP( 0xb1, i_mov_cld8 ) { Breg(CL) = FETCH(); CLKS(4,4,2); } -OP( 0xb2, i_mov_dld8 ) { Breg(DL) = FETCH(); CLKS(4,4,2); } -OP( 0xb3, i_mov_bld8 ) { Breg(BL) = FETCH(); CLKS(4,4,2); } -OP( 0xb4, i_mov_ahd8 ) { Breg(AH) = FETCH(); CLKS(4,4,2); } -OP( 0xb5, i_mov_chd8 ) { Breg(CH) = FETCH(); CLKS(4,4,2); } -OP( 0xb6, i_mov_dhd8 ) { Breg(DH) = FETCH(); CLKS(4,4,2); } -OP( 0xb7, i_mov_bhd8 ) { Breg(BH) = FETCH(); CLKS(4,4,2); } - -OP( 0xb8, i_mov_axd16 ) { Breg(AL) = FETCH(); Breg(AH) = FETCH(); CLKS(4,4,2); } -OP( 0xb9, i_mov_cxd16 ) { Breg(CL) = FETCH(); Breg(CH) = FETCH(); CLKS(4,4,2); } -OP( 0xba, i_mov_dxd16 ) { Breg(DL) = FETCH(); Breg(DH) = FETCH(); CLKS(4,4,2); } -OP( 0xbb, i_mov_bxd16 ) { Breg(BL) = FETCH(); Breg(BH) = FETCH(); CLKS(4,4,2); } -OP( 0xbc, i_mov_spd16 ) { Wreg(SP) = FETCHWORD(); CLKS(4,4,2); } -OP( 0xbd, i_mov_bpd16 ) { Wreg(BP) = FETCHWORD(); CLKS(4,4,2); } -OP( 0xbe, i_mov_sid16 ) { Wreg(IX) = FETCHWORD(); CLKS(4,4,2); } -OP( 0xbf, i_mov_did16 ) { Wreg(IY) = FETCHWORD(); CLKS(4,4,2); } +OP( 0xb0, i_mov_ald8 ) { Breg(AL) = fetch(); CLKS(4,4,2); } +OP( 0xb1, i_mov_cld8 ) { Breg(CL) = fetch(); CLKS(4,4,2); } +OP( 0xb2, i_mov_dld8 ) { Breg(DL) = fetch(); CLKS(4,4,2); } +OP( 0xb3, i_mov_bld8 ) { Breg(BL) = fetch(); CLKS(4,4,2); } +OP( 0xb4, i_mov_ahd8 ) { Breg(AH) = fetch(); CLKS(4,4,2); } +OP( 0xb5, i_mov_chd8 ) { Breg(CH) = fetch(); CLKS(4,4,2); } +OP( 0xb6, i_mov_dhd8 ) { Breg(DH) = fetch(); CLKS(4,4,2); } +OP( 0xb7, i_mov_bhd8 ) { Breg(BH) = fetch(); CLKS(4,4,2); } + +OP( 0xb8, i_mov_axd16 ) { Breg(AL) = fetch(); Breg(AH) = fetch(); CLKS(4,4,2); } +OP( 0xb9, i_mov_cxd16 ) { Breg(CL) = fetch(); Breg(CH) = fetch(); CLKS(4,4,2); } +OP( 0xba, i_mov_dxd16 ) { Breg(DL) = fetch(); Breg(DH) = fetch(); CLKS(4,4,2); } +OP( 0xbb, i_mov_bxd16 ) { Breg(BL) = fetch(); Breg(BH) = fetch(); CLKS(4,4,2); } +OP( 0xbc, i_mov_spd16 ) { Wreg(SP) = fetchword(); CLKS(4,4,2); } +OP( 0xbd, i_mov_bpd16 ) { Wreg(BP) = fetchword(); CLKS(4,4,2); } +OP( 0xbe, i_mov_sid16 ) { Wreg(IX) = fetchword(); CLKS(4,4,2); } +OP( 0xbf, i_mov_did16 ) { Wreg(IY) = fetchword(); CLKS(4,4,2); } OP( 0xc0, i_rotshft_bd8 ) { uint32_t src, dst; uint8_t c; GetModRM; src = (unsigned)GetRMByte(ModRM); dst=src; - c=FETCH(); + c=fetch(); CLKM(7,7,2,19,19,6); if (c) switch (ModRM & 0x38) { case 0x00: do { ROL_BYTE; c--; CLK(1); } while (c>0); PutbackRMByte(ModRM,(BYTE)dst); break; @@ -420,7 +420,7 @@ OP( 0xc0, i_rotshft_bd8 ) { OP( 0xc1, i_rotshft_wd8 ) { uint32_t src, dst; uint8_t c; GetModRM; src = (unsigned)GetRMWord(ModRM); dst=src; - c=FETCH(); + c=fetch(); CLKM(7,7,2,27,19,6); if (c) switch (ModRM & 0x38) { case 0x00: do { ROL_WORD; c--; CLK(1); } while (c>0); PutbackRMWord(ModRM,(WORD)dst); break; @@ -434,7 +434,7 @@ OP( 0xc1, i_rotshft_wd8 ) { } } -OP( 0xc2, i_ret_d16 ) { uint32_t count = FETCH(); count += FETCH() << 8; POP(m_ip); Wreg(SP)+=count; CHANGE_PC; CLKS(24,24,10); } +OP( 0xc2, i_ret_d16 ) { uint32_t count = fetch(); count += fetch() << 8; POP(m_ip); Wreg(SP)+=count; CHANGE_PC; CLKS(24,24,10); } OP( 0xc3, i_ret ) { POP(m_ip); CHANGE_PC; CLKS(19,19,10); } OP( 0xc4, i_les_dw ) { GetModRM; WORD tmp = GetRMWord(ModRM); RegWord(ModRM)=tmp; Sreg(DS1) = GetnextRMWord; CLKW(26,26,14,26,18,10,m_EA); } OP( 0xc5, i_lds_dw ) { GetModRM; WORD tmp = GetRMWord(ModRM); RegWord(ModRM)=tmp; Sreg(DS0) = GetnextRMWord; CLKW(26,26,14,26,18,10,m_EA); } @@ -442,12 +442,12 @@ OP( 0xc6, i_mov_bd8 ) { GetModRM; PutImmRMByte(ModRM); m_icount-=(ModRM >=0xc0 OP( 0xc7, i_mov_wd16 ) { GetModRM; PutImmRMWord(ModRM); m_icount-=(ModRM >=0xc0 )?4:15; } OP( 0xc8, i_enter ) { - uint32_t nb = FETCH(); + uint32_t nb = fetch(); uint32_t i,level; m_icount-=23; - nb += FETCH() << 8; - level = FETCH(); + nb += fetch() << 8; + level = fetch(); PUSH(Wreg(BP)); Wreg(BP)=Wreg(SP); Wreg(SP) -= nb; @@ -462,10 +462,10 @@ OP( 0xc9, i_leave ) { POP(Wreg(BP)); m_icount-=8; } -OP( 0xca, i_retf_d16 ) { uint32_t count = FETCH(); count += FETCH() << 8; POP(m_ip); POP(Sreg(PS)); Wreg(SP)+=count; CHANGE_PC; CLKS(32,32,16); } +OP( 0xca, i_retf_d16 ) { uint32_t count = fetch(); count += fetch() << 8; POP(m_ip); POP(Sreg(PS)); Wreg(SP)+=count; CHANGE_PC; CLKS(32,32,16); } OP( 0xcb, i_retf ) { POP(m_ip); POP(Sreg(PS)); CHANGE_PC; CLKS(29,29,16); } OP( 0xcc, i_int3 ) { nec_interrupt(3, BRK); CLKS(50,50,24); } -OP( 0xcd, i_int ) { nec_interrupt(FETCH(), BRK); CLKS(50,50,24); } +OP( 0xcd, i_int ) { nec_interrupt(fetch(), BRK); CLKS(50,50,24); } OP( 0xce, i_into ) { if (OF) { nec_interrupt(NEC_BRKV_VECTOR, BRK); CLKS(52,52,26); } else CLK(3); } OP( 0xcf, i_iret ) { POP(m_ip); POP(Sreg(PS)); i_popf(); CHANGE_PC; CLKS(39,39,19); } @@ -531,25 +531,25 @@ OP( 0xd3, i_rotshft_wcl ) { } } -OP( 0xd4, i_aam ) { FETCH(); Breg(AH) = Breg(AL) / 10; Breg(AL) %= 10; SetSZPF_Word(Wreg(AW)); CLKS(15,15,12); } -OP( 0xd5, i_aad ) { FETCH(); Breg(AL) = Breg(AH) * 10 + Breg(AL); Breg(AH) = 0; SetSZPF_Byte(Breg(AL)); CLKS(7,7,8); } +OP( 0xd4, i_aam ) { fetch(); Breg(AH) = Breg(AL) / 10; Breg(AL) %= 10; SetSZPF_Word(Wreg(AW)); CLKS(15,15,12); } +OP( 0xd5, i_aad ) { fetch(); Breg(AL) = Breg(AH) * 10 + Breg(AL); Breg(AH) = 0; SetSZPF_Byte(Breg(AL)); CLKS(7,7,8); } OP( 0xd6, i_setalc ) { Breg(AL) = (CF)?0xff:0x00; m_icount-=3; logerror("%06x: Undefined opcode (SETALC)\n",PC()); } OP( 0xd7, i_trans ) { uint32_t dest = (Wreg(BW)+Breg(AL))&0xffff; Breg(AL) = GetMemB(DS0, dest); CLKS(9,9,5); } OP( 0xd8, i_fpo ) { GetModRM; GetRMByte(ModRM); m_icount-=2; logerror("%06x: Unimplemented floating point control %04x\n",PC(),ModRM); } -OP( 0xe0, i_loopne ) { int8_t disp = (int8_t)FETCH(); Wreg(CW)--; if (!ZF && Wreg(CW)) { m_ip = (WORD)(m_ip+disp); /*CHANGE_PC;*/ CLKS(14,14,6); } else CLKS(5,5,3); } -OP( 0xe1, i_loope ) { int8_t disp = (int8_t)FETCH(); Wreg(CW)--; if ( ZF && Wreg(CW)) { m_ip = (WORD)(m_ip+disp); /*CHANGE_PC;*/ CLKS(14,14,6); } else CLKS(5,5,3); } -OP( 0xe2, i_loop ) { int8_t disp = (int8_t)FETCH(); Wreg(CW)--; if (Wreg(CW)) { m_ip = (WORD)(m_ip+disp); /*CHANGE_PC;*/ CLKS(13,13,6); } else CLKS(5,5,3); } -OP( 0xe3, i_jcxz ) { int8_t disp = (int8_t)FETCH(); if (Wreg(CW) == 0) { m_ip = (WORD)(m_ip+disp); /*CHANGE_PC;*/ CLKS(13,13,6); } else CLKS(5,5,3); } -OP( 0xe4, i_inal ) { uint8_t port = FETCH(); Breg(AL) = read_port_byte(port); CLKS(9,9,5); } -OP( 0xe5, i_inax ) { uint8_t port = FETCH(); Wreg(AW) = read_port_word(port); CLKW(13,13,7,13,9,5,port); } -OP( 0xe6, i_outal ) { uint8_t port = FETCH(); write_port_byte(port, Breg(AL)); CLKS(8,8,3); } -OP( 0xe7, i_outax ) { uint8_t port = FETCH(); write_port_word(port, Wreg(AW)); CLKW(12,12,5,12,8,3,port); } - -OP( 0xe8, i_call_d16 ) { uint32_t tmp; tmp = FETCHWORD(); PUSH(m_ip); m_ip = (WORD)(m_ip+(int16_t)tmp); CHANGE_PC; m_icount-=24; } -OP( 0xe9, i_jmp_d16 ) { uint32_t tmp; tmp = FETCHWORD(); m_ip = (WORD)(m_ip+(int16_t)tmp); CHANGE_PC; m_icount-=15; } -OP( 0xea, i_jmp_far ) { uint32_t tmp,tmp1; tmp = FETCHWORD(); tmp1 = FETCHWORD(); Sreg(PS) = (WORD)tmp1; m_ip = (WORD)tmp; CHANGE_PC; m_icount-=27; } -OP( 0xeb, i_jmp_d8 ) { int tmp = (int)((int8_t)FETCH()); m_icount-=12; m_ip = (WORD)(m_ip+tmp); } +OP( 0xe0, i_loopne ) { int8_t disp = (int8_t)fetch(); Wreg(CW)--; if (!ZF && Wreg(CW)) { m_ip = (WORD)(m_ip+disp); /*CHANGE_PC;*/ CLKS(14,14,6); } else CLKS(5,5,3); } +OP( 0xe1, i_loope ) { int8_t disp = (int8_t)fetch(); Wreg(CW)--; if ( ZF && Wreg(CW)) { m_ip = (WORD)(m_ip+disp); /*CHANGE_PC;*/ CLKS(14,14,6); } else CLKS(5,5,3); } +OP( 0xe2, i_loop ) { int8_t disp = (int8_t)fetch(); Wreg(CW)--; if (Wreg(CW)) { m_ip = (WORD)(m_ip+disp); /*CHANGE_PC;*/ CLKS(13,13,6); } else CLKS(5,5,3); } +OP( 0xe3, i_jcxz ) { int8_t disp = (int8_t)fetch(); if (Wreg(CW) == 0) { m_ip = (WORD)(m_ip+disp); /*CHANGE_PC;*/ CLKS(13,13,6); } else CLKS(5,5,3); } +OP( 0xe4, i_inal ) { uint8_t port = fetch(); Breg(AL) = read_port_byte(port); CLKS(9,9,5); } +OP( 0xe5, i_inax ) { uint8_t port = fetch(); Wreg(AW) = read_port_word(port); CLKW(13,13,7,13,9,5,port); } +OP( 0xe6, i_outal ) { uint8_t port = fetch(); write_port_byte(port, Breg(AL)); CLKS(8,8,3); } +OP( 0xe7, i_outax ) { uint8_t port = fetch(); write_port_word(port, Wreg(AW)); CLKW(12,12,5,12,8,3,port); } + +OP( 0xe8, i_call_d16 ) { uint32_t tmp; tmp = fetchword(); PUSH(m_ip); m_ip = (WORD)(m_ip+(int16_t)tmp); CHANGE_PC; m_icount-=24; } +OP( 0xe9, i_jmp_d16 ) { uint32_t tmp; tmp = fetchword(); m_ip = (WORD)(m_ip+(int16_t)tmp); CHANGE_PC; m_icount-=15; } +OP( 0xea, i_jmp_far ) { uint32_t tmp,tmp1; tmp = fetchword(); tmp1 = fetchword(); Sreg(PS) = (WORD)tmp1; m_ip = (WORD)tmp; CHANGE_PC; m_icount-=27; } +OP( 0xeb, i_jmp_d8 ) { int tmp = (int)((int8_t)fetch()); m_icount-=12; m_ip = (WORD)(m_ip+tmp); } OP( 0xec, i_inaldx ) { Breg(AL) = read_port_byte(Wreg(DW)); CLKS(8,8,5);} OP( 0xed, i_inaxdx ) { Wreg(AW) = read_port_word(Wreg(DW)); CLKW(12,12,7,12,8,5,Wreg(DW)); } OP( 0xee, i_outdxal ) { write_port_byte(Wreg(DW), Breg(AL)); CLKS(8,8,3); } @@ -615,7 +615,7 @@ OP( 0xf5, i_cmc ) { m_CarryVal = !CF; CLK(2); } OP( 0xf6, i_f6pre ) { uint32_t tmp; uint32_t uresult,uresult2; int32_t result,result2; GetModRM; tmp = GetRMByte(ModRM); switch (ModRM & 0x38) { - case 0x00: tmp &= FETCH(); m_CarryVal = m_OverVal = 0; SetSZPF_Byte(tmp); m_icount-=(ModRM >=0xc0 )?4:11; break; /* TEST */ + case 0x00: tmp &= fetch(); m_CarryVal = m_OverVal = 0; SetSZPF_Byte(tmp); m_icount-=(ModRM >=0xc0 )?4:11; break; /* TEST */ case 0x08: logerror("%06x: Undefined opcode 0xf6 0x08\n",PC()); break; case 0x10: PutbackRMByte(ModRM,~tmp); m_icount-=(ModRM >=0xc0 )?2:16; break; /* NOT */ case 0x18: m_CarryVal=(tmp!=0); tmp=(~tmp)+1; SetSZPF_Byte(tmp); PutbackRMByte(ModRM,tmp&0xff); m_icount-=(ModRM >=0xc0 )?2:16; break; /* NEG */ @@ -629,7 +629,7 @@ OP( 0xf6, i_f6pre ) { uint32_t tmp; uint32_t uresult,uresult2; int32_t result,re OP( 0xf7, i_f7pre ) { uint32_t tmp,tmp2; uint32_t uresult,uresult2; int32_t result,result2; GetModRM; tmp = GetRMWord(ModRM); switch (ModRM & 0x38) { - case 0x00: tmp2 = FETCHWORD(); tmp &= tmp2; m_CarryVal = m_OverVal = 0; SetSZPF_Word(tmp); m_icount-=(ModRM >=0xc0 )?4:11; break; /* TEST */ + case 0x00: tmp2 = fetchword(); tmp &= tmp2; m_CarryVal = m_OverVal = 0; SetSZPF_Word(tmp); m_icount-=(ModRM >=0xc0 )?4:11; break; /* TEST */ case 0x08: logerror("%06x: Undefined opcode 0xf7 0x08\n",PC()); break; case 0x10: PutbackRMWord(ModRM,~tmp); m_icount-=(ModRM >=0xc0 )?2:16; break; /* NOT */ case 0x18: m_CarryVal=(tmp!=0); tmp=(~tmp)+1; SetSZPF_Word(tmp); PutbackRMWord(ModRM,tmp&0xffff); m_icount-=(ModRM >=0xc0 )?2:16; break; /* NEG */ diff --git a/src/devices/cpu/nec/necmacro.h b/src/devices/cpu/nec/necmacro.h index c97f487cc2c..582c233979f 100644 --- a/src/devices/cpu/nec/necmacro.h +++ b/src/devices/cpu/nec/necmacro.h @@ -55,8 +55,8 @@ #define JMP(flag) \ int tmp; \ - EMPTY_PREFETCH(); \ - tmp = (int)((int8_t)FETCH()); \ + EMPTY_PREfetch(); \ + tmp = (int)((int8_t)fetch()); \ if (flag) \ { \ static const uint8_t table[3]={3,10,10}; \ @@ -98,7 +98,7 @@ Breg(AL) &= 0x0F #define BITOP_BYTE \ - ModRM = FETCH(); \ + ModRM = fetch(); \ if (ModRM >= 0xc0) { \ tmp=Breg(Mod_RM.RM.b[ModRM]); \ } \ @@ -108,7 +108,7 @@ } #define BITOP_WORD \ - ModRM = FETCH(); \ + ModRM = fetch(); \ if (ModRM >= 0xc0) { \ tmp=Wreg(Mod_RM.RM.w[ModRM]); \ } \ diff --git a/src/devices/cpu/nec/necmodrm.h b/src/devices/cpu/nec/necmodrm.h index 2bc3afdfd28..ac69a0010be 100644 --- a/src/devices/cpu/nec/necmodrm.h +++ b/src/devices/cpu/nec/necmodrm.h @@ -39,10 +39,10 @@ static struct { { \ WORD val; \ if (ModRM >= 0xc0) \ - Wreg(Mod_RM.RM.w[ModRM]) = FETCHWORD(); \ + Wreg(Mod_RM.RM.w[ModRM]) = fetchword(); \ else { \ (this->*s_GetEA[ModRM])(); \ - val = FETCHWORD(); \ + val = fetchword(); \ write_mem_word( m_EA , val); \ } \ } @@ -61,10 +61,10 @@ static struct { #define PutImmRMByte(ModRM) \ { \ if (ModRM >= 0xc0) \ - Breg(Mod_RM.RM.b[ModRM])=FETCH(); \ + Breg(Mod_RM.RM.b[ModRM])=fetch(); \ else { \ (this->*s_GetEA[ModRM])(); \ - write_mem_byte( m_EA , FETCH() ); \ + write_mem_byte( m_EA , fetch() ); \ } \ } @@ -77,30 +77,30 @@ static struct { } #define DEF_br8 \ - uint32_t ModRM = FETCH(),src,dst; \ + uint32_t ModRM = fetch(),src,dst; \ src = RegByte(ModRM); \ dst = GetRMByte(ModRM) #define DEF_wr16 \ - uint32_t ModRM = FETCH(),src,dst; \ + uint32_t ModRM = fetch(),src,dst; \ src = RegWord(ModRM); \ dst = GetRMWord(ModRM) #define DEF_r8b \ - uint32_t ModRM = FETCH(),src,dst; \ + uint32_t ModRM = fetch(),src,dst; \ dst = RegByte(ModRM); \ src = GetRMByte(ModRM) #define DEF_r16w \ - uint32_t ModRM = FETCH(),src,dst; \ + uint32_t ModRM = fetch(),src,dst; \ dst = RegWord(ModRM); \ src = GetRMWord(ModRM) #define DEF_ald8 \ - uint32_t src = FETCH(); \ + uint32_t src = fetch(); \ uint32_t dst = Breg(AL) #define DEF_axd16 \ - uint32_t src = FETCH(); \ + uint32_t src = fetch(); \ uint32_t dst = Wreg(AW); \ - src += (FETCH() << 8) + src += (fetch() << 8) diff --git a/src/devices/cpu/nec/necpriv.h b/src/devices/cpu/nec/necpriv.h index 2d4cb9f6b2f..459fa5017b4 100644 --- a/src/devices/cpu/nec/necpriv.h +++ b/src/devices/cpu/nec/necpriv.h @@ -64,7 +64,7 @@ enum BREGS { /************************************************************************/ -#define CHANGE_PC do { EMPTY_PREFETCH(); } while (0) +#define CHANGE_PC do { EMPTY_PREfetch(); } while (0) #define SegBase(Seg) (Sreg(Seg) << 4) @@ -78,15 +78,13 @@ enum BREGS { /* prefetch timing */ -#define FETCH() fetch() -#define FETCHWORD() fetchword() -#define EMPTY_PREFETCH() m_prefetch_reset = 1 +#define EMPTY_PREfetch() m_prefetch_reset = 1 #define PUSH(val) { Wreg(SP) -= 2; write_mem_word(((Sreg(SS)<<4)+Wreg(SP)), val); } #define POP(var) { Wreg(SP) += 2; var = read_mem_word(((Sreg(SS)<<4) + ((Wreg(SP)-2) & 0xffff))); } -#define GetModRM uint32_t ModRM=FETCH() +#define GetModRM uint32_t ModRM=fetch() /* Cycle count macros: CLK - cycle count is the same on all processors diff --git a/src/devices/cpu/nec/v25.cpp b/src/devices/cpu/nec/v25.cpp index d70bbd224c0..8f9392a24ad 100644 --- a/src/devices/cpu/nec/v25.cpp +++ b/src/devices/cpu/nec/v25.cpp @@ -44,7 +44,7 @@ typedef uint32_t DWORD; #include "v25.h" #include "v25priv.h" -#include "nec_common.h" +#include "necdasm.h" DEFINE_DEVICE_TYPE(V25, v25_device, "v25", "V25") DEFINE_DEVICE_TYPE(V35, v35_device, "v35", "V35") @@ -142,8 +142,8 @@ uint8_t v25_common_device::fetch() uint16_t v25_common_device::fetchword() { - uint16_t r = FETCH(); - r |= (FETCH()<<8); + uint16_t r = fetch(); + r |= (fetch()<<8); return r; } @@ -419,9 +419,9 @@ void v25_common_device::execute_set_input(int irqline, int state) } } -offs_t v25_common_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *v25_common_device::create_disassembler() { - return necv_dasm_one(stream, pc, oprom, m_v25v35_decryptiontable); + return new nec_disassembler(m_v25v35_decryptiontable); } void v25_common_device::device_start() diff --git a/src/devices/cpu/nec/v25.h b/src/devices/cpu/nec/v25.h index f0ccda61517..808b4ec3fc9 100644 --- a/src/devices/cpu/nec/v25.h +++ b/src/devices/cpu/nec/v25.h @@ -93,9 +93,7 @@ protected: virtual void state_export(const device_state_entry &entry) override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 8; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/nec/v25instr.hxx b/src/devices/cpu/nec/v25instr.hxx index 881f2044aae..e394e9ab213 100644 --- a/src/devices/cpu/nec/v25instr.hxx +++ b/src/devices/cpu/nec/v25instr.hxx @@ -1,7 +1,7 @@ // license:BSD-3-Clause // copyright-holders:Bryan McPhail, Alex W. Jackson #define GetRB \ - ModRM = FETCH(); \ + ModRM = fetch(); \ if (ModRM >= 0xc0) \ tmp = Wreg(Mod_RM.RM.w[ModRM]) & 0x7; \ else { \ @@ -43,7 +43,7 @@ } OP( 0x0f, i_pre_v25 ) { uint32_t ModRM, tmp, tmp2; - switch (FETCH()) { + switch (fetch()) { case 0x10 : BITOP_BYTE; CLKS(3,3,4); tmp2 = Breg(CL) & 0x7; m_ZeroVal = (tmp & (1<>8)&0xf); tmp &= 0xff; PutbackRMByte(ModRM,tmp); CLKM(13,13,9,28,28,15); break; - case 0x2a : ModRM = FETCH(); tmp = GetRMByte(ModRM); tmp2 = (Breg(AL) & 0xf)<<4; Breg(AL) = (Breg(AL) & 0xf0) | (tmp&0xf); tmp = tmp2 | (tmp>>4); PutbackRMByte(ModRM,tmp); CLKM(17,17,13,32,32,19); break; + case 0x28 : ModRM = fetch(); tmp = GetRMByte(ModRM); tmp <<= 4; tmp |= Breg(AL) & 0xf; Breg(AL) = (Breg(AL) & 0xf0) | ((tmp>>8)&0xf); tmp &= 0xff; PutbackRMByte(ModRM,tmp); CLKM(13,13,9,28,28,15); break; + case 0x2a : ModRM = fetch(); tmp = GetRMByte(ModRM); tmp2 = (Breg(AL) & 0xf)<<4; Breg(AL) = (Breg(AL) & 0xf0) | (tmp&0xf); tmp = tmp2 | (tmp>>4); PutbackRMByte(ModRM,tmp); CLKM(17,17,13,32,32,19); break; case 0x2d : GetRB; nec_bankswitch(tmp); CLK(15); break; - case 0x31 : ModRM = FETCH(); ModRM=0; logerror("%06x: Unimplemented bitfield INS\n",PC()); break; - case 0x33 : ModRM = FETCH(); ModRM=0; logerror("%06x: Unimplemented bitfield EXT\n",PC()); break; + case 0x31 : ModRM = fetch(); ModRM=0; logerror("%06x: Unimplemented bitfield INS\n",PC()); break; + case 0x33 : ModRM = fetch(); ModRM=0; logerror("%06x: Unimplemented bitfield EXT\n",PC()); break; case 0x91 : RETRBI; CLK(12); break; case 0x92 : FINT; CLK(2); m_no_interrupt = 1; break; case 0x94 : GetRB; TSKSW; CLK(20); break; @@ -80,5 +80,5 @@ OP( 0x0f, i_pre_v25 ) { uint32_t ModRM, tmp, tmp2; } } -OP( 0x63, i_brkn ) { nec_interrupt(FETCH(), BRKN); CLKS(50,50,24); } -OP( 0xF1, i_brks ) { nec_interrupt(FETCH(), BRKS); CLKS(50,50,24); } +OP( 0x63, i_brkn ) { nec_interrupt(fetch(), BRKN); CLKS(50,50,24); } +OP( 0xF1, i_brks ) { nec_interrupt(fetch(), BRKS); CLKS(50,50,24); } diff --git a/src/devices/cpu/nec/v25priv.h b/src/devices/cpu/nec/v25priv.h index c9022898436..eb60c8f041d 100644 --- a/src/devices/cpu/nec/v25priv.h +++ b/src/devices/cpu/nec/v25priv.h @@ -121,7 +121,7 @@ enum BREGS { /************************************************************************/ -#define CHANGE_PC do { EMPTY_PREFETCH(); } while (0) +#define CHANGE_PC do { EMPTY_PREfetch(); } while (0) #define SegBase(Seg) (Sreg(Seg) << 4) @@ -135,15 +135,13 @@ enum BREGS { /* prefetch timing */ -#define FETCH() fetch() -#define FETCHWORD() fetchword() -#define EMPTY_PREFETCH() m_prefetch_reset = 1 +#define EMPTY_PREfetch() m_prefetch_reset = 1 #define PUSH(val) { Wreg(SP) -= 2; write_mem_word(((Sreg(SS)<<4)+Wreg(SP)), val); } #define POP(var) { Wreg(SP) += 2; var = read_mem_word(((Sreg(SS)<<4) + ((Wreg(SP)-2) & 0xffff))); } -#define GetModRM uint32_t ModRM=FETCH() +#define GetModRM uint32_t ModRM=fetch() /* Cycle count macros: CLK - cycle count is the same on all processors diff --git a/src/devices/cpu/patinhofeio/patinho_feio.cpp b/src/devices/cpu/patinhofeio/patinho_feio.cpp index 6c4b84c4410..d87379cc8fb 100644 --- a/src/devices/cpu/patinhofeio/patinho_feio.cpp +++ b/src/devices/cpu/patinhofeio/patinho_feio.cpp @@ -6,6 +6,7 @@ #include "emu.h" #include "patinhofeio_cpu.h" +#include "patinho_feio_dasm.h" #include "debugger.h" #include "includes/patinhofeio.h" // FIXME: this is a dependency from devices on MAME @@ -782,8 +783,7 @@ void patinho_feio_cpu_device::execute_instruction() printf("unimplemented opcode: 0x%02X\n", m_opcode); } -offs_t patinho_feio_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *patinho_feio_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( patinho_feio ); - return CPU_DISASSEMBLE_NAME(patinho_feio)(this, stream, pc, oprom, opram, options); + return new patinho_feio_disassembler; } diff --git a/src/devices/cpu/patinhofeio/patinho_feio_dasm.cpp b/src/devices/cpu/patinhofeio/patinho_feio_dasm.cpp index c655314f348..b3f66b3ae9b 100644 --- a/src/devices/cpu/patinhofeio/patinho_feio_dasm.cpp +++ b/src/devices/cpu/patinhofeio/patinho_feio_dasm.cpp @@ -1,27 +1,32 @@ // license:GPL-2.0+ // copyright-holders:Felipe Sanches #include "emu.h" -#include "cpu/patinhofeio/patinhofeio_cpu.h" +#include "patinho_feio_dasm.h" -CPU_DISASSEMBLE(patinho_feio) +u32 patinho_feio_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t patinho_feio_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { int addr, value, n, f; - switch (oprom[0] & 0xF0) { + switch (opcodes.r8(pc) & 0xF0) { case 0x00: //PLA = "Pula": Unconditionally JUMP to effective address - addr = (oprom[0] & 0x0F) << 8 | oprom[1]; + addr = (opcodes.r8(pc) & 0x0F) << 8 | opcodes.r8(pc+1); util::stream_format(stream, "PLA /%03X", addr); return 2; case 0x10: //PLAX = "Pulo indexado": Unconditionally JUMP to indexed address - addr = (oprom[0] & 0x0F) << 8 | oprom[1]; + addr = (opcodes.r8(pc) & 0x0F) << 8 | opcodes.r8(pc+1); util::stream_format(stream, "PLAX (IDX) + /%03X", addr); return 2; case 0x20: //ARM = "Armazena": Stores the contents of the // accumulator in the given 12bit address - addr = (oprom[0] & 0x0F) << 8 | oprom[1]; + addr = (opcodes.r8(pc) & 0x0F) << 8 | opcodes.r8(pc+1); if (addr==0){ util::stream_format(stream, "ARM (IDX)"); }else{ @@ -31,13 +36,13 @@ CPU_DISASSEMBLE(patinho_feio) case 0x30: //ARMX = "Armazenamento indexado": Stores the contents of the accumulator in the // given 12bit address (indexed by IDX) - addr = (oprom[0] & 0x0F) << 8 | oprom[1]; + addr = (opcodes.r8(pc) & 0x0F) << 8 | opcodes.r8(pc+1); util::stream_format(stream, "ARMX (IDX) + /%03X", addr); return 2; case 0x40: //CAR = "Carrega": Loads the contents of the given 12bit address // into the accumulator - addr = (oprom[0] & 0x0F) << 8 | oprom[1]; + addr = (opcodes.r8(pc) & 0x0F) << 8 | opcodes.r8(pc+1); if (addr==0){ util::stream_format(stream, "CAR (IDX)"); }else{ @@ -47,39 +52,39 @@ CPU_DISASSEMBLE(patinho_feio) case 0x50: //CARX = "Carga indexada": Loads the contents of the given 12bit address // (indexed by IDX) into the accumulator - addr = (oprom[0] & 0x0F) << 8 | oprom[1]; + addr = (opcodes.r8(pc) & 0x0F) << 8 | opcodes.r8(pc+1); util::stream_format(stream, "CARX (IDX) + /%03X", addr); return 2; case 0x60: //SOM = "Soma": Adds the contents of the given 12bit address // into the accumulator - addr = (oprom[0] & 0x0F) << 8 | oprom[1]; + addr = (opcodes.r8(pc) & 0x0F) << 8 | opcodes.r8(pc+1); util::stream_format(stream, "SOM /%03X", addr); return 2; case 0x70: //SOMX = "Soma indexada": Adds the contents of the given 12bit address // (indexed by IDX) into the accumulator - addr = (oprom[0] & 0x0F) << 8 | oprom[1]; + addr = (opcodes.r8(pc) & 0x0F) << 8 | opcodes.r8(pc+1); util::stream_format(stream, "SOMX (IDX) + /%03X", addr); return 2; case 0xA0: //PLAN = "Pula se ACC for negativo": Jumps to the 12bit address // if the accumulator is negative - addr = (oprom[0] & 0x0F) << 8 | oprom[1]; + addr = (opcodes.r8(pc) & 0x0F) << 8 | opcodes.r8(pc+1); util::stream_format(stream, "PLAN /%03X", addr); return 2; case 0xB0: //PLAZ = "Pula se ACC for zero": Jumps to the 12bit address // if the accumulator is zero - addr = (oprom[0] & 0x0F) << 8 | oprom[1]; + addr = (opcodes.r8(pc) & 0x0F) << 8 | opcodes.r8(pc+1); util::stream_format(stream, "PLAZ /%03X", addr); return 2; case 0xC0: - n = (oprom[0] & 0x0F); - f = (oprom[1] & 0x0F); + n = (opcodes.r8(pc) & 0x0F); + f = (opcodes.r8(pc+1) & 0x0F); n+= (n < 10) ? '0' : 'A'-10; f+= (f < 10) ? '0' : 'A'-10; - switch(oprom[1] & 0xF0) + switch(opcodes.r8(pc+1) & 0xF0) { case 0x10: util::stream_format(stream, "FNC /%c%c", n, f); return 2; case 0x20: util::stream_format(stream, "SAL /%c%c", n, f); return 2; @@ -88,11 +93,11 @@ CPU_DISASSEMBLE(patinho_feio) } break; case 0xD0: - value = oprom[1] & 0x0F; - switch (oprom[0] & 0x0F) + value = opcodes.r8(pc+1) & 0x0F; + switch (opcodes.r8(pc) & 0x0F) { case 0x01: - switch (oprom[1] & 0xF0) + switch (opcodes.r8(pc+1) & 0xF0) { case 0x00: util::stream_format(stream, "DD /%01X", value); return 2; //DD = "Deslocamento para a direita": Shift right case 0x10: util::stream_format(stream, "DDV /%01X", value); return 2; //DDV = "Deslocamento para a direita c/ V": Shift right with carry @@ -105,25 +110,25 @@ CPU_DISASSEMBLE(patinho_feio) case 0x80: util::stream_format(stream, "DDS /%01X", value); return 2; //DDS = "Deslocamento para a direita com duplicacao de sinal": Shift right with sign duplication } break; - case 0x02: util::stream_format(stream, "XOR /%02X", oprom[1]); return 2; //Logical XOR - case 0x04: util::stream_format(stream, "NAND /%02X", oprom[1]); return 2; //Logical NAND - case 0x08: util::stream_format(stream, "SOMI /%02X", oprom[1]); return 2; //SOMI = "Soma imediata": Add immediate value into accumulator - case 0x0A: util::stream_format(stream, "CARI /%02X", oprom[1]); return 2; //CARI = "Carrega imediato": Loads an immediate value into the accumulator + case 0x02: util::stream_format(stream, "XOR /%02X", opcodes.r8(pc+1)); return 2; //Logical XOR + case 0x04: util::stream_format(stream, "NAND /%02X", opcodes.r8(pc+1)); return 2; //Logical NAND + case 0x08: util::stream_format(stream, "SOMI /%02X", opcodes.r8(pc+1)); return 2; //SOMI = "Soma imediata": Add immediate value into accumulator + case 0x0A: util::stream_format(stream, "CARI /%02X", opcodes.r8(pc+1)); return 2; //CARI = "Carrega imediato": Loads an immediate value into the accumulator } break; case 0xE0: //SUS = "Subtrai um ou salta" - addr = (oprom[0] & 0x0F) << 8 | oprom[1]; + addr = (opcodes.r8(pc) & 0x0F) << 8 | opcodes.r8(pc+1); util::stream_format(stream, "SUS /%03X", addr); return 2; case 0xF0: //PUG = "Pula e guarda" - addr = (oprom[0] & 0x0F) << 8 | oprom[1]; + addr = (opcodes.r8(pc) & 0x0F) << 8 | opcodes.r8(pc+1); util::stream_format(stream, "PUG /%03X", addr); return 2; } - switch (oprom[0]) { + switch (opcodes.r8(pc)) { case 0x80: util::stream_format(stream, "LIMPO"); return 1; case 0x81: util::stream_format(stream, "UM"); return 1; case 0x82: util::stream_format(stream, "CMP1"); return 1; diff --git a/src/devices/cpu/patinhofeio/patinho_feio_dasm.h b/src/devices/cpu/patinhofeio/patinho_feio_dasm.h new file mode 100644 index 00000000000..0d950a3689c --- /dev/null +++ b/src/devices/cpu/patinhofeio/patinho_feio_dasm.h @@ -0,0 +1,19 @@ +// license:GPL-2.0+ +// copyright-holders:Felipe Sanches + +#ifndef MAME_CPU_PATINHOFEIO_PATINHO_FEIO_DASM_H +#define MAME_CPU_PATINHOFEIO_PATINHO_FEIO_DASM_H + +#pragma once + +class patinho_feio_disassembler : public util::disasm_interface +{ +public: + patinho_feio_disassembler() = default; + virtual ~patinho_feio_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/patinhofeio/patinhofeio_cpu.h b/src/devices/cpu/patinhofeio/patinhofeio_cpu.h index 07b402871d0..008acd8e0ae 100644 --- a/src/devices/cpu/patinhofeio/patinhofeio_cpu.h +++ b/src/devices/cpu/patinhofeio/patinhofeio_cpu.h @@ -65,7 +65,7 @@ public: protected: virtual void execute_run() override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; address_space_config m_program_config; @@ -121,10 +121,6 @@ protected: // device_memory_interface overrides virtual space_config_vector memory_space_config() const override; - // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 2; } - private: void execute_instruction(); void compute_effective_address(unsigned int addr); diff --git a/src/devices/cpu/pdp1/pdp1.cpp b/src/devices/cpu/pdp1/pdp1.cpp index 2a5368ae56f..73482e5b82d 100644 --- a/src/devices/cpu/pdp1/pdp1.cpp +++ b/src/devices/cpu/pdp1/pdp1.cpp @@ -342,6 +342,7 @@ #include "emu.h" #include "debugger.h" #include "pdp1.h" +#include "pdp1dasm.h" #define LOG 0 #define LOG_EXTRA 0 @@ -418,10 +419,9 @@ void pdp1_device::device_config_complete() } -offs_t pdp1_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *pdp1_device::create_disassembler() { - extern CPU_DISASSEMBLE( pdp1 ); - return CPU_DISASSEMBLE_NAME(pdp1)(this, stream, pc, oprom, opram, options); + return new pdp1_disassembler; } diff --git a/src/devices/cpu/pdp1/pdp1.h b/src/devices/cpu/pdp1/pdp1.h index 174317d995e..5a2df5fd91e 100644 --- a/src/devices/cpu/pdp1/pdp1.h +++ b/src/devices/cpu/pdp1/pdp1.h @@ -114,9 +114,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 4; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/pdp1/pdp1dasm.cpp b/src/devices/cpu/pdp1/pdp1dasm.cpp index 7376b752538..9b04c91ec87 100644 --- a/src/devices/cpu/pdp1/pdp1dasm.cpp +++ b/src/devices/cpu/pdp1/pdp1dasm.cpp @@ -1,13 +1,10 @@ // license:BSD-3-Clause // copyright-holders:Raphael Nabet #include "emu.h" -#include "cpu/pdp1/pdp1.h" +#include "pdp1dasm.h" +#include "pdp1.h" -/* PDP1 registers */ -static int ib; -static int y; - -static inline void ea (void) +inline void pdp1_disassembler::ea() { /* while (1) { @@ -20,15 +17,20 @@ static inline void ea (void) #define IN if (ib) util::stream_format(stream, " i") -CPU_DISASSEMBLE(pdp1) +u32 pdp1_disassembler::opcode_alignment() const +{ + return 4; +} + +offs_t pdp1_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { int md; //int etime = 0; - md = oprom[0] << 24 | oprom[1] << 16 | oprom[2] << 8 | oprom[3]; + md = opcodes.r32(pc); - y = md & 07777; - ib = (md >> 12) & 1; /* */ + int y = md & 07777; + int ib = (md >> 12) & 1; /* */ switch (md >> 13) { case pdp1_device::AND: diff --git a/src/devices/cpu/pdp1/pdp1dasm.h b/src/devices/cpu/pdp1/pdp1dasm.h new file mode 100644 index 00000000000..e5dd4b0f031 --- /dev/null +++ b/src/devices/cpu/pdp1/pdp1dasm.h @@ -0,0 +1,22 @@ +// license:BSD-3-Clause +// copyright-holders:Raphael Nabet + +#ifndef MAME_CPU_PDP1_PDP1DASM_H +#define MAME_CPU_PDP1_PDP1DASM_H + +#pragma once + +class pdp1_disassembler : public util::disasm_interface +{ +public: + pdp1_disassembler() = default; + virtual ~pdp1_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + void ea(); +}; + +#endif diff --git a/src/devices/cpu/pdp1/tx0.cpp b/src/devices/cpu/pdp1/tx0.cpp index 89355ee2ef8..376cf15a346 100644 --- a/src/devices/cpu/pdp1/tx0.cpp +++ b/src/devices/cpu/pdp1/tx0.cpp @@ -12,6 +12,7 @@ #include "emu.h" #include "tx0.h" +#include "tx0dasm.h" #include "debugger.h" #define LOG 0 @@ -1075,15 +1076,12 @@ void tx0_device::io_complete() } -offs_t tx0_8kw_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *tx0_8kw_device::create_disassembler() { - extern CPU_DISASSEMBLE( tx0_8kw ); - return CPU_DISASSEMBLE_NAME(tx0_8kw)(this, stream, pc, oprom, opram, options); + return new tx0_8kw_disassembler; } - -offs_t tx0_64kw_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *tx0_64kw_device::create_disassembler() { - extern CPU_DISASSEMBLE( tx0_64kw ); - return CPU_DISASSEMBLE_NAME(tx0_64kw)(this, stream, pc, oprom, opram, options); + return new tx0_64kw_disassembler; } diff --git a/src/devices/cpu/pdp1/tx0.h b/src/devices/cpu/pdp1/tx0.h index 52cc7f4091a..e9174a46413 100644 --- a/src/devices/cpu/pdp1/tx0.h +++ b/src/devices/cpu/pdp1/tx0.h @@ -67,10 +67,6 @@ protected: // device_memory_interface overrides virtual space_config_vector memory_space_config() const override; - // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 4; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - protected: address_space_config m_program_config; @@ -151,7 +147,7 @@ public: protected: virtual void execute_run() override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: void execute_instruction_8kw(); @@ -166,7 +162,7 @@ public: protected: virtual void execute_run() override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: void execute_instruction_64kw(); diff --git a/src/devices/cpu/pdp1/tx0dasm.cpp b/src/devices/cpu/pdp1/tx0dasm.cpp index cda24ed930c..34d49194ed3 100644 --- a/src/devices/cpu/pdp1/tx0dasm.cpp +++ b/src/devices/cpu/pdp1/tx0dasm.cpp @@ -1,14 +1,19 @@ // license:BSD-3-Clause // copyright-holders:Raphael Nabet #include "emu.h" -#include "cpu/pdp1/tx0.h" +#include "tx0dasm.h" -CPU_DISASSEMBLE(tx0_64kw) +u32 tx0_64kw_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t tx0_64kw_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { int md; int x; - md = oprom[0] << 24 | oprom[1] << 16 | oprom[2] << 8 | oprom[3]; + md = opcodes.r32(pc); x = md & 0177777; switch (md >> 16) @@ -29,12 +34,17 @@ CPU_DISASSEMBLE(tx0_64kw) return 1; } -CPU_DISASSEMBLE(tx0_8kw) +u32 tx0_8kw_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t tx0_8kw_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { int md; int x; - md = oprom[0] << 24 | oprom[1] << 16 | oprom[2] << 8 | oprom[3]; + md = opcodes.r32(pc); x = md & 0017777; switch (md >> 13) diff --git a/src/devices/cpu/pdp1/tx0dasm.h b/src/devices/cpu/pdp1/tx0dasm.h new file mode 100644 index 00000000000..ae97e2bcc1d --- /dev/null +++ b/src/devices/cpu/pdp1/tx0dasm.h @@ -0,0 +1,29 @@ +// license:BSD-3-Clause +// copyright-holders:Raphael Nabet + +#ifndef MAME_CPU_PDP1_TX0DASM_H +#define MAME_CPU_PDP1_TX0DASM_H + +#pragma once + +class tx0_64kw_disassembler : public util::disasm_interface +{ +public: + tx0_64kw_disassembler() = default; + virtual ~tx0_64kw_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +class tx0_8kw_disassembler : public util::disasm_interface +{ +public: + tx0_8kw_disassembler() = default; + virtual ~tx0_8kw_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/pdp8/pdp8.cpp b/src/devices/cpu/pdp8/pdp8.cpp index 1a9150a236d..b3ade64fc75 100644 --- a/src/devices/cpu/pdp8/pdp8.cpp +++ b/src/devices/cpu/pdp8/pdp8.cpp @@ -9,8 +9,7 @@ #include "emu.h" #include "debugger.h" #include "pdp8.h" - -CPU_DISASSEMBLE( pdp8 ); +#include "pdp8dasm.h" #define OP ((op >> 011) & 07) @@ -148,36 +147,13 @@ void pdp8_device::state_string_export(const device_state_entry &entry, std::stri //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t pdp8_device::disasm_min_opcode_bytes() const -{ - return 2; -} - - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t pdp8_device::disasm_max_opcode_bytes() const -{ - return 2; -} - - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t pdp8_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *pdp8_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( pdp8 ); - return CPU_DISASSEMBLE_NAME(pdp8)(this, stream, pc, oprom, opram, options); + return new pdp8_disassembler; } diff --git a/src/devices/cpu/pdp8/pdp8.h b/src/devices/cpu/pdp8/pdp8.h index b21371fd181..c6dc47ce56f 100644 --- a/src/devices/cpu/pdp8/pdp8.h +++ b/src/devices/cpu/pdp8/pdp8.h @@ -40,9 +40,7 @@ public: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // device_state_interface overrides virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; diff --git a/src/devices/cpu/pdp8/pdp8dasm.cpp b/src/devices/cpu/pdp8/pdp8dasm.cpp index 5c2219af4f8..389cf11fda7 100644 --- a/src/devices/cpu/pdp8/pdp8dasm.cpp +++ b/src/devices/cpu/pdp8/pdp8dasm.cpp @@ -7,9 +7,16 @@ */ #include "emu.h" +#include "pdp8dasm.h" -static offs_t pdp8_dasm_one(std::ostream &stream, offs_t pc, uint16_t op) +u32 pdp8_disassembler::opcode_alignment() const { + return 2; +} + +offs_t pdp8_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + uint16_t op = opcodes.r16(pc); uint8_t opcode = (op >> 011) & 07; uint16_t current_page = pc & 07600; uint16_t zero_addr = op & 0177; @@ -157,15 +164,5 @@ static offs_t pdp8_dasm_one(std::ostream &stream, offs_t pc, uint16_t op) } } - return 2 | DASMFLAG_SUPPORTED; -} - - -/*****************************************************************************/ - -CPU_DISASSEMBLE( pdp8 ) -{ - uint16_t op = (*(uint8_t *)(opram + 0) << 8) | - (*(uint8_t *)(opram + 1) << 0); - return pdp8_dasm_one(stream, pc, op); + return 2 | SUPPORTED; } diff --git a/src/devices/cpu/pdp8/pdp8dasm.h b/src/devices/cpu/pdp8/pdp8dasm.h new file mode 100644 index 00000000000..df6c92e9ddb --- /dev/null +++ b/src/devices/cpu/pdp8/pdp8dasm.h @@ -0,0 +1,24 @@ +// license:BSD-3-Clause +// copyright-holders:Ryan Holtz +/* + First-gen DEC PDP-8 disassembler + + Written by Ryan Holtz +*/ + +#ifndef MAME_CPU_PDP8_PDP8DASM_H +#define MAME_CPU_PDP8_PDP8DASM_H + +#pragma once + +class pdp8_disassembler : public util::disasm_interface +{ +public: + pdp8_disassembler() = default; + virtual ~pdp8_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/pic16c5x/16c5xdsm.cpp b/src/devices/cpu/pic16c5x/16c5xdsm.cpp index 03cd0539c8c..06ee6eb01ba 100644 --- a/src/devices/cpu/pic16c5x/16c5xdsm.cpp +++ b/src/devices/cpu/pic16c5x/16c5xdsm.cpp @@ -24,86 +24,60 @@ \**************************************************************************/ #include "emu.h" +#include "16c5xdsm.h" #include -static const uint8_t *rombase; -static const uint8_t *rambase; -static offs_t pcbase; -#define READOP16(A) (rombase[(A) - pcbase] | (rombase[(A) + 1 - pcbase] << 8)) -#define READARG16(A) (rambase[(A) - pcbase] | (rambase[(A) + 1 - pcbase] << 8)) - - - -typedef unsigned char byte; -typedef unsigned short int word; - -#define FMT(a,b) a, b -#define PTRS_PER_FORMAT 2 - -static const char *const regfile[32] = { "Reg$00 (IND)", "Reg$01 (TMR)", "Reg$02 (PCL)", "Reg$03 (ST)", "Reg$04 (FSR)", "Reg$05 (PTA)", "Reg$06 (PTB)", "Reg$07 (PTC)", +const char *const pic16c5x_disassembler::regfile[32] = { "Reg$00 (IND)", "Reg$01 (TMR)", "Reg$02 (PCL)", "Reg$03 (ST)", "Reg$04 (FSR)", "Reg$05 (PTA)", "Reg$06 (PTB)", "Reg$07 (PTC)", "Reg$08", "Reg$09", "Reg$0A", "Reg$0B", "Reg$0C", "Reg$0D", "Reg$0E", "Reg$0F", "Reg$10", "Reg$11", "Reg$12", "Reg$13", "Reg$14", "Reg$15", "Reg$16", "Reg$17", "Reg$18", "Reg$19", "Reg$1A", "Reg$1B", "Reg$1C", "Reg$1D", "Reg$1E", "Reg$1F" }; -static const char *const dest[2] = { "W", "Reg" }; - -static const char *const PIC16C5xFormats[] = { - FMT("000000000000", "nop"), - FMT("000000000010", "option"), - FMT("000000000011", "sleep"), - FMT("000000000100", "clrwdt"), - FMT("000000000101", "tris Port A"), - FMT("000000000110", "tris Port B"), - FMT("000000000111", "tris Port C"), - FMT("0000001fffff", "movwf %F"), - FMT("000001000000", "clrw"), - FMT("0000011fffff", "clrf %F"), - FMT("000010dfffff", "subwf %F,%D"), - FMT("000011dfffff", "decf %F,%D"), - FMT("000100dfffff", "iorwf %F,%D"), - FMT("000101dfffff", "andwf %F,%D"), - FMT("000110dfffff", "xorwf %F,%D"), - FMT("000111dfffff", "addwf %F,%D"), - FMT("001000dfffff", "movf %F,%D"), - FMT("001001dfffff", "comf %F,%D"), - FMT("001010dfffff", "incf %F,%D"), - FMT("001011dfffff", "decfsz %F,%D"), - FMT("001100dfffff", "rrf %F,%D"), - FMT("001101dfffff", "rlf %F,%D"), - FMT("001110dfffff", "swapf %F,%D"), - FMT("001111dfffff", "incfsz %F,%D"), - FMT("0100bbbfffff", "bcf %F,%B"), - FMT("0101bbbfffff", "bsf %F,%B"), - FMT("0110bbbfffff", "btfsc %F,%B"), - FMT("0111bbbfffff", "btfss %F,%B"), - FMT("1000kkkkkkkk", "retlw %K"), - FMT("1001aaaaaaaa", "call %A"), - FMT("101aaaaaaaaa", "goto %A"), - FMT("1100kkkkkkkk", "movlw %K"), - FMT("1101kkkkkkkk", "iorlw %K"), - FMT("1110kkkkkkkk", "andlw %K"), - FMT("1111kkkkkkkk", "xorlw %K"), +const char *const pic16c5x_disassembler::dest[2] = { "W", "Reg" }; + +const char *const pic16c5x_disassembler::PIC16C5xFormats[] = { + "000000000000", "nop", + "000000000010", "option", + "000000000011", "sleep", + "000000000100", "clrwdt", + "000000000101", "tris Port A", + "000000000110", "tris Port B", + "000000000111", "tris Port C", + "0000001fffff", "movwf %F", + "000001000000", "clrw", + "0000011fffff", "clrf %F", + "000010dfffff", "subwf %F,%D", + "000011dfffff", "decf %F,%D", + "000100dfffff", "iorwf %F,%D", + "000101dfffff", "andwf %F,%D", + "000110dfffff", "xorwf %F,%D", + "000111dfffff", "addwf %F,%D", + "001000dfffff", "movf %F,%D", + "001001dfffff", "comf %F,%D", + "001010dfffff", "incf %F,%D", + "001011dfffff", "decfsz %F,%D", + "001100dfffff", "rrf %F,%D", + "001101dfffff", "rlf %F,%D", + "001110dfffff", "swapf %F,%D", + "001111dfffff", "incfsz %F,%D", + "0100bbbfffff", "bcf %F,%B", + "0101bbbfffff", "bsf %F,%B", + "0110bbbfffff", "btfsc %F,%B", + "0111bbbfffff", "btfss %F,%B", + "1000kkkkkkkk", "retlw %K", + "1001aaaaaaaa", "call %A", + "101aaaaaaaaa", "goto %A", + "1100kkkkkkkk", "movlw %K", + "1101kkkkkkkk", "iorlw %K", + "1110kkkkkkkk", "andlw %K", + "1111kkkkkkkk", "xorlw %K", nullptr }; -#define MAX_OPS ((ARRAY_LENGTH(PIC16C5xFormats) - 1) / PTRS_PER_FORMAT) - -struct PIC16C5xOpcode { - word mask; /* instruction mask */ - word bits; /* constant bits */ - word extcode; /* value that gets extension code */ - const char *parse; /* how to parse bits */ - const char *fmt; /* instruction format */ -}; - -static PIC16C5xOpcode Op[MAX_OPS+1]; -static int OpInizialized = 0; - -static void InitDasm16C5x(void) +pic16c5x_disassembler::pic16c5x_disassembler() { const char *p; const char *const *ops; - word mask, bits; + u16 mask, bits; int bit; int i; @@ -136,20 +110,14 @@ static void InitDasm16C5x(void) ops[0],ops[1],bit); } while (isspace((uint8_t)*p)) p++; - if (*p) Op[i].extcode = *p; - Op[i].bits = bits; - Op[i].mask = mask; - Op[i].fmt = ops[1]; - Op[i].parse = ops[0]; + Op.emplace_back(bits, mask, *p, ops[0], ops[1]); - ops += PTRS_PER_FORMAT; + ops += 2; i++; } - - OpInizialized = 1; } -CPU_DISASSEMBLE(pic16c5x) +offs_t pic16c5x_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { int a, b, d, f, k; /* these can all be filled in by parsing an instruction */ int i; @@ -161,15 +129,9 @@ CPU_DISASSEMBLE(pic16c5x) const char *cp; /* character pointer in OpFormats */ uint32_t flags = 0; - rombase = oprom; - rambase = opram; - pcbase = 2*pc; - - if (!OpInizialized) InitDasm16C5x(); - op = -1; /* no matching opcode */ - code = READOP16(2*pc); - for ( i = 0; i < MAX_OPS; i++) + code = opcodes.r16(pc); + for ( i = 0; i < int(Op.size()); i++) { if ((code & Op[i].mask) == Op[i].bits) { @@ -184,14 +146,14 @@ CPU_DISASSEMBLE(pic16c5x) if (op == -1) { util::stream_format(stream, "???? dw %04Xh",code); - return cnt; + return cnt | SUPPORTED; } //buffertmp = buffer; if (Op[op].extcode) /* Actually, theres no double length opcodes */ { bit = 27; code <<= 16; - code |= READARG16(2*(pc+cnt)); + code |= params.r16(pc+cnt); cnt++; } else @@ -223,9 +185,9 @@ CPU_DISASSEMBLE(pic16c5x) /* now traverse format string */ cp = Op[op].fmt; if (!strncmp(cp, "call", 4)) - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; else if (!strncmp(cp, "ret", 3)) - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; while (*cp) { @@ -248,5 +210,10 @@ CPU_DISASSEMBLE(pic16c5x) stream << *cp++; } } - return cnt | flags | DASMFLAG_SUPPORTED; + return cnt | flags | SUPPORTED; +} + +uint32_t pic16c5x_disassembler::opcode_alignment() const +{ + return 1; } diff --git a/src/devices/cpu/pic16c5x/16c5xdsm.h b/src/devices/cpu/pic16c5x/16c5xdsm.h new file mode 100644 index 00000000000..de3c8b4425f --- /dev/null +++ b/src/devices/cpu/pic16c5x/16c5xdsm.h @@ -0,0 +1,58 @@ +// license:BSD-3-Clause +// copyright-holders:Tony La Porta + /**************************************************************************\ + * Microchip PIC16C5x Emulator * + * * + * Copyright Tony La Porta * + * Originally written for the MAME project. * + * * + * * + * Addressing architecture is based on the Harvard addressing scheme. * + * * + * Many thanks to those involved in the i8039 Disassembler * + * as this was based on it. * + * * + * * + * * + * A Address to jump to. * + * B Bit address within an 8-bit file register. * + * D Destination select (0 = store result in W (accumulator)) * + * (1 = store result in file register) * + * F Register file address (00-1F). * + * K Literal field, constant data. * + * * + \**************************************************************************/ + +#ifndef MAME_CPU_PIC16C5X_16C5XDSM_H +#define MAME_CPU_PIC16C5X_16C5XDSM_H + +#pragma once + +class pic16c5x_disassembler : public util::disasm_interface +{ +public: + pic16c5x_disassembler(); + virtual ~pic16c5x_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + struct PIC16C5xOpcode { + u16 mask; /* instruction mask */ + u16 bits; /* constant bits */ + u16 extcode; /* value that gets extension code */ + const char *parse; /* how to parse bits */ + const char *fmt; /* instruction format */ + + PIC16C5xOpcode(u16 m, u16 b, u16 e, const char *p, const char *f) : mask(m), bits(b), extcode(e), parse(p), fmt(f) {} + }; + + static const char *const regfile[32]; + static const char *const dest[2]; + static const char *const PIC16C5xFormats[]; + + std::vector Op; +}; + +#endif diff --git a/src/devices/cpu/pic16c5x/dis16c5x.cpp b/src/devices/cpu/pic16c5x/dis16c5x.cpp deleted file mode 100644 index 08c7f2657df..00000000000 --- a/src/devices/cpu/pic16c5x/dis16c5x.cpp +++ /dev/null @@ -1,136 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:Tony La Porta - /**************************************************************************\ - * Microchip PIC16C5x Emulator * - * * - * Copyright Tony La Porta * - * Originally written for the MAME project. * - * * - * * - * Notes : Data is expected to be read from source file as LSB first. * - * * - \**************************************************************************/ - -#include -#include - -#include "16c5xdsm.c" - - -unsigned char *Buffer; - - -int main(int argc,char *argv[]) -{ - int length=0, length_to_dump=0, offset=0, disasm_words=0; - int filelength=0, bytes_read; - int Counter=0; - - FILE *F; - char *String_Output; - - if(argc<2) - { - printf("\n"); - printf("PIC16C5x Disassembler 1.0 by Tony La Porta (C)2003+\n\n"); - printf("Usage: dis16c5x [ [ ] ]\n"); - printf(" source file data must be MSB first\n"); - printf(" starting address to disassemble from (decimal)\n"); - printf(" number of addresses to disassemble (decimal)\n"); - printf(" Precede values with 0x if HEX values preffered\n"); - exit(1); - } - - if(!(F=fopen(argv[1],"rb"))) - { - printf("\n%s: Can't open file %s\n",argv[0],argv[1]); - exit(2); - } - argv++; argc--; - if (argv[1]) - { - offset = strtol(argv[1],nullptr,0); - argv++; argc--; - } - if (argv[1]) - { - length = strtol(argv[1],nullptr,0); - argv++; argc--; - } - - fseek(F,0, SEEK_END); - filelength = ftell(F); - - length *= 2; - - if ((length > (filelength - (offset*2))) || (length == 0)) length = filelength - (offset*2); - printf("Length=%04Xh(words) Offset=$%04Xh filelength=%04Xh(words) %04Xh(bytes)\n",length/2,offset,filelength/2,filelength); - length_to_dump = length; - printf("Starting from %d, dumping %d opcodes (word size)\n",offset,length/2); - Buffer = calloc((filelength+1),sizeof(char)); - if (Buffer==nullptr) - { - printf("Out of Memory !!!"); - fclose(F); - exit(3); - } - String_Output = calloc(80,sizeof(char)); - if (String_Output==nullptr) - { - printf("Out of Memory !!!"); - free(Buffer); - fclose(F); - exit(4); - } - - if (fseek(F,0,SEEK_SET) != 0) - { - printf("Error seeking to beginning of file\n"); - free(String_Output); - free(Buffer); - fclose(F); - exit(5); - } - - Counter = offset; - bytes_read = fread(Buffer,sizeof(char),filelength,F); - if (bytes_read >= length) - { - for (; length > 0; length -= (disasm_words*2)) - { - int ii; - disasm_words = Dasm16C5x(String_Output,Counter); - printf("$%03X: ",Counter); - for (ii = 0; ii < disasm_words; ii++) - { - if (((Counter*2) + ii) > filelength) /* Past end of length to dump ? */ - { - sprintf(String_Output,"???? dw %02.2X%02.2Xh (Past end of disassembly !)",Buffer[((Counter-1)*2)+1],Buffer[((Counter-1)*2)]); - } - else - { - printf("%02.2x%02.2x ",Buffer[(Counter*2)+1],Buffer[(Counter*2)]); - } - Counter++ ; - } - for (; ii < 4; ii++) - { - printf(" "); - } - printf("\t%s\n",String_Output); - } - } - else - { - printf("ERROR length to dump was %d ", length_to_dump/2); - printf(", but bytes read from file were %d\n", bytes_read/2); - free(String_Output); - free(Buffer); - fclose(F); - exit(7); - } - free(String_Output); - free(Buffer); - fclose(F); - return(0); -} diff --git a/src/devices/cpu/pic16c5x/pic16c5x.cpp b/src/devices/cpu/pic16c5x/pic16c5x.cpp index 52a9beeac77..0589f9dfadb 100644 --- a/src/devices/cpu/pic16c5x/pic16c5x.cpp +++ b/src/devices/cpu/pic16c5x/pic16c5x.cpp @@ -73,6 +73,7 @@ #include "emu.h" #include "pic16c5x.h" +#include "16c5xdsm.h" #include "debugger.h" @@ -183,10 +184,9 @@ device_memory_interface::space_config_vector pic16c5x_device::memory_space_confi }; } -offs_t pic16c5x_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *pic16c5x_device::create_disassembler() { - extern CPU_DISASSEMBLE( pic16c5x ); - return CPU_DISASSEMBLE_NAME(pic16c5x)(this, stream, pc, oprom, opram, options); + return new pic16c5x_disassembler; } diff --git a/src/devices/cpu/pic16c5x/pic16c5x.h b/src/devices/cpu/pic16c5x/pic16c5x.h index 593397e4847..918f251cdab 100644 --- a/src/devices/cpu/pic16c5x/pic16c5x.h +++ b/src/devices/cpu/pic16c5x/pic16c5x.h @@ -133,9 +133,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 2; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/pic16c62x/16c62xdsm.cpp b/src/devices/cpu/pic16c62x/16c62xdsm.cpp index f9fb88a88d1..8206a362869 100644 --- a/src/devices/cpu/pic16c62x/16c62xdsm.cpp +++ b/src/devices/cpu/pic16c62x/16c62xdsm.cpp @@ -27,93 +27,68 @@ \**************************************************************************/ #include "emu.h" -#include - -static const uint8_t *rombase; -static const uint8_t *rambase; -static offs_t pcbase; -#define READOP16(A) (rombase[(A) - pcbase] | (rombase[(A) + 1 - pcbase] << 8)) -#define READARG16(A) (rambase[(A) - pcbase] | (rambase[(A) + 1 - pcbase] << 8)) - - - -typedef unsigned char byte; -typedef unsigned short int word; +#include "16c62xdsm.h" -#define FMT(a,b) a, b -#define PTRS_PER_FORMAT 2 +#include /* Registers bank 0/1 */ -static const char *const regfile[32] = { "Reg$00 (INDF)", "Reg$01 (TMR0/OPTION)", "Reg$02 (PCL)", "Reg$03 (STATUS)", "Reg$04 (FSR)", "Reg$05 (PORTA/TRISA)", "Reg$06 (PORTB/TRISB)", "Reg$07", +const char *const pic16c62x_disassembler::regfile[32] = { "Reg$00 (INDF)", "Reg$01 (TMR0/OPTION)", "Reg$02 (PCL)", "Reg$03 (STATUS)", "Reg$04 (FSR)", "Reg$05 (PORTA/TRISA)", "Reg$06 (PORTB/TRISB)", "Reg$07", "Reg$08", "Reg$09", "Reg$0A (PCLATH)", "Reg$0B (INTCON)", "Reg$0C (PIR1/PIE1)", "Reg$0D", "Reg$0E (none/PCON)", "Reg$0F", "Reg$10", "Reg$11", "Reg$12", "Reg$13", "Reg$14", "Reg$15", "Reg$16", "Reg$17", "Reg$18", "Reg$19", "Reg$1A", "Reg$1B", "Reg$1C", "Reg$1D", "Reg$1E", "Reg$1F (CMCON/VRCON)" }; /* Registers bank 1 */ -/*static const char *const regfile1[32] = { "Reg$00 (INDF)", "Reg$01 (OPTION)", "Reg$02 (PCL)", "Reg$03 (STATUS)", "Reg$04 (FSR)", "Reg$05 (TRISA)", "Reg$06 (TRISB)", "Reg$07", +/*const char *const regfile1[32] = { "Reg$00 (INDF)", "Reg$01 (OPTION)", "Reg$02 (PCL)", "Reg$03 (STATUS)", "Reg$04 (FSR)", "Reg$05 (TRISA)", "Reg$06 (TRISB)", "Reg$07", "Reg$08", "Reg$09", "Reg$0A (PCLATH)", "Reg$0B (INTCON)", "Reg$0C (PIE1)", "Reg$0D", "Reg$0E (PCON)", "Reg$0F", "Reg$10", "Reg$11", "Reg$12", "Reg$13", "Reg$14", "Reg$15", "Reg$16", "Reg$17", "Reg$18", "Reg$19", "Reg$1A", "Reg$1B", "Reg$1C", "Reg$1D", "Reg$1E", "Reg$1F (VRCON)" }; -static const char **regfile[2] = { regfile0, regfile1 };*/ - -static const char *const dest[2] = { "W", "Reg" }; - -static const char *const PIC16C62xFormats[] = { - FMT("0000000xx00000", "nop"), - FMT("00000000001000", "return"), - FMT("00000000001001", "retfie"), - FMT("00000001100011", "sleep"), - FMT("00000001100100", "clrwdt"), - FMT("0000001fffffff", "movwf %F"), - FMT("00000100000011", "clrw"), - FMT("0000011fffffff", "clrf %F"), - FMT("000010dfffffff", "subwf %F,%D"), - FMT("000011dfffffff", "decf %F,%D"), - FMT("000100dfffffff", "iorwf %F,%D"), - FMT("000101dfffffff", "andwf %F,%D"), - FMT("000110dfffffff", "xorwf %F,%D"), - FMT("000111dfffffff", "addwf %F,%D"), - FMT("001000dfffffff", "movf %F,%D"), - FMT("001001dfffffff", "comf %F,%D"), - FMT("001010dfffffff", "incf %F,%D"), - FMT("001011dfffffff", "decfsz %F,%D"), - FMT("001100dfffffff", "rrf %F,%D"), - FMT("001101dfffffff", "rlf %F,%D"), - FMT("001110dfffffff", "swapf %F,%D"), - FMT("001111dfffffff", "incfsz %F,%D"), - FMT("0100bbbfffffff", "bcf %F,%B"), - FMT("0101bbbfffffff", "bsf %F,%B"), - FMT("0110bbbfffffff", "btfsc %F,%B"), - FMT("0111bbbfffffff", "btfss %F,%B"), - FMT("1101xxkkkkkkkk", "retlw %K"), - FMT("100aaaaaaaaaaa", "call %A"), - FMT("101aaaaaaaaaaa", "goto %A"), - FMT("1100xxkkkkkkkk", "movlw %K"), - FMT("111000kkkkkkkk", "iorlw %K"), - FMT("111001kkkkkkkk", "andlw %K"), - FMT("111010kkkkkkkk", "xorlw %K"), - FMT("11110xkkkkkkkk", "sublw %K"), - FMT("11111xkkkkkkkk", "addlw %K"), +const char **regfile[2] = { regfile0, regfile1 };*/ + +const char *const pic16c62x_disassembler::dest[2] = { "W", "Reg" }; + +const char *const pic16c62x_disassembler::PIC16C62xFormats[] = { + "0000000xx00000", "nop", + "00000000001000", "return", + "00000000001001", "retfie", + "00000001100011", "sleep", + "00000001100100", "clrwdt", + "0000001fffffff", "movwf %F", + "00000100000011", "clrw", + "0000011fffffff", "clrf %F", + "000010dfffffff", "subwf %F,%D", + "000011dfffffff", "decf %F,%D", + "000100dfffffff", "iorwf %F,%D", + "000101dfffffff", "andwf %F,%D", + "000110dfffffff", "xorwf %F,%D", + "000111dfffffff", "addwf %F,%D", + "001000dfffffff", "movf %F,%D", + "001001dfffffff", "comf %F,%D", + "001010dfffffff", "incf %F,%D", + "001011dfffffff", "decfsz %F,%D", + "001100dfffffff", "rrf %F,%D", + "001101dfffffff", "rlf %F,%D", + "001110dfffffff", "swapf %F,%D", + "001111dfffffff", "incfsz %F,%D", + "0100bbbfffffff", "bcf %F,%B", + "0101bbbfffffff", "bsf %F,%B", + "0110bbbfffffff", "btfsc %F,%B", + "0111bbbfffffff", "btfss %F,%B", + "1101xxkkkkkkkk", "retlw %K", + "100aaaaaaaaaaa", "call %A", + "101aaaaaaaaaaa", "goto %A", + "1100xxkkkkkkkk", "movlw %K", + "111000kkkkkkkk", "iorlw %K", + "111001kkkkkkkk", "andlw %K", + "111010kkkkkkkk", "xorlw %K", + "11110xkkkkkkkk", "sublw %K", + "11111xkkkkkkkk", "addlw %K", nullptr }; -#define MAX_OPS ((ARRAY_LENGTH(PIC16C62xFormats) - 1) / PTRS_PER_FORMAT) - -struct PIC16C62xOpcode { - word mask; /* instruction mask */ - word bits; /* constant bits */ - word extcode; /* value that gets extension code */ - const char *parse; /* how to parse bits */ - const char *fmt; /* instruction format */ -}; - -static PIC16C62xOpcode Op[MAX_OPS+1]; -static int OpInizialized = 0; - -static void InitDasm16C5x(void) +pic16c62x_disassembler::pic16c62x_disassembler() { const char *p; const char *const *ops; - word mask, bits; + u16 mask, bits; int bit; int i; @@ -147,20 +122,15 @@ static void InitDasm16C5x(void) ops[0],ops[1],bit); } while (isspace((uint8_t)*p)) p++; - if (*p) Op[i].extcode = *p; - Op[i].bits = bits; - Op[i].mask = mask; - Op[i].fmt = ops[1]; - Op[i].parse = ops[0]; + Op.emplace_back(bits, mask, *p, ops[0], ops[1]); - ops += PTRS_PER_FORMAT; + ops += 2; i++; } - OpInizialized = 1; } -CPU_DISASSEMBLE(pic16c62x) +offs_t pic16c62x_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { int a, b, d, f, k; /* these can all be filled in by parsing an instruction */ int i; @@ -172,15 +142,9 @@ CPU_DISASSEMBLE(pic16c62x) const char *cp; /* character pointer in OpFormats */ uint32_t flags = 0; - rombase = oprom; - rambase = opram; - pcbase = 2*pc; - - if (!OpInizialized) InitDasm16C5x(); - op = -1; /* no matching opcode */ - code = READOP16(2*pc); - for ( i = 0; i < MAX_OPS; i++) + code = opcodes.r16(pc); + for ( i = 0; i < int(Op.size()); i++) { if ((code & Op[i].mask) == Op[i].bits) { @@ -202,7 +166,7 @@ CPU_DISASSEMBLE(pic16c62x) { bit = 29; code <<= 16; - code |= READARG16(2*(pc+cnt)); + code |= params.r16(pc+cnt); cnt++; } else @@ -234,9 +198,9 @@ CPU_DISASSEMBLE(pic16c62x) /* now traverse format string */ cp = Op[op].fmt; if (!strncmp(cp, "call", 4)) - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; else if (!strncmp(cp, "ret", 3)) - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; while (*cp) { @@ -259,5 +223,10 @@ CPU_DISASSEMBLE(pic16c62x) stream << *cp++; } } - return cnt | flags | DASMFLAG_SUPPORTED; + return cnt | flags | SUPPORTED; +} + +uint32_t pic16c62x_disassembler::opcode_alignment() const +{ + return 1; } diff --git a/src/devices/cpu/pic16c62x/16c62xdsm.h b/src/devices/cpu/pic16c62x/16c62xdsm.h new file mode 100644 index 00000000000..a6ae323a59f --- /dev/null +++ b/src/devices/cpu/pic16c62x/16c62xdsm.h @@ -0,0 +1,62 @@ +// license:BSD-3-Clause +// copyright-holders:Tony La Porta + /**************************************************************************\ + * Microchip PIC16C62X Emulator * + * * + * Based On * + * Microchip PIC16C5X Emulator * + * Copyright Tony La Porta * + * Originally written for the MAME project. * + * * + * * + * Addressing architecture is based on the Harvard addressing scheme. * + * * + * Many thanks to those involved in the i8039 Disassembler * + * as this was based on it. * + * * + * * + * * + * A Address to jump to. * + * B Bit address within an 8-bit file register. * + * D Destination select (0 = store result in W (accumulator)) * + * (1 = store result in file register) * + * F Register file address (00-1F). * + * K Literal field, constant data. * + * X Not used * + * * + \**************************************************************************/ + +#ifndef MAME_CPU_PIC16C62X_16C62XDSM_H +#define MAME_CPU_PIC16C62X_16C62XDSM_H + +#pragma once + +class pic16c62x_disassembler : public util::disasm_interface +{ +public: + pic16c62x_disassembler(); + virtual ~pic16c62x_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + struct PIC16C62xOpcode { + u16 mask; /* instruction mask */ + u16 bits; /* constant bits */ + u16 extcode; /* value that gets extension code */ + const char *parse; /* how to parse bits */ + const char *fmt; /* instruction format */ + + PIC16C62xOpcode(u16 m, u16 b, u16 e, const char *p, const char *f) : mask(m), bits(b), extcode(e), parse(p), fmt(f) {} + }; + + static const char *const regfile[32]; + static const char *const dest[2]; + static const char *const PIC16C62xFormats[]; + + std::vector Op; + +}; + +#endif diff --git a/src/devices/cpu/pic16c62x/dis16c62x.cpp b/src/devices/cpu/pic16c62x/dis16c62x.cpp deleted file mode 100644 index 1fb91304dd2..00000000000 --- a/src/devices/cpu/pic16c62x/dis16c62x.cpp +++ /dev/null @@ -1,138 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:Tony La Porta - /**************************************************************************\ - * Microchip PIC16C62X Emulator * - * * - * Based On * - * Microchip PIC16C5X Emulator * - * Copyright Tony La Porta * - * Originally written for the MAME project. * - * * - * * - * Notes : Data is expected to be read from source file as LSB first. * - * * - \**************************************************************************/ - -#include -#include - -#include "16c62xdsm.c" - - -unsigned char *Buffer; - - -int main(int argc,char *argv[]) -{ - int length=0, length_to_dump=0, offset=0, disasm_words=0; - int filelength=0, bytes_read; - int Counter=0; - - FILE *F; - char *String_Output; - - if(argc<2) - { - printf("\n"); - printf("PIC16C5x Disassembler 1.0 by Tony La Porta (C)2003+\n\n"); - printf("Usage: dis16c5x [ [ ] ]\n"); - printf(" source file data must be MSB first\n"); - printf(" starting address to disassemble from (decimal)\n"); - printf(" number of addresses to disassemble (decimal)\n"); - printf(" Precede values with 0x if HEX values preffered\n"); - exit(1); - } - - if(!(F=fopen(argv[1],"rb"))) - { - printf("\n%s: Can't open file %s\n",argv[0],argv[1]); - exit(2); - } - argv++; argc--; - if (argv[1]) - { - offset = strtol(argv[1],nullptr,0); - argv++; argc--; - } - if (argv[1]) - { - length = strtol(argv[1],nullptr,0); - argv++; argc--; - } - - fseek(F,0, SEEK_END); - filelength = ftell(F); - - length *= 2; - - if ((length > (filelength - (offset*2))) || (length == 0)) length = filelength - (offset*2); - printf("Length=%04Xh(words) Offset=$%04Xh filelength=%04Xh(words) %04Xh(bytes)\n",length/2,offset,filelength/2,filelength); - length_to_dump = length; - printf("Starting from %d, dumping %d opcodes (word size)\n",offset,length/2); - Buffer = calloc((filelength+1),sizeof(char)); - if (Buffer==nullptr) - { - printf("Out of Memory !!!"); - fclose(F); - exit(3); - } - String_Output = calloc(80,sizeof(char)); - if (String_Output==nullptr) - { - printf("Out of Memory !!!"); - free(Buffer); - fclose(F); - exit(4); - } - - if (fseek(F,0,SEEK_SET) != 0) - { - printf("Error seeking to beginning of file\n"); - free(String_Output); - free(Buffer); - fclose(F); - exit(5); - } - - Counter = offset; - bytes_read = fread(Buffer,sizeof(char),filelength,F); - if (bytes_read >= length) - { - for (; length > 0; length -= (disasm_words*2)) - { - int ii; - disasm_words = Dasm16C5x(String_Output,Counter); - printf("$%03X: ",Counter); - for (ii = 0; ii < disasm_words; ii++) - { - if (((Counter*2) + ii) > filelength) /* Past end of length to dump ? */ - { - sprintf(String_Output,"???? dw %02.2X%02.2Xh (Past end of disassembly !)",Buffer[((Counter-1)*2)+1],Buffer[((Counter-1)*2)]); - } - else - { - printf("%02.2x%02.2x ",Buffer[(Counter*2)+1],Buffer[(Counter*2)]); - } - Counter++ ; - } - for (; ii < 4; ii++) - { - printf(" "); - } - printf("\t%s\n",String_Output); - } - } - else - { - printf("ERROR length to dump was %d ", length_to_dump/2); - printf(", but bytes read from file were %d\n", bytes_read/2); - free(String_Output); - free(Buffer); - fclose(F); - exit(7); - } - free(String_Output); - free(Buffer); - fclose(F); - return(0); -} diff --git a/src/devices/cpu/pic16c62x/pic16c62x.cpp b/src/devices/cpu/pic16c62x/pic16c62x.cpp index c7943ad8480..cce876a045c 100644 --- a/src/devices/cpu/pic16c62x/pic16c62x.cpp +++ b/src/devices/cpu/pic16c62x/pic16c62x.cpp @@ -54,6 +54,7 @@ #include "emu.h" #include "pic16c62x.h" +#include "16c62xdsm.h" #include "debugger.h" @@ -158,10 +159,9 @@ pic16c622a_device::pic16c622a_device(const machine_config &mconfig, const char * } -offs_t pic16c62x_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *pic16c62x_device::create_disassembler() { - extern CPU_DISASSEMBLE( pic16c62x ); - return CPU_DISASSEMBLE_NAME(pic16c62x)(this, stream, pc, oprom, opram, options); + return new pic16c62x_disassembler; } diff --git a/src/devices/cpu/pic16c62x/pic16c62x.h b/src/devices/cpu/pic16c62x/pic16c62x.h index 0c99e0e67e1..45e4be304f6 100644 --- a/src/devices/cpu/pic16c62x/pic16c62x.h +++ b/src/devices/cpu/pic16c62x/pic16c62x.h @@ -79,9 +79,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 2; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/powerpc/ppc.h b/src/devices/cpu/powerpc/ppc.h index dd09cce15e4..fa3d79d916c 100644 --- a/src/devices/cpu/powerpc/ppc.h +++ b/src/devices/cpu/powerpc/ppc.h @@ -268,9 +268,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 4; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; /* exception types */ enum diff --git a/src/devices/cpu/powerpc/ppc_dasm.cpp b/src/devices/cpu/powerpc/ppc_dasm.cpp index 77f01f9f552..50b015b1aff 100644 --- a/src/devices/cpu/powerpc/ppc_dasm.cpp +++ b/src/devices/cpu/powerpc/ppc_dasm.cpp @@ -16,103 +16,9 @@ */ #include "emu.h" -#include "debugger.h" +#include "ppc_dasm.h" #include "ppccom.h" -/* - * Operand Formats - * - * These convey information on what operand fields are present and how they - * ought to be printed. - * - * I'm fairly certain all of these are used, but that is not guaranteed. - */ - -enum -{ - F_NONE, // - F_LI, // LI*4+PC if AA=0 else LI*4 - F_BCx, // BO, BI, target_addr used only by BCx - F_RT_RA_0_SIMM, // rT, rA|0, SIMM rA|0 means if rA == 0, print 0 - F_ADDIS, // rT, rA, SIMM (printed as unsigned) only used by ADDIS - F_RT_RA_SIMM, // rT, rA, SIMM - F_RA_RT_UIMM, // rA, rT, UIMM - F_CMP_SIMM, // crfD, L, A, SIMM - F_CMP_UIMM, // crfD, L, A, UIMM - F_RT_RA_0_RB, // rT, rA|0, rB - F_RT_RA_RB, // rT, rA, rB - F_RT_D_RA_0, // rT, d(rA|0) - F_RT_D_RA, // rT, d(rA) - F_RA_RT_RB, // rA, rT, rB - F_FRT_D_RA_0, // frT, d(RA|0) - F_FRT_D_RA, // frT, d(RA) - F_FRT_RA_0_RB, // frT, rA|0, rB - F_FRT_RA_RB, // frT, rA, rB - F_TWI, // TO, rA, SIMM only used by TWI instruction - F_CMP, // crfD, L, rA, rB - F_RA_RT, // rA, rT - F_RA_0_RB, // rA|0, rB - F_FRT_FRB, // frT, frB - F_FCMP, // crfD, frA, frB - F_CRFD_CRFS, // crfD, crfS - F_MCRXR, // crfD only used by MCRXR - F_RT, // rT - F_MFSR, // rT, SR only used by MFSR - F_MTSR, // SR, rT only used by MTSR - F_MFFSx, // frT only used by MFFSx - F_FCRBD, // crbD FPSCR[crbD] - F_MTFSFIx, // crfD, IMM only used by MTFSFIx - F_RB, // rB - F_TW, // TO, rA, rB only used by TW - F_RT_RA_0_NB, // rT, rA|0, NB print 32 if NB == 0 - F_SRAWIx, // rA, rT, SH only used by SRAWIx - F_BO_BI, // BO, BI - F_CRBD_CRBA_CRBB, // crbD, crbA, crbB - F_RT_SPR, // rT, SPR and TBR - F_MTSPR, // SPR, rT only used by MTSPR - F_MTCRF, // CRM, rT only used by MTCRF - F_MTFSFx, // FM, frB only used by MTFSFx - F_RT_DCR, // rT, DCR - F_MTDCR, // DCR, rT - F_RT_RA, // rT, rA - F_FRT_FRA_FRC_FRB, // frT, frA, frC, frB - F_FRT_FRA_FRB, // frT, frA, frB - F_FRT_FRA_FRC, // frT, frA, frC - F_RA_RT_SH_MB_ME, // rA, rT, SH, MB, ME - F_RLWNMx, // rT, rA, rB, MB, ME only used by RLWNMx - F_RT_RB // rT, rB -}; - -/* - * Flags - */ - -#define FL_OE (1 << 0) // if there is an OE field -#define FL_RC (1 << 1) // if there is an RC field -#define FL_LK (1 << 2) // if there is an LK field -#define FL_AA (1 << 3) // if there is an AA field -#define FL_CHECK_RA_RT (1 << 4) // assert rA!=0 and rA!=rT -#define FL_CHECK_RA (1 << 5) // assert rA!=0 -#define FL_CHECK_LSWI (1 << 6) // specific check for LSWI validity -#define FL_CHECK_LSWX (1 << 7) // specific check for LSWX validity -#define FL_SO (1 << 8) // use DASMFLAG_STEP_OUT - - -/* - * Instruction Descriptor - * - * Describes the layout of an instruction. - */ - -struct IDESCR -{ - char mnem[32]; // mnemonic - uint32_t match; // bit pattern of instruction after it has been masked - uint32_t mask; // mask of variable fields (AND with ~mask to compare w/ - // bit pattern to determine a match) - int format; // operand format - int flags; // flags -}; /* * Instruction Table @@ -121,7 +27,7 @@ struct IDESCR * and print instructions. */ -static const IDESCR itab[] = +const powerpc_disassembler::IDESCR powerpc_disassembler::itab[] = { { "add", D_OP(31)|D_XO(266), M_RT|M_RA|M_RB|M_OE|M_RC, F_RT_RA_RB, FL_OE|FL_RC }, { "addc", D_OP(31)|D_XO(10), M_RT|M_RA|M_RB|M_OE|M_RC, F_RT_RA_RB, FL_OE|FL_RC }, @@ -342,18 +248,18 @@ static const IDESCR itab[] = * Use an index of BI&3 into this table to obtain the CR field bit name. */ -static const char *const crbit[4] = { "lt", "gt", "eq", "so" }; -static const char *const crnbit[4] = { "ge", "le", "ne", "nso" }; +const char *const powerpc_disassembler::crbit[4] = { "lt", "gt", "eq", "so" }; +const char *const powerpc_disassembler::crnbit[4] = { "ge", "le", "ne", "nso" }; /* * SPR(): * - * Decode the SPR (or TBR) field and append the register name to dest. If - * no name is associated with the field value, the value itself is printed. + * Decode the SPR (or TBR) field and return the register name. If + * no name is associated with the field value, return the value itself. */ -static void SPR(char *dest, int spr_field) +std::string powerpc_disassembler::SPR(int spr_field) { int spr; @@ -371,93 +277,93 @@ static void SPR(char *dest, int spr_field) switch (spr) { /* UISA SPR register indexes */ - case SPR_XER: strcat(dest, "xer"); break; - case SPR_LR: strcat(dest, "lr"); break; - case SPR_CTR: strcat(dest, "ctr"); break; + case SPR_XER: return "xer"; + case SPR_LR: return "lr"; + case SPR_CTR: return "ctr"; /* VEA SPR register indexes */ - case SPRVEA_TBL_R: strcat(dest, "tbl"); break; - case SPRVEA_TBU_R: strcat(dest, "tbu"); break; + case SPRVEA_TBL_R: return "tbl"; + case SPRVEA_TBU_R: return "tbu"; /* OEA SPR register indexes */ - case SPROEA_DSISR: strcat(dest, "dsisr"); break; - case SPROEA_DAR: strcat(dest, "dar"); break; - case SPROEA_DEC: strcat(dest, "dec"); break; - case SPROEA_SDR1: strcat(dest, "sdr1"); break; - case SPROEA_SRR0: strcat(dest, "srr0"); break; - case SPROEA_SRR1: strcat(dest, "srr1"); break; - case SPROEA_SPRG0: strcat(dest, "sprg0"); break; - case SPROEA_SPRG1: strcat(dest, "sprg1"); break; - case SPROEA_SPRG2: strcat(dest, "sprg2"); break; - case SPROEA_SPRG3: strcat(dest, "sprg3"); break; - case SPROEA_ASR: strcat(dest, "asr"); break; - case SPROEA_EAR: strcat(dest, "ear"); break; - case SPROEA_PVR: strcat(dest, "pvr"); break; - case SPROEA_IBAT0U: strcat(dest, "ibat0u"); break; - case SPROEA_IBAT0L: strcat(dest, "ibat0l"); break; - case SPROEA_IBAT1U: strcat(dest, "ibat1u"); break; - case SPROEA_IBAT1L: strcat(dest, "ibat1l"); break; - case SPROEA_IBAT2U: strcat(dest, "ibat2u"); break; - case SPROEA_IBAT2L: strcat(dest, "ibat2l"); break; - case SPROEA_IBAT3U: strcat(dest, "ibat3u"); break; - case SPROEA_IBAT3L: strcat(dest, "ibat3l"); break; - case SPROEA_DBAT0U: strcat(dest, "dbat0u"); break; - case SPROEA_DBAT0L: strcat(dest, "dbat0l"); break; - case SPROEA_DBAT1U: strcat(dest, "dbat1u"); break; - case SPROEA_DBAT1L: strcat(dest, "dbat1l"); break; - case SPROEA_DBAT2U: strcat(dest, "dbat2u"); break; - case SPROEA_DBAT2L: strcat(dest, "dbat2l"); break; - case SPROEA_DBAT3U: strcat(dest, "dbat3u"); break; - case SPROEA_DBAT3L: strcat(dest, "dbat3l"); break; - case SPROEA_DABR: strcat(dest, "dabr/iac2"); break; // unsupported on 603e/EC603e + case SPROEA_DSISR: return "dsisr"; + case SPROEA_DAR: return "dar"; + case SPROEA_DEC: return "dec"; + case SPROEA_SDR1: return "sdr1"; + case SPROEA_SRR0: return "srr0"; + case SPROEA_SRR1: return "srr1"; + case SPROEA_SPRG0: return "sprg0"; + case SPROEA_SPRG1: return "sprg1"; + case SPROEA_SPRG2: return "sprg2"; + case SPROEA_SPRG3: return "sprg3"; + case SPROEA_ASR: return "asr"; + case SPROEA_EAR: return "ear"; + case SPROEA_PVR: return "pvr"; + case SPROEA_IBAT0U: return "ibat0u"; + case SPROEA_IBAT0L: return "ibat0l"; + case SPROEA_IBAT1U: return "ibat1u"; + case SPROEA_IBAT1L: return "ibat1l"; + case SPROEA_IBAT2U: return "ibat2u"; + case SPROEA_IBAT2L: return "ibat2l"; + case SPROEA_IBAT3U: return "ibat3u"; + case SPROEA_IBAT3L: return "ibat3l"; + case SPROEA_DBAT0U: return "dbat0u"; + case SPROEA_DBAT0L: return "dbat0l"; + case SPROEA_DBAT1U: return "dbat1u"; + case SPROEA_DBAT1L: return "dbat1l"; + case SPROEA_DBAT2U: return "dbat2u"; + case SPROEA_DBAT2L: return "dbat2l"; + case SPROEA_DBAT3U: return "dbat3u"; + case SPROEA_DBAT3L: return "dbat3l"; + case SPROEA_DABR: return "dabr/iac2"; // unsupported on 603e/EC603e /* PowerPC 603E SPR register indexes */ - case SPR603_HID0: strcat(dest, "hid0/dbsr"); break; - case SPR603_HID1: strcat(dest, "hid1"); break; - case SPR603_DMISS: strcat(dest, "dmiss"); break; - case SPR603_DCMP: strcat(dest, "dcmp"); break; - case SPR603_HASH1: strcat(dest, "hash1"); break; - case SPR603_HASH2: strcat(dest, "hash2/icdbdr"); break; - case SPR603_IMISS: strcat(dest, "imiss"); break; - case SPR603_ICMP: strcat(dest, "icmp/dear"); break; - case SPR603_RPA: strcat(dest, "rpa/evpr"); break; - case SPR603_IABR: strcat(dest, "iabr/dbcr"); break; + case SPR603_HID0: return "hid0/dbsr"; + case SPR603_HID1: return "hid1"; + case SPR603_DMISS: return "dmiss"; + case SPR603_DCMP: return "dcmp"; + case SPR603_HASH1: return "hash1"; + case SPR603_HASH2: return "hash2/icdbdr"; + case SPR603_IMISS: return "imiss"; + case SPR603_ICMP: return "icmp/dear"; + case SPR603_RPA: return "rpa/evpr"; + case SPR603_IABR: return "iabr/dbcr"; /* PowerPC 4XX SPR register indexes */ - case SPR4XX_SGR: strcat(dest, "sgr"); break; - case SPR4XX_DCWR: strcat(dest, "dcwr"); break; - case SPR4XX_PID: strcat(dest, "pid"); break; - case SPR4XX_TBHU: strcat(dest, "tbhu"); break; - case SPR4XX_TBLU: strcat(dest, "tblu"); break; -// case SPR4XX_ICDBDR: strcat(dest, "icdbdr"); break; // same as SPR603E_HASH2 -// case SPR4XX_DEAR: strcat(dest, "dear"); break; // same as SPR603E_ICMP -// case SPR4XX_EVPR: strcat(dest, "evpr"); break; // same as SPR603E_RPA - case SPR4XX_CDBCR: strcat(dest, "cdbcr"); break; - case SPR4XX_TSR: strcat(dest, "tsr"); break; - case SPR4XX_TCR: strcat(dest, "tcr"); break; - case SPR4XX_PIT: strcat(dest, "pit"); break; - case SPR4XX_TBHI: strcat(dest, "tbhi"); break; - case SPR4XX_TBLO: strcat(dest, "tblo"); break; - case SPR4XX_SRR2: strcat(dest, "srr2"); break; - case SPR4XX_SRR3: strcat(dest, "srr3"); break; -// case SPR4XX_DBSR: strcat(dest, "dbsr"); break; // same as SPR603E_HID0 -// case SPR4XX_DBCR: strcat(dest, "dbcr"); break; // same as SPR603E_IABR - case SPR4XX_IAC1: strcat(dest, "iac1"); break; -// case SPR4XX_IAC2: strcat(dest, "iac2"); break; // same as SPROEA_DABR - case SPR4XX_DAC1: strcat(dest, "dac1"); break; - case SPR4XX_DAC2: strcat(dest, "dac2"); break; - case SPR4XX_DCCR: strcat(dest, "dccr"); break; - case SPR4XX_ICCR: strcat(dest, "iccr"); break; - case SPR4XX_PBL1: strcat(dest, "pbl1"); break; - case SPR4XX_PBU1: strcat(dest, "pbu1"); break; - case SPR4XX_PBL2: strcat(dest, "pbl2"); break; - case SPR4XX_PBU2: strcat(dest, "pbu2"); break; - - default: sprintf(dest + strlen(dest), "%d", spr); break; + case SPR4XX_SGR: return "sgr"; + case SPR4XX_DCWR: return "dcwr"; + case SPR4XX_PID: return "pid"; + case SPR4XX_TBHU: return "tbhu"; + case SPR4XX_TBLU: return "tblu"; +// case SPR4XX_ICDBDR: return "icdbdr"; // same as SPR603E_HASH2 +// case SPR4XX_DEAR: return "dear"; // same as SPR603E_ICMP +// case SPR4XX_EVPR: return "evpr"; // same as SPR603E_RPA + case SPR4XX_CDBCR: return "cdbcr"; + case SPR4XX_TSR: return "tsr"; + case SPR4XX_TCR: return "tcr"; + case SPR4XX_PIT: return "pit"; + case SPR4XX_TBHI: return "tbhi"; + case SPR4XX_TBLO: return "tblo"; + case SPR4XX_SRR2: return "srr2"; + case SPR4XX_SRR3: return "srr3"; +// case SPR4XX_DBSR: return "dbsr"; // same as SPR603E_HID0 +// case SPR4XX_DBCR: return "dbcr"; // same as SPR603E_IABR + case SPR4XX_IAC1: return "iac1"; +// case SPR4XX_IAC2: return "iac2"; // same as SPROEA_DABR + case SPR4XX_DAC1: return "dac1"; + case SPR4XX_DAC2: return "dac2"; + case SPR4XX_DCCR: return "dccr"; + case SPR4XX_ICCR: return "iccr"; + case SPR4XX_PBL1: return "pbl1"; + case SPR4XX_PBU1: return "pbu1"; + case SPR4XX_PBL2: return "pbl2"; + case SPR4XX_PBU2: return "pbu2"; + + default: return util::string_format("%d", spr); } } -static void DCR(char *dest, int dcr_field) +std::string powerpc_disassembler::DCR(int dcr_field) { int dcr; @@ -474,50 +380,50 @@ static void DCR(char *dest, int dcr_field) switch (dcr) { - case 144: strcat(dest, "bear"); break; - case 145: strcat(dest, "besr"); break; - case 128: strcat(dest, "br0"); break; - case 129: strcat(dest, "br1"); break; - case 130: strcat(dest, "br2"); break; - case 131: strcat(dest, "br3"); break; - case 132: strcat(dest, "br4"); break; - case 133: strcat(dest, "br5"); break; - case 134: strcat(dest, "br6"); break; - case 135: strcat(dest, "br7"); break; - case 112: strcat(dest, "brh0"); break; - case 113: strcat(dest, "brh1"); break; - case 114: strcat(dest, "brh2"); break; - case 115: strcat(dest, "brh3"); break; - case 116: strcat(dest, "brh4"); break; - case 117: strcat(dest, "brh5"); break; - case 118: strcat(dest, "brh6"); break; - case 119: strcat(dest, "brh7"); break; - case 196: strcat(dest, "dmacc0"); break; - case 204: strcat(dest, "dmacc1"); break; - case 212: strcat(dest, "dmacc2"); break; - case 220: strcat(dest, "dmacc3"); break; - case 192: strcat(dest, "dmacr0"); break; - case 200: strcat(dest, "dmacr1"); break; - case 208: strcat(dest, "dmacr2"); break; - case 216: strcat(dest, "dmacr3"); break; - case 193: strcat(dest, "dmact0"); break; - case 201: strcat(dest, "dmact1"); break; - case 209: strcat(dest, "dmact2"); break; - case 217: strcat(dest, "dmact3"); break; - case 194: strcat(dest, "dmada0"); break; - case 202: strcat(dest, "dmada1"); break; - case 210: strcat(dest, "dmada2"); break; - case 218: strcat(dest, "dmada3"); break; - case 195: strcat(dest, "dmasa0"); break; - case 203: strcat(dest, "dmasa1"); break; - case 211: strcat(dest, "dmasa2"); break; - case 219: strcat(dest, "dmasa3"); break; - case 224: strcat(dest, "dmasr"); break; - case 66: strcat(dest, "exier"); break; - case 64: strcat(dest, "exisr"); break; - case 160: strcat(dest, "iocr"); break; - - default: sprintf(dest + strlen(dest), "%d", dcr); break; + case 144: return "bear"; + case 145: return "besr"; + case 128: return "br0"; + case 129: return "br1"; + case 130: return "br2"; + case 131: return "br3"; + case 132: return "br4"; + case 133: return "br5"; + case 134: return "br6"; + case 135: return "br7"; + case 112: return "brh0"; + case 113: return "brh1"; + case 114: return "brh2"; + case 115: return "brh3"; + case 116: return "brh4"; + case 117: return "brh5"; + case 118: return "brh6"; + case 119: return "brh7"; + case 196: return "dmacc0"; + case 204: return "dmacc1"; + case 212: return "dmacc2"; + case 220: return "dmacc3"; + case 192: return "dmacr0"; + case 200: return "dmacr1"; + case 208: return "dmacr2"; + case 216: return "dmacr3"; + case 193: return "dmact0"; + case 201: return "dmact1"; + case 209: return "dmact2"; + case 217: return "dmact3"; + case 194: return "dmada0"; + case 202: return "dmada1"; + case 210: return "dmada2"; + case 218: return "dmada3"; + case 195: return "dmasa0"; + case 203: return "dmasa1"; + case 211: return "dmasa2"; + case 219: return "dmasa3"; + case 224: return "dmasr"; + case 66: return "exier"; + case 64: return "exisr"; + case 160: return "iocr"; + + default: return util::string_format("%d", dcr); } } @@ -529,22 +435,22 @@ static void DCR(char *dest, int dcr_field) * unsigned 16-bit integer. */ -static void DecodeSigned16(char *outbuf, uint32_t op, int do_unsigned) +std::string powerpc_disassembler::DecodeSigned16(uint32_t op, int do_unsigned) { int16_t s; s = G_SIMM(op); if (do_unsigned) // sign extend to unsigned 32-bits - sprintf(outbuf, "0x%04X", (uint32_t) s); + return util::string_format("0x%04X", (uint32_t) s); else // print as signed 16 bits { if (s < 0) { s *= -1; - sprintf(outbuf, "-0x%04X", s); + return util::string_format("-0x%04X", s); } else - sprintf(outbuf, "0x%04X",s); + return util::string_format("0x%04X",s); } } @@ -554,7 +460,7 @@ static void DecodeSigned16(char *outbuf, uint32_t op, int do_unsigned) * Generate a mask from bit MB through ME (PPC-style backwards bit numbering.) */ -static uint32_t Mask(int mb, int me) +uint32_t powerpc_disassembler::Mask(int mb, int me) { uint32_t i, mask; @@ -574,77 +480,14 @@ static uint32_t Mask(int mb, int me) return mask; } -/* - * Check(): - * - * Perform checks on the instruction as required by the flags. Returns 1 if - * the instruction failed. - */ - -#if 0 -static int Check(uint32_t op, int flags) -{ - int nb, rt, ra; - - if( !flags ) return 0; // nothing to check for! - - rt = G_RT(op); - ra = G_RA(op); - - if (flags & FL_CHECK_RA_RT) // invalid if rA==0 or rA==rT - { - if ((G_RA(op) == 0) || (G_RA(op) == G_RT(op))) - return 1; - } - - if (flags & FL_CHECK_RA) // invalid if rA==0 - { - if (G_RA(op) == 0) - return 1; - } - - if (flags & FL_CHECK_LSWI) - { - /* - * Check that rA is not in the range of registers to be loaded (even - * if rA == 0) - */ - - nb = G_NB(op); - - if (ra >= rt && ra <= (rt + nb - 1)) return 1; - if ((rt + nb - 1) > 31) // register wrap-around! - { - if (ra < ((rt + nb - 1) - 31)) - return 1; - } - } - - if (flags & FL_CHECK_LSWX) - { - /* - * Check that rT != rA, rT != rB, and rD and rA both do not specify - * R0. - * - * We cannot check fully whether rA or rB are in the range of - * registers specified to be loaded because that depends on XER. - */ - - if (rt == ra || rt == G_RB(op) || ((rt == 0) && (ra == 0))) - return 1; - } - - return 0; // passed checks -} -#endif /* * Simplified(): * - * Handles all simplified instruction forms. Returns 1 if one was decoded, - * otherwise 0 to indicate disassembly should carry on as normal. + * Handles all simplified instruction forms. Returns true if one was decoded, + * otherwise false to indicate disassembly should carry on as normal. */ -static int Simplified(uint32_t op, uint32_t vpc, char *signed16, char *mnem, char *oprs) +bool powerpc_disassembler::Simplified(uint32_t op, uint32_t vpc, std::string &signed16, std::string &mnem, std::string &oprs) { uint32_t value, disp; @@ -653,96 +496,96 @@ static int Simplified(uint32_t op, uint32_t vpc, char *signed16, char *mnem, cha value |= 0xffff0000; if (op == (D_OP(24)|D_RT(0)|D_RA(0)|D_UIMM(0))) - strcat(mnem, "nop"); // ori r0,r0,0 -> nop + mnem += "nop"; // ori r0,r0,0 -> nop else if ((op & ~(M_RT|M_RA|M_RB|M_RC)) == (D_OP(31)|D_XO(444))) { if (G_RT(op) == G_RB(op)) { - strcat(mnem, "mr"); // orx rA,rT,rT -> mrx rA,rT - if (op & M_RC) strcat(mnem, "."); - sprintf(oprs, "r%d,r%d", G_RA(op), G_RT(op)); + mnem += "mr"; // orx rA,rT,rT -> mrx rA,rT + if (op & M_RC) mnem += "."; + oprs = util::string_format("r%d,r%d", G_RA(op), G_RT(op)); } else - return 0; + return false; } else if ((op & ~(M_RT|M_RA|M_RB|M_RC)) == (D_OP(31)|D_XO(124))) { if (G_RT(op) == G_RB(op)) { - strcat(mnem, "not"); // nor rA,rT,rT -> not rA,rT - if (op & M_RC) strcat(mnem, "."); - sprintf(oprs, "r%d,r%d", G_RA(op), G_RT(op)); + mnem += "not"; // nor rA,rT,rT -> not rA,rT + if (op & M_RC) mnem += "."; + oprs = util::string_format("r%d,r%d", G_RA(op), G_RT(op)); } else - return 0; + return false; } else if ((op & ~(M_RT|M_RA|M_SIMM)) == D_OP(14)) { if (G_RA(op) == 0) { - strcat(mnem, "li"); // addi rT,0,value -> li rT,value - sprintf(oprs, "r%d,0x%08X", G_RT(op), value); + mnem += "li"; // addi rT,0,value -> li rT,value + oprs = util::string_format("r%d,0x%08X", G_RT(op), value); } else - return 0; + return false; } else if ((op & ~(M_RT|M_RA|M_SIMM)) == D_OP(15)) { if (G_RA(op) == 0) { - strcat(mnem, "li"); // addis rT,0,value -> li rT,(value<<16) - sprintf(oprs, "r%d,0x%08X", G_RT(op), value << 16); + mnem += "li"; // addis rT,0,value -> li rT,(value<<16) + oprs = util::string_format("r%d,0x%08X", G_RT(op), value << 16); } else { - strcat(mnem, "addi"); // addis rT,rA,SIMM -> addi rT,rA,SIMM<<16 - sprintf(oprs, "r%d,r%d,0x%08X", G_RT(op), G_RA(op), value << 16); + mnem += "addi"; // addis rT,rA,SIMM -> addi rT,rA,SIMM<<16 + oprs = util::string_format("r%d,r%d,0x%08X", G_RT(op), G_RA(op), value << 16); } } else if ((op & ~(M_RT|M_RA|M_UIMM)) == D_OP(29)) { - strcat(mnem, "andi."); // andis. rA,rT,UIMM -> andi. rA,rT,UIMM<<16 - sprintf(oprs, "r%d,r%d,0x%08X", G_RA(op), G_RT(op), G_UIMM(op) << 16); + mnem += "andi."; // andis. rA,rT,UIMM -> andi. rA,rT,UIMM<<16 + oprs = util::string_format("r%d,r%d,0x%08X", G_RA(op), G_RT(op), G_UIMM(op) << 16); } else if ((op & ~(M_RT|M_RA|M_UIMM)) == D_OP(25)) { - strcat(mnem, "ori"); // oris rA,rT,UIMM -> ori rA,rT,UIMM<<16 - sprintf(oprs, "r%d,r%d,0x%08X", G_RA(op), G_RT(op), G_UIMM(op) << 16); + mnem += "ori"; // oris rA,rT,UIMM -> ori rA,rT,UIMM<<16 + oprs = util::string_format("r%d,r%d,0x%08X", G_RA(op), G_RT(op), G_UIMM(op) << 16); } else if ((op & ~(M_RT|M_RA|M_UIMM)) == D_OP(27)) { - strcat(mnem, "xori"); // xoris rA,rT,UIMM -> xori rA,rT,UIMM<<16 - sprintf(oprs, "r%d,r%d,0x%08X", G_RA(op), G_RT(op), G_UIMM(op) << 16); + mnem += "xori"; // xoris rA,rT,UIMM -> xori rA,rT,UIMM<<16 + oprs = util::string_format("r%d,r%d,0x%08X", G_RA(op), G_RT(op), G_UIMM(op) << 16); } else if ((op & ~(M_RT|M_RA|M_SH|M_MB|M_ME|M_RC)) == D_OP(20)) { value = Mask(G_MB(op), G_ME(op)); - strcat(mnem, "rlwimi"); // rlwimi[.] rA,rT,SH,MB,ME -> rlwimi[.] rA,rT,SH,MASK - if (op & M_RC) strcat(mnem, "."); - sprintf(oprs, "r%d,r%d,%d,0x%08X", G_RA(op), G_RT(op), G_SH(op), value); + mnem += "rlwimi"; // rlwimi[.] rA,rT,SH,MB,ME -> rlwimi[.] rA,rT,SH,MASK + if (op & M_RC) mnem += "."; + oprs = util::string_format("r%d,r%d,%d,0x%08X", G_RA(op), G_RT(op), G_SH(op), value); } else if ((op & ~(M_RT|M_RA|M_SH|M_MB|M_ME|M_RC)) == D_OP(21)) { value = Mask(G_MB(op), G_ME(op)); if (G_SH(op) == 0) // rlwinm[.] rA,rT,0,MB,ME -> and[.] rA,rT,MASK { - strcat(mnem, "and"); - if (op & M_RC) strcat(mnem, "."); - sprintf(oprs, "r%d,r%d,0x%08X", G_RA(op), G_RT(op), value); + mnem += "and"; + if (op & M_RC) mnem += "."; + oprs = util::string_format("r%d,r%d,0x%08X", G_RA(op), G_RT(op), value); } else // rlwinm[.] rA,rT,SH,MASK { - strcat(mnem, "rlwinm"); - if (op & M_RC) strcat(mnem, "."); - sprintf(oprs, "r%d,r%d,%d,0x%08X", G_RA(op), G_RT(op), G_SH(op), value); + mnem += "rlwinm"; + if (op & M_RC) mnem += "."; + oprs = util::string_format("r%d,r%d,%d,0x%08X", G_RA(op), G_RT(op), G_SH(op), value); } } else if ((op & ~(M_RT|M_RA|M_RB|M_MB|M_ME|M_RC)) == D_OP(23)) { value = Mask(G_MB(op), G_ME(op)); - strcat(mnem, "rlwnm"); // rlwnm[.] rA,rT,SH,MB,ME -> rlwnm[.] rA,rT,SH,MASK - if (op & M_RC) strcat(mnem, "."); - sprintf(oprs, "r%d,r%d,r%d,0x%08X", G_RA(op), G_RT(op), G_RB(op), value); + mnem += "rlwnm"; // rlwnm[.] rA,rT,SH,MB,ME -> rlwnm[.] rA,rT,SH,MASK + if (op & M_RC) mnem += "."; + oprs = util::string_format("r%d,r%d,r%d,0x%08X", G_RA(op), G_RT(op), G_RB(op), value); } else if ((op & ~(M_BO|M_BI|M_BD|M_AA|M_LK)) == D_OP(16)) { @@ -753,105 +596,100 @@ static int Simplified(uint32_t op, uint32_t vpc, char *signed16, char *mnem, cha switch (G_BO(op)) { case 0x04: case 0x05: case 0x06: case 0x07: - strcat(mnem, "b"); - strcat(mnem, crnbit[G_BI(op) & 3]); + mnem += "b"; + mnem += crnbit[G_BI(op) & 3]; break; case 0x0c: case 0x0d: case 0x0e: case 0x0f: - strcat(mnem, "b"); - strcat(mnem, crbit[G_BI(op) & 3]); + mnem += "b"; + mnem += crbit[G_BI(op) & 3]; break; case 0x10: case 0x11: case 0x18: case 0x19: - strcat(mnem, "bdnz"); + mnem += "bdnz"; break; case 0x12: case 0x13: case 0x1a: case 0x1b: - strcat(mnem, "bdz"); + mnem += "bdz"; break; case 0x14: case 0x15: case 0x16: case 0x17: case 0x1c: case 0x1d: case 0x1e: case 0x1f: - strcat(mnem, "b"); + mnem += "b"; break; default: - return 0; + return false; } - if (op & M_LK) strcat(mnem, "l"); - if (op & M_AA) strcat(mnem, "a"); + if (op & M_LK) mnem += "l"; + if (op & M_AA) mnem += "a"; if (!(G_BO(op) & 0x10) && G_BI(op) / 4 != 0) - sprintf(oprs, "cr%d,0x%08X", G_BI(op) / 4, disp + ((op & M_AA) ? 0 : vpc)); + oprs = util::string_format("cr%d,0x%08X", G_BI(op) / 4, disp + ((op & M_AA) ? 0 : vpc)); else - sprintf(oprs, "0x%08X", disp + ((op & M_AA) ? 0 : vpc)); + oprs = util::string_format("0x%08X", disp + ((op & M_AA) ? 0 : vpc)); } else if ((op & ~(M_BO|M_BI|M_LK)) == (D_OP(19)|D_XO(528)) || (op & ~(M_BO|M_BI|M_LK)) == (D_OP(19)|D_XO(16))) { switch (G_BO(op)) { case 0x04: case 0x05: case 0x06: case 0x07: - strcat(mnem, "b"); - strcat(mnem, crnbit[G_BI(op) & 3]); + mnem += "b"; + mnem += crnbit[G_BI(op) & 3]; break; case 0x0c: case 0x0d: case 0x0e: case 0x0f: - strcat(mnem, "b"); - strcat(mnem, crbit[G_BI(op) & 3]); + mnem += "b"; + mnem += crbit[G_BI(op) & 3]; break; case 0x10: case 0x11: case 0x18: case 0x19: - strcat(mnem, "bdnz"); + mnem += "bdnz"; break; case 0x12: case 0x13: case 0x1a: case 0x1b: - strcat(mnem, "bdz"); + mnem += "bdz"; break; case 0x14: case 0x15: case 0x16: case 0x17: case 0x1c: case 0x1d: case 0x1e: case 0x1f: - strcat(mnem, "b"); + mnem += "b"; break; default: - return 0; + return false; } - strcat(mnem, (G_XO(op) == 528) ? "ctr" : "lr"); - if (op & M_LK) strcat(mnem, "l"); - if (op & M_AA) strcat(mnem, "a"); + mnem += (G_XO(op) == 528) ? "ctr" : "lr"; + if (op & M_LK) mnem += "l"; + if (op & M_AA) mnem += "a"; if (!(G_BO(op) & 0x10) && G_BI(op) / 4 != 0) - sprintf(oprs, "cr%d", G_BI(op) / 4); + oprs = util::string_format("cr%d", G_BI(op) / 4); } else if ((op & ~(M_RT|M_RA|M_RB|M_OE|M_RC)) == (D_OP(31)|D_XO(40))) { - strcat(mnem, "sub"); - if (op & M_OE) strcat(mnem, "o"); - if (op & M_RC) strcat(mnem, "."); - sprintf(oprs, "r%d,r%d,r%d", G_RT(op), G_RB(op), G_RA(op)); + mnem += "sub"; + if (op & M_OE) mnem += "o"; + if (op & M_RC) mnem += "."; + oprs = util::string_format("r%d,r%d,r%d", G_RT(op), G_RB(op), G_RA(op)); } else if ((op & ~(M_RT|M_RA|M_RB|M_OE|M_RC)) == (D_OP(31)|D_XO(8))) { - strcat(mnem, "subc"); - if (op & M_OE) strcat(mnem, "o"); - if (op & M_RC) strcat(mnem, "."); - sprintf(oprs, "r%d,r%d,r%d", G_RT(op), G_RB(op), G_RA(op)); + mnem += "subc"; + if (op & M_OE) mnem += "o"; + if (op & M_RC) mnem += "."; + oprs = util::string_format("r%d,r%d,r%d", G_RT(op), G_RB(op), G_RA(op)); } else - return 0; // no match + return false; // no match - return 1; + return true; } -offs_t ppc_dasm_one(std::ostream &stream, uint32_t pc, uint32_t op) +offs_t powerpc_disassembler::dasm_one(std::ostream &stream, uint32_t pc, uint32_t op) { - char signed16[12]; + std::string signed16, mnem, oprs; uint32_t disp; int i,j; - char mnem[200]; - char oprs[200]; - offs_t flags = DASMFLAG_SUPPORTED; - - mnem[0] = '\0'; // so we can use strcat() - oprs[0] = '\0'; + offs_t flags = SUPPORTED; /* * Decode signed 16-bit fields (SIMM and d) to spare us the work later */ - DecodeSigned16(signed16, op, 0); + signed16 = DecodeSigned16(op, 0); /* * Try simplified forms first, then real instructions @@ -859,7 +697,7 @@ offs_t ppc_dasm_one(std::ostream &stream, uint32_t pc, uint32_t op) if( Simplified(op, pc, signed16, mnem, oprs) ) { util::stream_format(stream, "%s", mnem); - for( j = strlen(mnem); j < 10; j++ ) { + for( j = mnem.size(); j < 10; j++ ) { util::stream_format(stream, " "); } util::stream_format(stream, "%s", oprs); @@ -878,11 +716,11 @@ offs_t ppc_dasm_one(std::ostream &stream, uint32_t pc, uint32_t op) * Base mnemonic followed be O, ., L, A */ - strcat(mnem, itab[i].mnem); - if (itab[i].flags & FL_OE) if (op & M_OE) strcat(mnem, "o"); - if (itab[i].flags & FL_RC) if (op & M_RC) strcat(mnem, "."); - if (itab[i].flags & FL_LK) if (op & M_LK) strcat(mnem, "l"); - if (itab[i].flags & FL_AA) if (op & M_AA) strcat(mnem, "a"); + mnem += itab[i].mnem; + if (itab[i].flags & FL_OE) if (op & M_OE) mnem += "o"; + if (itab[i].flags & FL_RC) if (op & M_RC) mnem += "."; + if (itab[i].flags & FL_LK) if (op & M_LK) mnem += "l"; + if (itab[i].flags & FL_AA) if (op & M_AA) mnem += "a"; /* * Print operands @@ -891,44 +729,44 @@ offs_t ppc_dasm_one(std::ostream &stream, uint32_t pc, uint32_t op) switch (itab[i].format) { case F_RT_RA_RB: - sprintf(oprs, "r%d,r%d,r%d", G_RT(op), G_RA(op), G_RB(op)); + oprs = util::string_format("r%d,r%d,r%d", G_RT(op), G_RA(op), G_RB(op)); break; case F_RT_RA_0_SIMM: if (G_RA(op)) - sprintf(oprs, "r%d,r%d,%s", G_RT(op), G_RA(op), signed16); + oprs = util::string_format("r%d,r%d,%s", G_RT(op), G_RA(op), signed16); else - sprintf(oprs, "r%d,0,%s", G_RT(op), signed16); + oprs = util::string_format("r%d,0,%s", G_RT(op), signed16); break; case F_ADDIS: if (G_RA(op)) - sprintf(oprs, "r%d,r%d,0x%04X", G_RT(op), G_RA(op), G_SIMM(op)); + oprs = util::string_format("r%d,r%d,0x%04X", G_RT(op), G_RA(op), G_SIMM(op)); else - sprintf(oprs, "r%d,0,0x%04X", G_RT(op), G_SIMM(op)); + oprs = util::string_format("r%d,0,0x%04X", G_RT(op), G_SIMM(op)); break; case F_RT_RA_SIMM: - sprintf(oprs, "r%d,r%d,%s", G_RT(op), G_RA(op), signed16); + oprs = util::string_format("r%d,r%d,%s", G_RT(op), G_RA(op), signed16); break; case F_RT_RA: - sprintf(oprs, "r%d,r%d", G_RT(op), G_RA(op)); + oprs = util::string_format("r%d,r%d", G_RT(op), G_RA(op)); break; case F_RA_RT_RB: - sprintf(oprs, "r%d,r%d,r%d", G_RA(op), G_RT(op), G_RB(op)); + oprs = util::string_format("r%d,r%d,r%d", G_RA(op), G_RT(op), G_RB(op)); break; case F_RA_RT_UIMM: - sprintf(oprs, "r%d,r%d,0x%04X", G_RA(op), G_RT(op), G_UIMM(op)); + oprs = util::string_format("r%d,r%d,0x%04X", G_RA(op), G_RT(op), G_UIMM(op)); break; case F_LI: disp = G_LI(op) * 4; if (disp & 0x02000000) // sign extend disp |= 0xfc000000; - sprintf(oprs, "0x%08X", disp + ((op & M_AA) ? 0 : pc)); + oprs = util::string_format("0x%08X", disp + ((op & M_AA) ? 0 : pc)); break; case F_BCx: @@ -937,213 +775,209 @@ offs_t ppc_dasm_one(std::ostream &stream, uint32_t pc, uint32_t op) disp |= 0xffff0000; if (G_BO(op) & 0x10) // BI is ignored (don't print CR bit) - sprintf(oprs, "0x%02X,%d,0x%08X", G_BO(op), G_BI(op), disp + ((op & M_AA) ? 0 : pc)); + oprs = util::string_format("0x%02X,%d,0x%08X", G_BO(op), G_BI(op), disp + ((op & M_AA) ? 0 : pc)); else // BI gives us the condition bit - sprintf(oprs, "0x%02X,cr%d[%s],0x%08X", G_BO(op), G_BI(op) / 4, crbit[G_BI(op) & 3], disp + ((op & M_AA) ? 0 : pc)); + oprs = util::string_format("0x%02X,cr%d[%s],0x%08X", G_BO(op), G_BI(op) / 4, crbit[G_BI(op) & 3], disp + ((op & M_AA) ? 0 : pc)); break; case F_BO_BI: if (G_BO(op) & 0x10) // BI is ignored (don't print CR bit) - sprintf(oprs, "0x%02X,%d", G_BO(op), G_BI(op)); + oprs = util::string_format("0x%02X,%d", G_BO(op), G_BI(op)); else - sprintf(oprs, "0x%02X,cr%d[%s]", G_BO(op), G_BI(op) / 4, crbit[G_BI(op) & 3]); + oprs = util::string_format("0x%02X,cr%d[%s]", G_BO(op), G_BI(op) / 4, crbit[G_BI(op) & 3]); break; case F_CMP: if (G_L(op)) - strcat(mnem, "d"); + mnem += "d"; if (G_CRFD(op) == 0) - sprintf(oprs, "r%d,r%d", G_RA(op), G_RB(op)); + oprs = util::string_format("r%d,r%d", G_RA(op), G_RB(op)); else - sprintf(oprs, "cr%d,r%d,r%d", G_CRFD(op), G_RA(op), G_RB(op)); + oprs = util::string_format("cr%d,r%d,r%d", G_CRFD(op), G_RA(op), G_RB(op)); break; case F_CMP_SIMM: if (G_L(op)) - strcat(mnem, "d"); + mnem += "d"; if (G_CRFD(op) == 0) - sprintf(oprs, "r%d,%s", G_RA(op), signed16); + oprs = util::string_format("r%d,%s", G_RA(op), signed16); else - sprintf(oprs, "cr%d,r%d,%s", G_CRFD(op), G_RA(op), signed16); + oprs = util::string_format("cr%d,r%d,%s", G_CRFD(op), G_RA(op), signed16); break; case F_CMP_UIMM: if (G_L(op)) - strcat(mnem, "d"); + mnem += "d"; if (G_CRFD(op) == 0) - sprintf(oprs, "r%d,0x%04X", G_RA(op), G_UIMM(op)); + oprs = util::string_format("r%d,0x%04X", G_RA(op), G_UIMM(op)); else - sprintf(oprs, "cr%d,r%d,0x%04X", G_CRFD(op), G_RA(op), G_UIMM(op)); + oprs = util::string_format("cr%d,r%d,0x%04X", G_CRFD(op), G_RA(op), G_UIMM(op)); break; case F_RA_RT: - sprintf(oprs, "r%d,r%d", G_RA(op), G_RT(op)); + oprs = util::string_format("r%d,r%d", G_RA(op), G_RT(op)); break; case F_CRBD_CRBA_CRBB: - sprintf(oprs, "cr%d[%s],cr%d[%s],cr%d[%s]", G_CRBD(op) / 4, crbit[G_CRBD(op) & 3], G_CRBA(op) / 4, crbit[G_CRBA(op) & 3], G_CRBB(op) / 4, crbit[G_CRBB(op) & 3]); + oprs = util::string_format("cr%d[%s],cr%d[%s],cr%d[%s]", G_CRBD(op) / 4, crbit[G_CRBD(op) & 3], G_CRBA(op) / 4, crbit[G_CRBA(op) & 3], G_CRBB(op) / 4, crbit[G_CRBB(op) & 3]); break; case F_RA_0_RB: if (G_RA(op)) - sprintf(oprs, "r%d,r%d", G_RA(op), G_RB(op)); + oprs = util::string_format("r%d,r%d", G_RA(op), G_RB(op)); else - sprintf(oprs, "0,r%d", G_RB(op)); + oprs = util::string_format("0,r%d", G_RB(op)); break; case F_RT_RA_0_RB: if (G_RA(op)) - sprintf(oprs, "r%d,r%d,r%d", G_RT(op), G_RA(op), G_RB(op)); + oprs = util::string_format("r%d,r%d,r%d", G_RT(op), G_RA(op), G_RB(op)); else - sprintf(oprs, "r%d,0,r%d", G_RT(op), G_RB(op)); + oprs = util::string_format("r%d,0,r%d", G_RT(op), G_RB(op)); break; case F_FRT_FRB: - sprintf(oprs, "f%d,f%d", G_RT(op), G_RB(op)); + oprs = util::string_format("f%d,f%d", G_RT(op), G_RB(op)); break; case F_FRT_FRA_FRB: - sprintf(oprs, "f%d,f%d,f%d", G_RT(op), G_RA(op), G_RB(op)); + oprs = util::string_format("f%d,f%d,f%d", G_RT(op), G_RA(op), G_RB(op)); break; case F_FCMP: - sprintf(oprs, "cr%d,f%d,f%d", G_CRFD(op), G_RA(op), G_RB(op)); + oprs = util::string_format("cr%d,f%d,f%d", G_CRFD(op), G_RA(op), G_RB(op)); break; case F_FRT_FRA_FRC_FRB: - sprintf(oprs, "f%d,f%d,f%d,f%d", G_RT(op), G_RA(op), G_REGC(op), G_RB(op)); + oprs = util::string_format("f%d,f%d,f%d,f%d", G_RT(op), G_RA(op), G_REGC(op), G_RB(op)); break; case F_FRT_FRA_FRC: - sprintf(oprs, "f%d,f%d,f%d", G_RT(op), G_RA(op), G_REGC(op)); + oprs = util::string_format("f%d,f%d,f%d", G_RT(op), G_RA(op), G_REGC(op)); break; case F_RT_D_RA_0: if (G_RA(op)) - sprintf(oprs, "r%d,%s(r%d)", G_RT(op), signed16, G_RA(op)); + oprs = util::string_format("r%d,%s(r%d)", G_RT(op), signed16, G_RA(op)); else - sprintf(oprs, "r%d,0x%08X", G_RT(op), (uint32_t) ((int16_t) G_D(op))); + oprs = util::string_format("r%d,0x%08X", G_RT(op), (uint32_t) ((int16_t) G_D(op))); break; case F_RT_D_RA: - sprintf(oprs, "r%d,%s(r%d)", G_RT(op), signed16, G_RA(op)); + oprs = util::string_format("r%d,%s(r%d)", G_RT(op), signed16, G_RA(op)); break; case F_FRT_D_RA_0: if (G_RA(op)) - sprintf(oprs, "f%d,%s(r%d)", G_RT(op), signed16, G_RA(op)); + oprs = util::string_format("f%d,%s(r%d)", G_RT(op), signed16, G_RA(op)); else - sprintf(oprs, "f%d,0x%08X", G_RT(op), (uint32_t) ((int16_t) G_D(op))); + oprs = util::string_format("f%d,0x%08X", G_RT(op), (uint32_t) ((int16_t) G_D(op))); break; case F_FRT_D_RA: - sprintf(oprs, "f%d,%s(r%d)", G_RT(op), signed16, G_RA(op)); + oprs = util::string_format("f%d,%s(r%d)", G_RT(op), signed16, G_RA(op)); break; case F_FRT_RA_RB: - sprintf(oprs, "f%d,r%d,r%d", G_RT(op), G_RA(op), G_RB(op)); + oprs = util::string_format("f%d,r%d,r%d", G_RT(op), G_RA(op), G_RB(op)); break; case F_FRT_RA_0_RB: if (G_RA(op)) - sprintf(oprs, "f%d,r%d,r%d", G_RT(op), G_RA(op), G_RB(op)); + oprs = util::string_format("f%d,r%d,r%d", G_RT(op), G_RA(op), G_RB(op)); else - sprintf(oprs, "f%d,0,r%d", G_RT(op), G_RB(op)); + oprs = util::string_format("f%d,0,r%d", G_RT(op), G_RB(op)); break; case F_RT_RA_0_NB: if (G_RA(op)) - sprintf(oprs, "r%d,r%d,%d", G_RT(op), G_RA(op), G_NB(op) ? G_NB(op) : 32); + oprs = util::string_format("r%d,r%d,%d", G_RT(op), G_RA(op), G_NB(op) ? G_NB(op) : 32); else - sprintf(oprs, "r%d,0,%d", G_RT(op), G_NB(op) ? G_NB(op) : 32); + oprs = util::string_format("r%d,0,%d", G_RT(op), G_NB(op) ? G_NB(op) : 32); break; case F_CRFD_CRFS: - sprintf(oprs, "cr%d,cr%d", G_CRFD(op), G_CRFS(op)); + oprs = util::string_format("cr%d,cr%d", G_CRFD(op), G_CRFS(op)); break; case F_MCRXR: - sprintf(oprs, "cr%d", G_CRFD(op)); + oprs = util::string_format("cr%d", G_CRFD(op)); break; case F_RT: - sprintf(oprs, "r%d", G_RT(op)); + oprs = util::string_format("r%d", G_RT(op)); break; case F_MFFSx: - sprintf(oprs, "f%d", G_RT(op)); + oprs = util::string_format("f%d", G_RT(op)); break; case F_FCRBD: - sprintf(oprs, "fpscr[%d]", G_CRBD(op)); + oprs = util::string_format("fpscr[%d]", G_CRBD(op)); break; case F_RT_SPR: - sprintf(oprs, "r%d,", G_RT(op)); - SPR(oprs, G_SPR(op)); + oprs = util::string_format("r%d,", G_RT(op)) + SPR(G_SPR(op)); break; case F_RT_DCR: - sprintf(oprs, "r%d,", G_RT(op)); - DCR(oprs, G_DCR(op)); + oprs = util::string_format("r%d,", G_RT(op)) + DCR(G_DCR(op)); break; case F_MFSR: - sprintf(oprs, "r%d,sr%d", G_RT(op), G_SR(op)); + oprs = util::string_format("r%d,sr%d", G_RT(op), G_SR(op)); break; case F_MTCRF: - sprintf(oprs, "0x%02X,r%d", G_CRM(op), G_RT(op)); + oprs = util::string_format("0x%02X,r%d", G_CRM(op), G_RT(op)); break; case F_MTFSFx: - sprintf(oprs, "0x%02X,f%d", G_FM(op), G_RB(op)); + oprs = util::string_format("0x%02X,f%d", G_FM(op), G_RB(op)); break; case F_MTFSFIx: - sprintf(oprs, "cr%d,0x%X", G_CRFD(op), G_IMM(op)); + oprs = util::string_format("cr%d,0x%X", G_CRFD(op), G_IMM(op)); break; case F_MTSPR: - SPR(oprs, G_SPR(op)); - sprintf(oprs + strlen(oprs), ",r%d", G_RT(op)); + oprs = SPR(G_SPR(op)) + util::string_format(",r%d", G_RT(op)); break; case F_MTDCR: - DCR(oprs, G_DCR(op)); - sprintf(oprs + strlen(oprs), ",r%d", G_RT(op)); + oprs = DCR(G_DCR(op)) + util::string_format(",r%d", G_RT(op)); break; case F_MTSR: - sprintf(oprs, "sr%d,r%d", G_SR(op), G_RT(op)); + oprs = util::string_format("sr%d,r%d", G_SR(op), G_RT(op)); break; case F_RT_RB: - sprintf(oprs, "r%d,r%d", G_RT(op), G_RB(op)); + oprs = util::string_format("r%d,r%d", G_RT(op), G_RB(op)); break; case F_RA_RT_SH_MB_ME: - sprintf(oprs, "r%d,r%d,%d,%d,%d", G_RA(op), G_RT(op), G_SH(op), G_MB(op), G_ME(op)); + oprs = util::string_format("r%d,r%d,%d,%d,%d", G_RA(op), G_RT(op), G_SH(op), G_MB(op), G_ME(op)); break; case F_RLWNMx: - sprintf(oprs, "r%d,r%d,r%d,%d,%d", G_RA(op), G_RT(op), G_RB(op), G_MB(op), G_ME(op)); + oprs = util::string_format("r%d,r%d,r%d,%d,%d", G_RA(op), G_RT(op), G_RB(op), G_MB(op), G_ME(op)); break; case F_SRAWIx: - sprintf(oprs, "r%d,r%d,%d", G_RA(op), G_RT(op), G_SH(op)); + oprs = util::string_format("r%d,r%d,%d", G_RA(op), G_RT(op), G_SH(op)); break; case F_RB: - sprintf(oprs, "r%d", G_RB(op)); + oprs = util::string_format("r%d", G_RB(op)); break; case F_TW: - sprintf(oprs, "%d,r%d,r%d", G_TO(op), G_RA(op), G_RB(op)); + oprs = util::string_format("%d,r%d,r%d", G_TO(op), G_RA(op), G_RB(op)); break; case F_TWI: - sprintf(oprs, "%d,r%d,%s", G_TO(op), G_RA(op), signed16); + oprs = util::string_format("%d,r%d,%s", G_TO(op), G_RA(op), signed16); break; case F_NONE: @@ -1152,12 +986,12 @@ offs_t ppc_dasm_one(std::ostream &stream, uint32_t pc, uint32_t op) } if ((itab[i].flags & FL_LK) && (op & M_LK)) - flags |= DASMFLAG_STEP_OVER; + flags |= STEP_OVER; else if (itab[i].flags & FL_SO) - flags |= DASMFLAG_STEP_OUT; + flags |= STEP_OUT; util::stream_format(stream, "%s", mnem); - for( j = strlen(mnem); j < 10; j++ ) { + for( j = mnem.size(); j < 10; j++ ) { util::stream_format(stream, " "); } util::stream_format(stream, "%s", oprs); @@ -1169,10 +1003,12 @@ offs_t ppc_dasm_one(std::ostream &stream, uint32_t pc, uint32_t op) return 4 | flags; } +offs_t powerpc_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + return dasm_one(stream, pc, opcodes.r32(pc)); +} -CPU_DISASSEMBLE( powerpc ) +u32 powerpc_disassembler::opcode_alignment() const { - uint32_t op = *(uint32_t *)oprom; - op = big_endianize_int32(op); - return ppc_dasm_one(stream, pc, op); + return 4; } diff --git a/src/devices/cpu/powerpc/ppc_dasm.h b/src/devices/cpu/powerpc/ppc_dasm.h new file mode 100644 index 00000000000..5fab7dfe074 --- /dev/null +++ b/src/devices/cpu/powerpc/ppc_dasm.h @@ -0,0 +1,142 @@ +// license:BSD-3-Clause +// copyright-holders:Aaron Giles +/* + * disasm.c + * + * PowerPC 603e disassembler. + * + * When possible, invalid forms of instructions are checked for. To the best + * of my knowledge, all appropriate load/store instructions are checked. I'm + * not sure whether any other kinds of instructions need checking. + */ + +/* Originally written by Bart Trzynadlowski for Supermodel project + * + * PowerPC 403 opcodes and MAME conversion by Ville Linde + */ + +#ifndef MAME_CPU_POWERPC_PPC_DASM_H +#define MAME_CPU_POWERPC_PPC_DASM_H + +#pragma once + +class powerpc_disassembler : public util::disasm_interface +{ +public: + powerpc_disassembler() = default; + virtual ~powerpc_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + static offs_t dasm_one(std::ostream &stream, uint32_t pc, uint32_t op); + +private: + /* + * Operand Formats + * + * These convey information on what operand fields are present and how they + * ought to be printed. + * + * I'm fairly certain all of these are used, but that is not guaranteed. + */ + + enum + { + F_NONE, // + F_LI, // LI*4+PC if AA=0 else LI*4 + F_BCx, // BO, BI, target_addr used only by BCx + F_RT_RA_0_SIMM, // rT, rA|0, SIMM rA|0 means if rA == 0, print 0 + F_ADDIS, // rT, rA, SIMM (printed as unsigned) only used by ADDIS + F_RT_RA_SIMM, // rT, rA, SIMM + F_RA_RT_UIMM, // rA, rT, UIMM + F_CMP_SIMM, // crfD, L, A, SIMM + F_CMP_UIMM, // crfD, L, A, UIMM + F_RT_RA_0_RB, // rT, rA|0, rB + F_RT_RA_RB, // rT, rA, rB + F_RT_D_RA_0, // rT, d(rA|0) + F_RT_D_RA, // rT, d(rA) + F_RA_RT_RB, // rA, rT, rB + F_FRT_D_RA_0, // frT, d(RA|0) + F_FRT_D_RA, // frT, d(RA) + F_FRT_RA_0_RB, // frT, rA|0, rB + F_FRT_RA_RB, // frT, rA, rB + F_TWI, // TO, rA, SIMM only used by TWI instruction + F_CMP, // crfD, L, rA, rB + F_RA_RT, // rA, rT + F_RA_0_RB, // rA|0, rB + F_FRT_FRB, // frT, frB + F_FCMP, // crfD, frA, frB + F_CRFD_CRFS, // crfD, crfS + F_MCRXR, // crfD only used by MCRXR + F_RT, // rT + F_MFSR, // rT, SR only used by MFSR + F_MTSR, // SR, rT only used by MTSR + F_MFFSx, // frT only used by MFFSx + F_FCRBD, // crbD FPSCR[crbD] + F_MTFSFIx, // crfD, IMM only used by MTFSFIx + F_RB, // rB + F_TW, // TO, rA, rB only used by TW + F_RT_RA_0_NB, // rT, rA|0, NB print 32 if NB == 0 + F_SRAWIx, // rA, rT, SH only used by SRAWIx + F_BO_BI, // BO, BI + F_CRBD_CRBA_CRBB, // crbD, crbA, crbB + F_RT_SPR, // rT, SPR and TBR + F_MTSPR, // SPR, rT only used by MTSPR + F_MTCRF, // CRM, rT only used by MTCRF + F_MTFSFx, // FM, frB only used by MTFSFx + F_RT_DCR, // rT, DCR + F_MTDCR, // DCR, rT + F_RT_RA, // rT, rA + F_FRT_FRA_FRC_FRB, // frT, frA, frC, frB + F_FRT_FRA_FRB, // frT, frA, frB + F_FRT_FRA_FRC, // frT, frA, frC + F_RA_RT_SH_MB_ME, // rA, rT, SH, MB, ME + F_RLWNMx, // rT, rA, rB, MB, ME only used by RLWNMx + F_RT_RB // rT, rB + }; + + /* + * Flags + */ + + enum + { + FL_OE = 1 << 0, // if there is an OE field + FL_RC = 1 << 1, // if there is an RC field + FL_LK = 1 << 2, // if there is an LK field + FL_AA = 1 << 3, // if there is an AA field + FL_CHECK_RA_RT = 1 << 4, // assert rA!=0 and rA!=rT + FL_CHECK_RA = 1 << 5, // assert rA!=0 + FL_CHECK_LSWI = 1 << 6, // specific check for LSWI validity + FL_CHECK_LSWX = 1 << 7, // specific check for LSWX validity + FL_SO = 1 << 8 // use STEP_OUT + }; + + /* + * Instruction Descriptor + * + * Describes the layout of an instruction. + */ + + struct IDESCR + { + char mnem[32]; // mnemonic + uint32_t match; // bit pattern of instruction after it has been masked + uint32_t mask; // mask of variable fields (AND with ~mask to compare w/ + // bit pattern to determine a match) + int format; // operand format + int flags; // flags + }; + + static const IDESCR itab[]; + static const char *const crbit[4]; + static const char *const crnbit[4]; + + static std::string SPR(int spr_field); + static std::string DCR(int dcr_field); + static std::string DecodeSigned16(uint32_t op, int do_unsigned); + static uint32_t Mask(int mb, int me); + static bool Simplified(uint32_t op, uint32_t vpc, std::string &signed16, std::string &mnem, std::string &oprs); +}; + +#endif diff --git a/src/devices/cpu/powerpc/ppccom.cpp b/src/devices/cpu/powerpc/ppccom.cpp index d9b4cf3ba96..42b5be40ace 100644 --- a/src/devices/cpu/powerpc/ppccom.cpp +++ b/src/devices/cpu/powerpc/ppccom.cpp @@ -11,7 +11,7 @@ #include "emu.h" #include "ppccom.h" #include "ppcfe.h" - +#include "ppc_dasm.h" /*************************************************************************** DEBUGGING @@ -1165,11 +1165,9 @@ void ppc_device::device_reset() CPU -------------------------------------------------*/ -offs_t ppc_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *ppc_device::create_disassembler() { - uint32_t op = *(uint32_t *)oprom; - op = big_endianize_int32(op); - return ppc_dasm_one(stream, pc, op); + return new powerpc_disassembler; } diff --git a/src/devices/cpu/powerpc/ppcdrc.cpp b/src/devices/cpu/powerpc/ppcdrc.cpp index 2d2a8f0dcee..ac587dc3259 100644 --- a/src/devices/cpu/powerpc/ppcdrc.cpp +++ b/src/devices/cpu/powerpc/ppcdrc.cpp @@ -19,6 +19,7 @@ #include "ppc.h" #include "ppccom.h" #include "ppcfe.h" +#include "ppc_dasm.h" #include "cpu/drcfe.h" #include "cpu/drcuml.h" #include "cpu/drcumlsh.h" @@ -3770,10 +3771,9 @@ void ppc_device::log_add_disasm_comment(drcuml_block *block, uint32_t pc, uint32 { if (m_drcuml->logging()) { - util::ovectorstream stream; - ppc_dasm_one(stream, pc, op); - stream.put('\0'); - block->append_comment("%08X: %s", pc, &stream.vec()[0]); // comment + std::ostringstream stream; + powerpc_disassembler::dasm_one(stream, pc, op); + block->append_comment("%08X: %s", pc, stream.str()); // comment } } @@ -3961,7 +3961,7 @@ void ppc_device::log_opcode_desc(drcuml_state *drcuml, const opcode_desc *descli if (desclist->flags & OPFLAG_VIRTUAL_NOOP) buffer << ""; else - ppc_dasm_one(buffer, desclist->pc, desclist->opptr.l[0]); + powerpc_disassembler::dasm_one(buffer, desclist->pc, desclist->opptr.l[0]); } else buffer << "???"; diff --git a/src/devices/cpu/pps4/pps4.cpp b/src/devices/cpu/pps4/pps4.cpp index c0b5ad60aa8..bddeddd6097 100644 --- a/src/devices/cpu/pps4/pps4.cpp +++ b/src/devices/cpu/pps4/pps4.cpp @@ -78,6 +78,7 @@ #include "emu.h" #include "pps4.h" +#include "pps4dasm.h" #include "debugger.h" @@ -139,10 +140,9 @@ void pps4_device::W(u8 data) m_SAG = 0; } -offs_t pps4_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +util::disasm_interface *pps4_device::create_disassembler() { - extern CPU_DISASSEMBLE( pps4 ); - return CPU_DISASSEMBLE_NAME(pps4)(this, stream, pc, oprom, opram, options); + return new pps4_disassembler; } /** diff --git a/src/devices/cpu/pps4/pps4.h b/src/devices/cpu/pps4/pps4.h index ef3c4dee977..dad4ba6fb5f 100644 --- a/src/devices/cpu/pps4/pps4.h +++ b/src/devices/cpu/pps4/pps4.h @@ -82,9 +82,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual u32 disasm_min_opcode_bytes() const override { return 1; } - virtual u32 disasm_max_opcode_bytes() const override { return 2; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; address_space_config m_program_config; address_space_config m_data_config; diff --git a/src/devices/cpu/pps4/pps4dasm.cpp b/src/devices/cpu/pps4/pps4dasm.cpp index 71bf93dcb44..edb15db12b3 100644 --- a/src/devices/cpu/pps4/pps4dasm.cpp +++ b/src/devices/cpu/pps4/pps4dasm.cpp @@ -11,36 +11,9 @@ * *****************************************************************************/ #include "emu.h" +#include "pps4dasm.h" -#define OP(A) oprom[(A) - PC] -#define ARG(A) opram[(A) - PC] - -typedef enum pps4_token_e { - t_AD, t_ADC, t_ADSK, t_ADCSK, t_ADI, - t_DC, t_AND, t_OR, t_EOR, t_COMP, - t_SC, t_RC, t_SF1, t_RF1, t_SF2, - t_RF2, t_LD, t_EX, t_EXD, t_LDI, - t_LAX, t_LXA, t_LABL, t_LBMX, t_LBUA, - t_XABL, t_XBMX, t_XAX, t_XS, t_CYS, - t_LB, t_LBL, t_INCB, t_DECB, t_T, - t_TM, t_TL, t_TML, t_SKC, t_SKZ, - t_SKBI, t_SKF1, t_SKF2, t_RTN, t_RTNSK, - t_IOL, t_DIA, t_DIB, t_DOA, t_SAG, - t_COUNT, - t_MASK = (1 << 6) - 1, - t_I3c = 1 << 6, /* immediate 3 bit constant, complemented */ - t_I4 = 1 << 7, /* immediate 4 bit constant */ - t_I4c = 1 << 8, /* immediate 4 bit constant, complemented */ - t_I4p = 1 << 9, /* immediate 4 bit offset into page 3 */ - t_I6p = 1 << 10, /* immediate 6 bit constant; address in current page */ - t_I6i = 1 << 11, /* immediate 6 bit indirect page 3 offset (16 ... 63) + followed by page 1 address */ - t_I8 = 1 << 12, /* immediate 8 bit constant (I/O port number) */ - t_I8c = 1 << 13, /* immediate 8 bit constant inverted */ - t_OVER = 1 << 14, /* Debugger step over (CALL) */ - t_OUT = 1 << 15 /* Debugger step out (RETURN) */ -} pps4_token_e; - -static const char *token_str[t_COUNT] = { +const char *pps4_disassembler::token_str[t_COUNT] = { "ad", /* add */ "adc", /* add with carry-in */ "adsk", /* add and skip on carry-out */ @@ -93,7 +66,7 @@ static const char *token_str[t_COUNT] = { "sag" /* special address generation */ }; -static const uint16_t table[] = { +const uint16_t pps4_disassembler::table[] = { /* 00 */ t_LBL | t_I8c, /* 01 */ t_TML | t_I4 | t_I8, /* 02 */ t_TML | t_I4 | t_I8, @@ -367,11 +340,16 @@ static const uint16_t table[] = { /* ff */ t_TM | t_I6i | t_OVER }; -CPU_DISASSEMBLE(pps4) +u32 pps4_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t pps4_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { uint32_t flags = 0; unsigned PC = pc; - uint8_t op = OP(pc++); + uint8_t op = opcodes.r8(pc++); uint32_t tok = table[op]; if (0 == (tok & t_MASK)) { @@ -422,21 +400,21 @@ CPU_DISASSEMBLE(pps4) if (tok & t_I8) { // 8 bit immediate I/O port address - uint8_t arg = ARG(pc++); + uint8_t arg = params.r8(pc++); util::stream_format(stream, "%02x", arg); } if (tok & t_I8c) { // 8 bit immediate offset into page - uint16_t arg = ~ARG(pc++) & 255; + uint16_t arg = ~params.r8(pc++) & 255; util::stream_format(stream, "%02x", arg); } if (tok & t_OVER) // TL or TML - flags |= DASMFLAG_STEP_OVER; + flags |= STEP_OVER; if (tok & t_OUT) // RTN or RTNSK - flags |= DASMFLAG_STEP_OUT; + flags |= STEP_OUT; - return (pc - PC) | flags | DASMFLAG_SUPPORTED; + return (pc - PC) | flags | SUPPORTED; } diff --git a/src/devices/cpu/pps4/pps4dasm.h b/src/devices/cpu/pps4/pps4dasm.h new file mode 100644 index 00000000000..7e0f0ab9b91 --- /dev/null +++ b/src/devices/cpu/pps4/pps4dasm.h @@ -0,0 +1,59 @@ +// license:BSD-3-Clause +// copyright-holders:Juergen Buchmueller +/***************************************************************************** + * + * pps4dasm.c + * + * Rockwell PPS-4 CPU Disassembly + * + * + * TODO: double verify all opcodes with t_Ixx flags + * + *****************************************************************************/ + +#ifndef MAME_CPU_PPS4_PPS4DASM_H +#define MAME_CPU_PPS4_PPS4DASM_H + +#pragma once + +class pps4_disassembler : public util::disasm_interface +{ +public: + pps4_disassembler() = default; + virtual ~pps4_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + typedef enum pps4_token_e { + t_AD, t_ADC, t_ADSK, t_ADCSK, t_ADI, + t_DC, t_AND, t_OR, t_EOR, t_COMP, + t_SC, t_RC, t_SF1, t_RF1, t_SF2, + t_RF2, t_LD, t_EX, t_EXD, t_LDI, + t_LAX, t_LXA, t_LABL, t_LBMX, t_LBUA, + t_XABL, t_XBMX, t_XAX, t_XS, t_CYS, + t_LB, t_LBL, t_INCB, t_DECB, t_T, + t_TM, t_TL, t_TML, t_SKC, t_SKZ, + t_SKBI, t_SKF1, t_SKF2, t_RTN, t_RTNSK, + t_IOL, t_DIA, t_DIB, t_DOA, t_SAG, + t_COUNT, + t_MASK = (1 << 6) - 1, + t_I3c = 1 << 6, /* immediate 3 bit constant, complemented */ + t_I4 = 1 << 7, /* immediate 4 bit constant */ + t_I4c = 1 << 8, /* immediate 4 bit constant, complemented */ + t_I4p = 1 << 9, /* immediate 4 bit offset into page 3 */ + t_I6p = 1 << 10, /* immediate 6 bit constant; address in current page */ + t_I6i = 1 << 11, /* immediate 6 bit indirect page 3 offset (16 ... 63) + followed by page 1 address */ + t_I8 = 1 << 12, /* immediate 8 bit constant (I/O port number) */ + t_I8c = 1 << 13, /* immediate 8 bit constant inverted */ + t_OVER = 1 << 14, /* Debugger step over (CALL) */ + t_OUT = 1 << 15 /* Debugger step out (RETURN) */ + } pps4_token_e; + + static const char *token_str[t_COUNT]; + static const uint16_t table[]; + +}; + +#endif diff --git a/src/devices/cpu/psx/dismips.cpp b/src/devices/cpu/psx/dismips.cpp deleted file mode 100644 index 2551a2d56a8..00000000000 --- a/src/devices/cpu/psx/dismips.cpp +++ /dev/null @@ -1,332 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:smf -/* - * standalone MIPS disassembler by smf - * - * based on DIS68k by Aaron Giles - * - */ - -#include "emu.h" -#include "psx.h" - -extern CPU_DISASSEMBLE( r3000le ); - -static struct -{ - uint8_t id[ 8 ]; - uint32_t text; /* SCE only */ - uint32_t data; /* SCE only */ - uint32_t pc0; - uint32_t gp0; /* SCE only */ - uint32_t t_addr; - uint32_t t_size; - uint32_t d_addr; /* SCE only */ - uint32_t d_size; /* SCE only */ - uint32_t b_addr; /* SCE only */ - uint32_t b_size; /* SCE only */ - uint32_t s_addr; - uint32_t s_size; - uint32_t SavedSP; - uint32_t SavedFP; - uint32_t SavedGP; - uint32_t SavedRA; - uint32_t SavedS0; - uint8_t dummy[ 0x800 - 76 ]; -} m_psxexe_header; - -#define FORMAT_BIN ( 0 ) -#define FORMAT_PSX ( 1 ) - -#define CPU_PSX ( 0 ) -#define CPU_R3000 ( 1 ) -#define CPU_R4000 ( 2 ) - -static uint8_t *filebuf; -static uint32_t offset; -static uint8_t order[] = { 0, 1, 2, 3 }; - -static const char *const Options[]= -{ - "begin", "end", "offset", "order", "format", "cpu", 0 -}; - -static void usage (void) -{ - fprintf( stderr, - "Usage: DISMIPS [options] \n\n" - "Available options are:\n" - " -begin - Specify begin offset in file to disassemble in bytes [0]\n" - " -end - Specify end offset in file to disassemble in bytes [none]\n" - " -offset - Specify address to load program in bytes [0]\n" - " -order - Specify byte order [0123]\n" - " -format - Specify file format bin|psx [bin]\n" - " -cpu - Specify cpu psx|r3000|r4000 [psx]\n\n" - "All values should be entered in hexadecimal\n" ); - exit( 1 ); -} - -int main( int argc, char *argv[] ) -{ - FILE *f; - uint8_t i; - uint8_t j; - uint8_t n; - uint8_t p; - uint32_t begin; - uint32_t end; - uint32_t filelen; - uint32_t len; - uint32_t pc; - char buffer[ 80 ]; - char *filename; - uint32_t format; - uint32_t cpu; - - filename = nullptr; - begin = 0; - end = 0xffffffff; - format = FORMAT_BIN; - cpu = CPU_PSX; - - n = 0; - for( i = 1; i < argc; i++ ) - { - if( argv[ i ][ 0 ] != '-' ) - { - switch( n ) - { - case 0: - filename = argv[ i ]; - break; - default: - usage(); - break; - } - n++; - } - else - { - for( j = 0; Options[ j ]; j++ ) - { - if( strcmp( argv[ i ] + 1, Options[ j ] ) == 0 ) - { - break; - } - } - switch( j ) - { - case 0: - i++; - if( i > argc ) - { - usage(); - } - begin = strtoul( argv[ i ], 0, 16 ); - break; - case 1: - i++; - if( i > argc ) - { - usage(); - } - end = strtoul( argv[ i ], 0, 16 ); - break; - case 2: - i++; - if( i > argc ) - { - usage(); - } - offset = strtoul( argv[ i ], 0, 16 ); - break; - case 3: - i++; - if( i > argc ) - { - usage(); - } - if( strlen( argv[ i ] ) != 4 ) - { - usage(); - } - for( p = 0; p < 4; p++ ) - { - if( argv[ i ][ p ] < '0' || argv[ i ][ p ] > '3' ) - { - usage(); - } - order[ p ] = argv[ i ][ p ] - '0'; - } - break; - case 4: - i++; - if( i > argc ) - { - usage(); - } - if( core_stricmp( argv[ i ], "bin" ) == 0 ) - { - format = FORMAT_BIN; - } - else if( core_stricmp( argv[ i ], "psx" ) == 0 ) - { - format = FORMAT_PSX; - } - else - { - usage(); - } - break; - case 5: - i++; - if( i > argc ) - { - usage(); - } - if( core_stricmp( argv[ i ], "psx" ) == 0 ) - { - cpu = CPU_PSX; - } - else if( core_stricmp( argv[ i ], "r3000" ) == 0 ) - { - cpu = CPU_R3000; - } - else if( core_stricmp( argv[ i ], "r4000" ) == 0 ) - { - cpu = CPU_R4000; - } - else - { - usage(); - } - break; - default: - usage(); - break; - } - } - } - - if (!filename) - { - usage(); - return 1; - } - f=fopen (filename,"rb"); - if (!f) - { - printf ("Unable to open %s\n",filename); - return 2; - } - fseek (f,0,SEEK_END); - filelen=ftell (f); - - if( format == FORMAT_PSX ) - { - fseek( f, 0, SEEK_SET ); - if( fread( &m_psxexe_header, 1, sizeof( m_psxexe_header ), f ) != sizeof( m_psxexe_header ) ) - { - fprintf( stderr, "error reading ps-x exe header\n" ); - fclose( f ); - return 3; - } - if( memcmp( m_psxexe_header.id, "PS-X EXE", sizeof( m_psxexe_header.id ) ) != 0 ) - { - fprintf( stderr, "invalid ps-x exe header\n" ); - fclose( f ); - return 3; - } - printf( "_start = $%08x\n\n", m_psxexe_header.pc0 ); - if( offset == 0 ) - { - offset = m_psxexe_header.t_addr; - } - if( begin == 0 ) - { - begin = sizeof( m_psxexe_header ); - } - if( end == 0xffffffff ) - { - end = sizeof( m_psxexe_header ) + m_psxexe_header.t_size; - } - } - - fseek (f,begin,SEEK_SET); - len=(filelen>end)? (end-begin+1):(filelen-begin); - filebuf=(uint8_t *)malloc(len+16); - if (!filebuf) - { - printf ("Memory allocation error\n"); - fclose (f); - return 3; - } - memset (filebuf,0,len+16); - if (fread(filebuf,1,len,f)!=len) - { - printf ("Read error\n"); - fclose (f); - free (filebuf); - return 4; - } - fclose (f); - - pc = 0; - while( pc < len ) - { - uint8_t op0 = filebuf[ pc + order[ 0 ] ]; - uint8_t op1 = filebuf[ pc + order[ 1 ] ]; - uint8_t op2 = filebuf[ pc + order[ 2 ] ]; - uint8_t op3 = filebuf[ pc + order[ 3 ] ]; - filebuf[ pc + 0 ] = op0; - filebuf[ pc + 1 ] = op1; - filebuf[ pc + 2 ] = op2; - filebuf[ pc + 3 ] = op3; - - pc += 4; - } - - pc = 0; - while( pc < len ) - { - switch( cpu ) - { - case CPU_PSX: - i = DasmPSXCPU( nullptr, buffer, pc + offset, filebuf + pc ); - break; - case CPU_R3000: - { - cpu_device *device = nullptr; - int options = 0; - uint8_t *opram = filebuf + pc; - uint8_t *oprom = opram; - i = CPU_DISASSEMBLE_CALL( r3000le ); - } - break; - case CPU_R4000: - { - uint8_t *opram = filebuf + pc; - uint32_t op = ( opram[ 3 ] << 24 ) | ( opram[ 2 ] << 16 ) | ( opram[ 1 ] << 8 ) | ( opram[ 0 ] << 0 ); - i = dasmmips3( buffer, pc + offset, op ); - } - break; - } - - i &= DASMFLAG_LENGTHMASK; - - printf( "%08x: ", pc + offset ); - for( j = 0; j < i; j++ ) - { - printf( "%02x ", filebuf[ pc ] ); - pc++; - } - while( j < 10 ) - { - printf( " " ); - j++; - } - printf( "%s\n", buffer ); - } - free (filebuf); - return 0; -} diff --git a/src/devices/cpu/psx/dismips.mak b/src/devices/cpu/psx/dismips.mak deleted file mode 100644 index a229a305bb4..00000000000 --- a/src/devices/cpu/psx/dismips.mak +++ /dev/null @@ -1,2 +0,0 @@ -..\..\..\..\dismips.exe: dismips.cpp psxdasm.cpp ..\mips\r3kdasm.cpp ..\mips\mips3dsm.cpp ../../../lib/util/corestr.cpp - g++ -O3 -x c++ -Wall -Wno-sign-compare -I../.. -I../../../emu -I../../../osd -I../../../lib/util -I../../../lib/expat -DINLINE="static __inline__" -DSTANDALONE -DLSB_FIRST dismips.cpp psxdasm.cpp ..\mips\r3kdasm.cpp ..\mips\mips3dsm.cpp ../../../lib/util/corestr.cpp -o../../../../dismips diff --git a/src/devices/cpu/psx/psx.cpp b/src/devices/cpu/psx/psx.cpp index 36d7c1742f4..926a25103a8 100644 --- a/src/devices/cpu/psx/psx.cpp +++ b/src/devices/cpu/psx/psx.cpp @@ -2067,13 +2067,13 @@ void psxcpu_device::state_string_export( const device_state_entry &entry, std::s //------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t psxcpu_device::disasm_disassemble( std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options ) +util::disasm_interface *psxcpu_device::create_disassembler() { - return DasmPSXCPU( this, stream, pc, opram ); + return new psxcpu_disassembler(this); } diff --git a/src/devices/cpu/psx/psx.h b/src/devices/cpu/psx/psx.h index da70d2c300c..2b7d02df6e3 100644 --- a/src/devices/cpu/psx/psx.h +++ b/src/devices/cpu/psx/psx.h @@ -17,6 +17,7 @@ #include "gte.h" #include "irq.h" #include "sio.h" +#include "psxdasm.h" //************************************************************************** // CONSTANTS @@ -140,20 +141,9 @@ enum // TYPE DEFINITIONS //************************************************************************** -class psxcpu_state -{ -public: - virtual ~psxcpu_state() { } - - virtual uint32_t pc() = 0; - virtual uint32_t delayr() = 0; - virtual uint32_t delayv() = 0; - virtual uint32_t r(int i) = 0; -}; - // ======================> psxcpu_device -class psxcpu_device : public cpu_device, psxcpu_state +class psxcpu_device : public cpu_device, psxcpu_disassembler::config { public: // static configuration helpers @@ -229,9 +219,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 4; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 8; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // CPU registers uint32_t m_pc; @@ -409,6 +397,4 @@ DECLARE_DEVICE_TYPE(CXD8606BQ, cxd8606bq_device) DECLARE_DEVICE_TYPE(CXD8606CQ, cxd8606cq_device) -extern unsigned DasmPSXCPU(psxcpu_state *state, std::ostream &stream, uint32_t pc, const uint8_t *opram); - #endif // MAME_CPU_PSX_PSX_H diff --git a/src/devices/cpu/psx/psxdasm.cpp b/src/devices/cpu/psx/psxdasm.cpp index 2bb38b6d407..51a62f6dc1d 100644 --- a/src/devices/cpu/psx/psxdasm.cpp +++ b/src/devices/cpu/psx/psxdasm.cpp @@ -10,25 +10,22 @@ #include "gte.h" #include "psxdefs.h" +#include "psxdasm.h" -static char *make_signed_hex_str_16( uint32_t value ) +std::string psxcpu_disassembler::make_signed_hex_str_16( uint32_t value ) { - static char s_hex[ 20 ]; - if( value & 0x8000 ) { - sprintf( s_hex, "-$%x", -value & 0xffff ); + return util::string_format("-$%x", -value & 0xffff ); } else { - sprintf( s_hex, "$%x", value & 0xffff ); + return util::string_format("$%x", value & 0xffff ); } - - return s_hex; } -static const char *const s_cpugenreg[] = +const char *const psxcpu_disassembler::s_cpugenreg[] = { "zero", "at", "v0", "v1", "a0", "a1", "a2", "a3", "t0", "t1", "t2", "t3", "t4", "t5", "t6", "t7", @@ -36,7 +33,7 @@ static const char *const s_cpugenreg[] = "t8", "t9", "k0", "k1", "gp", "sp", "fp", "ra" }; -static const char *const s_cp0genreg[] = +const char *const psxcpu_disassembler::s_cp0genreg[] = { "!Index", "!Random", "!EntryLo", "BPC", "!Context", "BDA", "TAR", "DCIC", "BadA", "BDAM", "!EntryHi", "BPCM", "SR", "Cause", "EPC", "PRId", @@ -44,7 +41,7 @@ static const char *const s_cp0genreg[] = "cp0r24", "cp0r25", "cp0r26", "cp0r27", "cp0r28", "cp0r29", "cp0r30", "cp0r31" }; -static const char *const s_cp0ctlreg[] = +const char *const psxcpu_disassembler::s_cp0ctlreg[] = { "cp0cr0", "cp0cr1", "cp0cr2", "cp0cr3", "cp0cr4", "cp0cr5", "cp0cr6", "cp0cr7", "cp0cr8", "cp0cr9", "cp0cr10", "cp0cr11", "cp0cr12", "cp0cr13", "cp0cr14", "cp0cr15", @@ -52,7 +49,7 @@ static const char *const s_cp0ctlreg[] = "cp0cr24", "cp0cr25", "cp0cr26", "cp0cr27", "cp0cr28", "cp0cr29", "cp0cr30", "cp0cr31" }; -static const char *const s_cp1genreg[] = +const char *const psxcpu_disassembler::s_cp1genreg[] = { "cp1r0", "cp1r1", "cp1r2", "cp1r3", "cp1r4", "cp1r5", "cp1r6", "cp1r7", "cp1r8", "cp1r9", "cp1r10", "cp1r11", "cp1r12", "cp1r13", "cp1r14", "cp1r15", @@ -60,7 +57,7 @@ static const char *const s_cp1genreg[] = "cp1r23", "cp1r24", "cp1r25", "cp1r26", "cp1r27", "cp1r28", "cp1r29", "cp1r30" }; -static const char *const s_cp1ctlreg[] = +const char *const psxcpu_disassembler::s_cp1ctlreg[] = { "cp1cr0", "cp1cr1", "cp1cr2", "cp1cr3", "cp1cr4", "cp1cr5", "cp1cr6", "cp1cr7", "cp1cr8", "cp1cr9", "cp1cr10", "cp1cr11", "cp1cr12", "cp1cr13", "cp1cr14", "cp1cr15", @@ -68,7 +65,7 @@ static const char *const s_cp1ctlreg[] = "cp1cr24", "cp1cr25", "cp1cr26", "cp1cr27", "cp1cr28", "cp1cr29", "cp1cr30", "cp1cr31" }; -static const char *const s_cp2genreg[] = +const char *const psxcpu_disassembler::s_cp2genreg[] = { "vxy0", "vz0", "vxy1", "vz1", "vxy2", "vz2", "rgb", "otz", "ir0", "ir1", "ir2", "ir3", "sxy0", "sxy1", "sxy2", "sxyp", @@ -76,7 +73,7 @@ static const char *const s_cp2genreg[] = "mac0", "mac1", "mac2", "mac3", "irgb", "orgb", "lzcs", "lzcr" }; -static const char *const s_cp2ctlreg[] = +const char *const psxcpu_disassembler::s_cp2ctlreg[] = { "r11r12", "r13r21", "r22r23", "r31r32", "r33", "trx", "try", "trz", "l11l12", "l13l21", "l22l23", "l31l32", "l33", "rbk", "gbk", "bbk", @@ -84,7 +81,7 @@ static const char *const s_cp2ctlreg[] = "ofx", "ofy", "h", "dqa", "dqb", "zsf3", "zsf4", "flag" }; -static const char *const s_cp3genreg[] = +const char *const psxcpu_disassembler::s_cp3genreg[] = { "cp3r0", "cp3r1", "cp3r2", "cp3r3", "cp3r4", "cp3r5", "cp3r6", "cp3r7", "cp3r8", "cp3r9", "cp3r10", "cp3r11", "cp3r12", "cp3r13", "cp3r14", "cp3r15", @@ -92,7 +89,7 @@ static const char *const s_cp3genreg[] = "cp3r23", "cp3r24", "cp3r25", "cp3r26", "cp3r27", "cp3r28", "cp3r29", "cp3r30" }; -static const char *const s_cp3ctlreg[] = +const char *const psxcpu_disassembler::s_cp3ctlreg[] = { "cp3cr0", "cp3cr1", "cp3cr2", "cp3cr3", "cp3cr4", "cp3cr5", "cp3cr6", "cp3cr7", "cp3cr8", "cp3cr9", "cp3cr10", "cp3cr11", "cp3cr12", "cp3cr13", "cp3cr14", "cp3cr15", @@ -100,101 +97,96 @@ static const char *const s_cp3ctlreg[] = "cp3cr24", "cp3cr25", "cp3cr26", "cp3cr27", "cp3cr28", "cp3cr29", "cp3cr30", "cp3cr31" }; -static const char *const s_gtesf[] = +const char *const psxcpu_disassembler::s_gtesf[] = { " sf=0", " sf=12" }; -static const char *const s_gtemx[] = +const char *const psxcpu_disassembler::s_gtemx[] = { "rm", "lm", "cm", "0" }; -static const char *const s_gtev[] = +const char *const psxcpu_disassembler::s_gtev[] = { "v0", "v1", "v2", "ir" }; -static const char *const s_gtecv[] = +const char *const psxcpu_disassembler::s_gtecv[] = { "tr", "bk", "fc", "0" }; -static const char *const s_gtelm[] = +const char *const psxcpu_disassembler::s_gtelm[] = { " lm=s16", " lm=u15" }; -static char *effective_address( psxcpu_state *state, uint32_t pc, uint32_t op ) +std::string psxcpu_disassembler::effective_address( uint32_t pc, uint32_t op ) { - static char s_address[ 30 ]; - - if( state != nullptr && state->pc() == pc ) + if( m_config && m_config->pc() == pc ) { - sprintf( s_address, "%s(%s) ; 0x%08x", make_signed_hex_str_16( INS_IMMEDIATE( op ) ), s_cpugenreg[ INS_RS( op ) ], - (uint32_t)( state->r( INS_RS( op ) ) + (int16_t)INS_IMMEDIATE( op ) ) ); - return s_address; + return util::string_format("%s(%s) ; 0x%08x", make_signed_hex_str_16( INS_IMMEDIATE( op ) ), s_cpugenreg[ INS_RS( op ) ], + (uint32_t)( m_config->r( INS_RS( op ) ) + (int16_t)INS_IMMEDIATE( op ) ) ); } - sprintf( s_address, "%s(%s)", make_signed_hex_str_16( INS_IMMEDIATE( op ) ), s_cpugenreg[ INS_RS( op ) ] ); - return s_address; + return util::string_format("%s(%s)", make_signed_hex_str_16( INS_IMMEDIATE( op ) ), s_cpugenreg[ INS_RS( op ) ] ); } -static uint32_t relative_address( psxcpu_state *state, uint32_t pc, uint32_t op ) +uint32_t psxcpu_disassembler::relative_address( uint32_t pc, uint32_t op ) { uint32_t nextpc = pc + 4; - if( state != nullptr && state->pc() == pc && state->delayr() == PSXCPU_DELAYR_PC ) + if( m_config && m_config->pc() == pc && m_config->delayr() == PSXCPU_DELAYR_PC ) { - nextpc = state->delayv(); + nextpc = m_config->delayv(); } return nextpc + ( PSXCPU_WORD_EXTEND( INS_IMMEDIATE( op ) ) << 2 ); } -static uint32_t jump_address( psxcpu_state *state, uint32_t pc, uint32_t op ) +uint32_t psxcpu_disassembler::jump_address( uint32_t pc, uint32_t op ) { uint32_t nextpc = pc + 4; - if( state != nullptr && state->pc() == pc && state->delayr() == PSXCPU_DELAYR_PC ) + if( m_config && m_config->pc() == pc && m_config->delayr() == PSXCPU_DELAYR_PC ) { - nextpc = state->delayv(); + nextpc = m_config->delayv(); } return ( nextpc & 0xf0000000 ) + ( INS_TARGET( op ) << 2 ); } -static uint32_t fetch_op( const uint8_t *opram ) -{ - return ( opram[ 3 ] << 24 ) | ( opram[ 2 ] << 16 ) | ( opram[ 1 ] << 8 ) | ( opram[ 0 ] << 0 ); -} - -static char *upper_address( uint32_t op, const uint8_t *opram ) +std::string psxcpu_disassembler::upper_address( uint32_t op, offs_t pos, const data_buffer &opcodes ) { - static char s_address[ 20 ]; - uint32_t nextop = fetch_op( opram ); + uint32_t nextop = opcodes.r32( pos ); if( INS_OP( nextop ) == OP_ORI && INS_RT( op ) == INS_RS( nextop ) ) { - sprintf( s_address, "$%04x ; 0x%08x", INS_IMMEDIATE( op ), ( INS_IMMEDIATE( op ) << 16 ) | INS_IMMEDIATE( nextop ) ); + return util::string_format("$%04x ; 0x%08x", INS_IMMEDIATE( op ), ( INS_IMMEDIATE( op ) << 16 ) | INS_IMMEDIATE( nextop ) ); } else if( INS_OP( nextop ) == OP_ADDIU && INS_RT( op ) == INS_RS( nextop ) ) { - sprintf( s_address, "$%04x ; 0x%08x", INS_IMMEDIATE( op ), ( INS_IMMEDIATE( op ) << 16 ) + (int16_t) INS_IMMEDIATE( nextop ) ); + return util::string_format("$%04x ; 0x%08x", INS_IMMEDIATE( op ), ( INS_IMMEDIATE( op ) << 16 ) + (int16_t) INS_IMMEDIATE( nextop ) ); } else { - sprintf( s_address, "$%04x", INS_IMMEDIATE( op ) ); + return util::string_format("$%04x", INS_IMMEDIATE( op ) ); } +} + +psxcpu_disassembler::psxcpu_disassembler(config *conf) : m_config(conf) +{ +} - return s_address; +u32 psxcpu_disassembler::opcode_alignment() const +{ + return 4; } -unsigned DasmPSXCPU( psxcpu_state *state, std::ostream &stream, uint32_t pc, const uint8_t *opram ) +offs_t psxcpu_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { uint32_t op; - const uint8_t *oldopram; uint32_t flags = 0; - - oldopram = opram; - op = fetch_op( opram ); - opram += 4; + offs_t pos = pc; + op = opcodes.r32( pos ); + pos += 4; std::streampos current_pos = stream.tellp(); @@ -233,20 +225,20 @@ unsigned DasmPSXCPU( psxcpu_state *state, std::ostream &stream, uint32_t pc, con util::stream_format( stream, "jr %s", s_cpugenreg[ INS_RS( op ) ] ); if( INS_RS( op ) == 31 ) { - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; } break; case FUNCT_JALR: util::stream_format( stream, "jalr %s,%s", s_cpugenreg[ INS_RD( op ) ], s_cpugenreg[ INS_RS( op ) ] ); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA( 1 ); + flags = STEP_OVER | step_over_extra( 1 ); break; case FUNCT_SYSCALL: util::stream_format( stream, "syscall $%05x", INS_CODE( op ) ); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case FUNCT_BREAK: util::stream_format( stream, "break $%05x", INS_CODE( op ) ); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case FUNCT_MFHI: util::stream_format( stream, "mfhi %s", s_cpugenreg[ INS_RD( op ) ] ); @@ -310,45 +302,45 @@ unsigned DasmPSXCPU( psxcpu_state *state, std::ostream &stream, uint32_t pc, con case RT_BLTZ: if( INS_RT( op ) == RT_BLTZAL ) { - util::stream_format( stream, "bltzal %s,$%08x", s_cpugenreg[ INS_RS( op ) ], relative_address( state, pc, op ) ); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA( 1 ); + util::stream_format( stream, "bltzal %s,$%08x", s_cpugenreg[ INS_RS( op ) ], relative_address( pc, op ) ); + flags = STEP_OVER | step_over_extra( 1 ); } else { - util::stream_format( stream, "bltz %s,$%08x", s_cpugenreg[ INS_RS( op ) ], relative_address( state, pc, op ) ); + util::stream_format( stream, "bltz %s,$%08x", s_cpugenreg[ INS_RS( op ) ], relative_address( pc, op ) ); } break; case RT_BGEZ: if( INS_RT( op ) == RT_BGEZAL ) { - util::stream_format( stream, "bgezal %s,$%08x", s_cpugenreg[ INS_RS( op ) ], relative_address( state, pc, op ) ); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA( 1 ); + util::stream_format( stream, "bgezal %s,$%08x", s_cpugenreg[ INS_RS( op ) ], relative_address( pc, op ) ); + flags = STEP_OVER | step_over_extra( 1 ); } else { - util::stream_format( stream, "bgez %s,$%08x", s_cpugenreg[ INS_RS( op ) ], relative_address( state, pc, op ) ); + util::stream_format( stream, "bgez %s,$%08x", s_cpugenreg[ INS_RS( op ) ], relative_address( pc, op ) ); } break; } break; case OP_J: - util::stream_format( stream, "j $%08x", jump_address( state, pc, op ) ); + util::stream_format( stream, "j $%08x", jump_address( pc, op ) ); break; case OP_JAL: - util::stream_format( stream, "jal $%08x", jump_address( state, pc, op ) ); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA( 1 ); + util::stream_format( stream, "jal $%08x", jump_address( pc, op ) ); + flags = STEP_OVER | step_over_extra( 1 ); break; case OP_BEQ: - util::stream_format( stream, "beq %s,%s,$%08x", s_cpugenreg[ INS_RS( op ) ], s_cpugenreg[ INS_RT( op ) ], relative_address( state, pc, op ) ); + util::stream_format( stream, "beq %s,%s,$%08x", s_cpugenreg[ INS_RS( op ) ], s_cpugenreg[ INS_RT( op ) ], relative_address( pc, op ) ); break; case OP_BNE: - util::stream_format( stream, "bne %s,%s,$%08x", s_cpugenreg[ INS_RS( op ) ], s_cpugenreg[ INS_RT( op ) ], relative_address( state, pc, op ) ); + util::stream_format( stream, "bne %s,%s,$%08x", s_cpugenreg[ INS_RS( op ) ], s_cpugenreg[ INS_RT( op ) ], relative_address( pc, op ) ); break; case OP_BLEZ: - util::stream_format( stream, "blez %s,%s,$%08x", s_cpugenreg[ INS_RS( op ) ], s_cpugenreg[ INS_RT( op ) ], relative_address( state, pc, op ) ); + util::stream_format( stream, "blez %s,%s,$%08x", s_cpugenreg[ INS_RS( op ) ], s_cpugenreg[ INS_RT( op ) ], relative_address( pc, op ) ); break; case OP_BGTZ: - util::stream_format( stream, "bgtz %s,%s,$%08x", s_cpugenreg[ INS_RS( op ) ], s_cpugenreg[ INS_RT( op ) ], relative_address( state, pc, op ) ); + util::stream_format( stream, "bgtz %s,%s,$%08x", s_cpugenreg[ INS_RS( op ) ], s_cpugenreg[ INS_RT( op ) ], relative_address( pc, op ) ); break; case OP_ADDI: util::stream_format( stream, "addi %s,%s,%s", s_cpugenreg[ INS_RT( op ) ], s_cpugenreg[ INS_RS( op ) ], make_signed_hex_str_16( INS_IMMEDIATE( op ) ) ); @@ -372,7 +364,7 @@ unsigned DasmPSXCPU( psxcpu_state *state, std::ostream &stream, uint32_t pc, con util::stream_format( stream, "xori %s,%s,$%04x", s_cpugenreg[ INS_RT( op ) ], s_cpugenreg[ INS_RS( op ) ], INS_IMMEDIATE( op ) ); break; case OP_LUI: - util::stream_format( stream, "lui %s,%s", s_cpugenreg[ INS_RT( op ) ], upper_address( op, opram ) ); + util::stream_format( stream, "lui %s,%s", s_cpugenreg[ INS_RT( op ) ], upper_address( op, pos, opcodes ) ); break; case OP_COP0: switch( INS_RS( op ) ) @@ -394,10 +386,10 @@ unsigned DasmPSXCPU( psxcpu_state *state, std::ostream &stream, uint32_t pc, con switch( INS_BC( op ) ) { case BC_BCF: - util::stream_format( stream, "bc0f $%08x", relative_address( state, pc, op ) ); + util::stream_format( stream, "bc0f $%08x", relative_address( pc, op ) ); break; case BC_BCT: - util::stream_format( stream, "bc0t $%08x", relative_address( state, pc, op ) ); + util::stream_format( stream, "bc0t $%08x", relative_address( pc, op ) ); break; } break; @@ -451,10 +443,10 @@ unsigned DasmPSXCPU( psxcpu_state *state, std::ostream &stream, uint32_t pc, con switch( INS_BC( op ) ) { case BC_BCF: - util::stream_format( stream, "bc1f $%08x", relative_address( state, pc, op ) ); + util::stream_format( stream, "bc1f $%08x", relative_address( pc, op ) ); break; case BC_BCT: - util::stream_format( stream, "bc1t $%08x", relative_address( state, pc, op ) ); + util::stream_format( stream, "bc1t $%08x", relative_address( pc, op ) ); break; } break; @@ -488,10 +480,10 @@ unsigned DasmPSXCPU( psxcpu_state *state, std::ostream &stream, uint32_t pc, con switch( INS_BC( op ) ) { case BC_BCF: - util::stream_format( stream, "bc2f $%08x", relative_address( state, pc, op ) ); + util::stream_format( stream, "bc2f $%08x", relative_address( pc, op ) ); break; case BC_BCT: - util::stream_format( stream, "bc2t $%08x", relative_address( state, pc, op ) ); + util::stream_format( stream, "bc2t $%08x", relative_address( pc, op ) ); break; } break; @@ -598,10 +590,10 @@ unsigned DasmPSXCPU( psxcpu_state *state, std::ostream &stream, uint32_t pc, con switch( INS_BC( op ) ) { case BC_BCF: - util::stream_format( stream, "bc3f $%08x", relative_address( state, pc, op ) ); + util::stream_format( stream, "bc3f $%08x", relative_address( pc, op ) ); break; case BC_BCT: - util::stream_format( stream, "bc3t $%08x", relative_address( state, pc, op ) ); + util::stream_format( stream, "bc3t $%08x", relative_address( pc, op ) ); break; } break; @@ -616,64 +608,64 @@ unsigned DasmPSXCPU( psxcpu_state *state, std::ostream &stream, uint32_t pc, con } break; case OP_LB: - util::stream_format( stream, "lb %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "lb %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_LH: - util::stream_format( stream, "lh %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "lh %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_LWL: - util::stream_format( stream, "lwl %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "lwl %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_LW: - util::stream_format( stream, "lw %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "lw %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_LBU: - util::stream_format( stream, "lbu %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "lbu %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_LHU: - util::stream_format( stream, "lhu %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "lhu %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_LWR: - util::stream_format( stream, "lwr %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "lwr %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_SB: - util::stream_format( stream, "sb %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "sb %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_SH: - util::stream_format( stream, "sh %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "sh %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_SWL: - util::stream_format( stream, "swl %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "swl %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_SW: - util::stream_format( stream, "sw %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "sw %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_SWR: - util::stream_format( stream, "swr %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "swr %s,%s", s_cpugenreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_LWC0: - util::stream_format( stream, "lwc0 %s,%s", s_cp0genreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "lwc0 %s,%s", s_cp0genreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_LWC1: - util::stream_format( stream, "lwc1 %s,%s", s_cp1genreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "lwc1 %s,%s", s_cp1genreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_LWC2: - util::stream_format( stream, "lwc2 %s,%s", s_cp2genreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "lwc2 %s,%s", s_cp2genreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_LWC3: - util::stream_format( stream, "lwc3 %s,%s", s_cp2genreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "lwc3 %s,%s", s_cp2genreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_SWC0: - util::stream_format( stream, "swc0 %s,%s", s_cp0genreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "swc0 %s,%s", s_cp0genreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_SWC1: - util::stream_format( stream, "swc1 %s,%s", s_cp1genreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "swc1 %s,%s", s_cp1genreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_SWC2: - util::stream_format( stream, "swc2 %s,%s", s_cp2genreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "swc2 %s,%s", s_cp2genreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; case OP_SWC3: - util::stream_format( stream, "swc3 %s,%s", s_cp2genreg[ INS_RT( op ) ], effective_address( state, pc, op ) ); + util::stream_format( stream, "swc3 %s,%s", s_cp2genreg[ INS_RT( op ) ], effective_address( pc, op ) ); break; } @@ -683,11 +675,5 @@ unsigned DasmPSXCPU( psxcpu_state *state, std::ostream &stream, uint32_t pc, con util::stream_format(stream, "dw $%08x", op); } - return ( opram - oldopram ) | flags | DASMFLAG_SUPPORTED; -} - - -CPU_DISASSEMBLE( psxcpu_generic ) -{ - return DasmPSXCPU( nullptr, stream, pc, opram ); + return ( pos - pc ) | flags | SUPPORTED; } diff --git a/src/devices/cpu/psx/psxdasm.h b/src/devices/cpu/psx/psxdasm.h new file mode 100644 index 00000000000..d3a6199616e --- /dev/null +++ b/src/devices/cpu/psx/psxdasm.h @@ -0,0 +1,56 @@ +// license:BSD-3-Clause +// copyright-holders:smf +/* + * PSXCPU disassembler for the MAME project written by smf + * + */ + +#ifndef MAME_CPU_PSX_PSXDASM_H +#define MAME_CPU_PSX_PSXDASM_H + +#pragma once + +class psxcpu_disassembler : public util::disasm_interface +{ +public: + struct config { + virtual ~config() = default; + + virtual uint32_t pc() = 0; + virtual uint32_t delayr() = 0; + virtual uint32_t delayv() = 0; + virtual uint32_t r(int i) = 0; + }; + + psxcpu_disassembler(config *conf = nullptr); + virtual ~psxcpu_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *const s_cpugenreg[]; + static const char *const s_cp0genreg[]; + static const char *const s_cp0ctlreg[]; + static const char *const s_cp1genreg[]; + static const char *const s_cp1ctlreg[]; + static const char *const s_cp2genreg[]; + static const char *const s_cp2ctlreg[]; + static const char *const s_cp3genreg[]; + static const char *const s_cp3ctlreg[]; + static const char *const s_gtesf[]; + static const char *const s_gtemx[]; + static const char *const s_gtev[]; + static const char *const s_gtecv[]; + static const char *const s_gtelm[]; + + std::string make_signed_hex_str_16( uint32_t value ); + std::string effective_address( uint32_t pc, uint32_t op ); + uint32_t relative_address( uint32_t pc, uint32_t op ); + uint32_t jump_address( uint32_t pc, uint32_t op ); + std::string upper_address( uint32_t op, offs_t pos, const data_buffer &opcodes ); + + config *m_config; +}; + +#endif diff --git a/src/devices/cpu/rsp/rsp.cpp b/src/devices/cpu/rsp/rsp.cpp index 6565fa6924d..1c3eb4b694e 100644 --- a/src/devices/cpu/rsp/rsp.cpp +++ b/src/devices/cpu/rsp/rsp.cpp @@ -17,6 +17,7 @@ #include "rspdefs.h" +#include "rsp_dasm.h" DEFINE_DEVICE_TYPE(RSP, rsp_device, "rsp", "RSP") @@ -150,10 +151,9 @@ device_memory_interface::space_config_vector rsp_device::memory_space_config() c }; } -offs_t rsp_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *rsp_device::create_disassembler() { - extern CPU_DISASSEMBLE( rsp ); - return CPU_DISASSEMBLE_NAME( rsp )(this, stream, pc, oprom, opram, options); + return new rsp_disassembler; } void rsp_device::rsp_add_imem(uint32_t *base) @@ -319,10 +319,10 @@ void rsp_device::unimplemented_opcode(uint32_t op) { if ((machine().debug_flags & DEBUG_FLAG_ENABLED) != 0) { - util::ovectorstream string; - rsp_dasm_one(string, m_ppc, op); - string.put('\0'); - osd_printf_debug("%08X: %s\n", m_ppc, &string.vec()[0]); + std::ostringstream string; + rsp_disassembler rspd; + rspd.dasm_one(string, m_ppc, op); + osd_printf_debug("%08X: %s\n", m_ppc, string.str().c_str()); } #if SAVE_DISASM @@ -747,13 +747,13 @@ void rsp_device::execute_run() int i, l; static uint32_t prev_regs[32]; - util::ovectorstream string; - rsp_dasm_one(string, m_ppc, op); - string.put('\0'); + rsp_disassembler rspd; + std::ostringstream string; + rspd.dasm_one(string, m_ppc, op); - fprintf(m_exec_output, "%08X: %s", m_ppc, &string.vec()[0]); + fprintf(m_exec_output, "%08X: %s", m_ppc, string.str().c_str()); - l = string.vec().size() - 1; + l = string.str().size(); if (l < 36) { for (i=l; i < 36; i++) diff --git a/src/devices/cpu/rsp/rsp.h b/src/devices/cpu/rsp/rsp.h index cf1a7019f92..6c876671ab1 100644 --- a/src/devices/cpu/rsp/rsp.h +++ b/src/devices/cpu/rsp/rsp.h @@ -160,9 +160,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 4; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; void unimplemented_opcode(uint32_t op); @@ -299,7 +297,4 @@ private: DECLARE_DEVICE_TYPE(RSP, rsp_device) -extern offs_t rsp_dasm_one(std::ostream &stream, offs_t pc, uint32_t op); - - #endif // MAME_CPU_RSP_RSP_H diff --git a/src/devices/cpu/rsp/rsp_dasm.cpp b/src/devices/cpu/rsp/rsp_dasm.cpp index 1222c0023a4..dec44596d45 100644 --- a/src/devices/cpu/rsp/rsp_dasm.cpp +++ b/src/devices/cpu/rsp/rsp_dasm.cpp @@ -7,8 +7,9 @@ */ #include "emu.h" +#include "rsp_dasm.h" -/*static const char *const reg[32] = +/*const char *const rsp_disassembler::reg[32] = { "0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15", @@ -17,7 +18,7 @@ }; */ -static const char *const reg[32] = +const char *const rsp_disassembler::reg[32] = { "$0", "$at", "$v0", "$v1", "$a0", "$a1", "$a2", "$a3", "$t0", "$t1", "$t2", "$t3", "$t4", "$t5", "$t6", "$t7", @@ -25,7 +26,7 @@ static const char *const reg[32] = "$t8", "$t9", "$k0", "$k1", "$gp", "$sp", "$fp", "$ra" }; -static const char *const vreg[32] = +const char *const rsp_disassembler::vreg[32] = { " v0", " v1", " v2", " v3", " v4", " v5", " v6", " v7", " v8", " v9", "v10", "v11", "v12", "v13", "v14", "v15", @@ -33,7 +34,7 @@ static const char *const vreg[32] = "v24", "v25", "v26", "v27", "v28", "v29", "v30", "v31" }; -static const char *const cop0_regs[32] = +const char *const rsp_disassembler::cop0_regs[32] = { "SP_MEM_ADDR", "SP_DRAM_ADDR", "SP_RD_LEN", "SP_WR_LEN", "SP_STATUS", "SP_DMA_FULL", "SP_DMA_BUSY", "SP_SEMAPHORE", @@ -45,36 +46,34 @@ static const char *const cop0_regs[32] = "???", "???", "???", "???" }; -static const char *const element[16] = +const char *const rsp_disassembler::element[16] = { "", "[???]", "[00224466]", "[11335577]", "[00004444]", "[11115555]", "[22226666]", "[33337777]", "[00000000]", "[11111111]", "[22222222]", "[33333333]", "[44444444]", "[55555555]", "[66666666]", "[77777777]" }; -static const char *const element2[16] = +const char *const rsp_disassembler::element2[16] = { "01234567", "????????", "00224466", "11335577", "00004444", "11115555", "22226666", "33337777", "00000000", "11111111", "22222222", "33333333", "44444444", "55555555", "66666666", "77777777" }; -static inline char *signed_imm16(uint32_t op) +inline std::string rsp_disassembler::signed_imm16(uint32_t op) { - static char temp[10]; int16_t value = op & 0xffff; if (value < 0) { - sprintf(temp, "-$%04x", -value); + return util::string_format("-$%04x", -value); } else { - sprintf(temp, "$%04x", value); + return util::string_format("$%04x", value); } - return temp; } -static void disasm_cop0(std::ostream &stream, uint32_t op) +void rsp_disassembler::disasm_cop0(std::ostream &stream, uint32_t op) { int rt = (op >> 16) & 31; int rd = (op >> 11) & 31; @@ -88,7 +87,7 @@ static void disasm_cop0(std::ostream &stream, uint32_t op) } } -static void disasm_cop2(std::ostream &stream, uint32_t op) +void rsp_disassembler::disasm_cop2(std::ostream &stream, uint32_t op) { int rt = (op >> 16) & 31; int rd = (op >> 11) & 31; @@ -175,7 +174,7 @@ static void disasm_cop2(std::ostream &stream, uint32_t op) } } -static void disasm_lwc2(std::ostream &stream, uint32_t op) +void rsp_disassembler::disasm_lwc2(std::ostream &stream, uint32_t op) { int dest = (op >> 16) & 0x1f; int base = (op >> 21) & 0x1f; @@ -202,7 +201,7 @@ static void disasm_lwc2(std::ostream &stream, uint32_t op) } } -static void disasm_swc2(std::ostream &stream, uint32_t op) +void rsp_disassembler::disasm_swc2(std::ostream &stream, uint32_t op) { int dest = (op >> 16) & 0x1f; int base = (op >> 21) & 0x1f; @@ -229,7 +228,12 @@ static void disasm_swc2(std::ostream &stream, uint32_t op) } } -offs_t rsp_dasm_one(std::ostream &stream, offs_t pc, uint32_t op) +u32 rsp_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t rsp_disassembler::dasm_one(std::ostream &stream, offs_t pc, u32 op) { int rs = (op >> 21) & 31; int rt = (op >> 16) & 31; @@ -260,7 +264,7 @@ offs_t rsp_dasm_one(std::ostream &stream, offs_t pc, uint32_t op) case 0x04: util::stream_format(stream, "sllv %s, %s, %s", reg[rd], reg[rt], reg[rs]); break; case 0x06: util::stream_format(stream, "srlv %s, %s, %s", reg[rd], reg[rt], reg[rs]); break; case 0x07: util::stream_format(stream, "srav %s, %s, %s", reg[rd], reg[rt], reg[rs]); break; - case 0x08: util::stream_format(stream, "jr %s", reg[rs]); if (rs == 31) flags = DASMFLAG_STEP_OUT; break; + case 0x08: util::stream_format(stream, "jr %s", reg[rs]); if (rs == 31) flags = STEP_OUT; break; case 0x09: { if (rd == 31) @@ -271,10 +275,10 @@ offs_t rsp_dasm_one(std::ostream &stream, offs_t pc, uint32_t op) { util::stream_format(stream, "jalr %s, %s", reg[rs], reg[rd]); } - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; } - case 0x0d: util::stream_format(stream, "break"); flags = DASMFLAG_STEP_OVER; break; + case 0x0d: util::stream_format(stream, "break"); flags = STEP_OVER; break; case 0x20: util::stream_format(stream, "add %s, %s, %s", reg[rd], reg[rs], reg[rt]); break; case 0x21: util::stream_format(stream, "addu %s, %s, %s", reg[rd], reg[rs], reg[rt]); break; case 0x22: util::stream_format(stream, "sub %s, %s, %s", reg[rd], reg[rs], reg[rt]); break; @@ -338,14 +342,11 @@ offs_t rsp_dasm_one(std::ostream &stream, offs_t pc, uint32_t op) default: util::stream_format(stream, "???"); break; } - return 4 | flags | DASMFLAG_SUPPORTED; + return 4 | flags | SUPPORTED; } -/*****************************************************************************/ - -CPU_DISASSEMBLE( rsp ) +offs_t rsp_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - uint32_t op = *(uint32_t *)opram; - op = big_endianize_int32(op); - return rsp_dasm_one(stream, pc, op); + u32 op = opcodes.r32(pc); + return dasm_one(stream, pc, op); } diff --git a/src/devices/cpu/rsp/rsp_dasm.h b/src/devices/cpu/rsp/rsp_dasm.h new file mode 100644 index 00000000000..72dcdaae5e6 --- /dev/null +++ b/src/devices/cpu/rsp/rsp_dasm.h @@ -0,0 +1,38 @@ +// license:BSD-3-Clause +// copyright-holders:Ville Linde, Ryan Holtz +/* + Nintendo/SGI RSP Disassembler + + Written by Ville Linde +*/ + +#ifndef MAME_CPU_RSP_RSP_DASM_H +#define MAME_CPU_RSP_RSP_DASM_H + +#pragma once + +class rsp_disassembler : public util::disasm_interface +{ +public: + rsp_disassembler() = default; + virtual ~rsp_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + + offs_t dasm_one(std::ostream &stream, offs_t pc, u32 op); + +private: + static const char *const reg[32]; + static const char *const vreg[32]; + static const char *const cop0_regs[32]; + static const char *const element[16]; + static const char *const element2[16]; + inline std::string signed_imm16(uint32_t op); + void disasm_cop0(std::ostream &stream, uint32_t op); + void disasm_cop2(std::ostream &stream, uint32_t op); + void disasm_lwc2(std::ostream &stream, uint32_t op); + void disasm_swc2(std::ostream &stream, uint32_t op); +}; + +#endif diff --git a/src/devices/cpu/rsp/rspcp2d.cpp b/src/devices/cpu/rsp/rspcp2d.cpp index 7152d6cbe59..47972b54747 100644 --- a/src/devices/cpu/rsp/rspcp2d.cpp +++ b/src/devices/cpu/rsp/rspcp2d.cpp @@ -13,6 +13,7 @@ #include "rspcp2d.h" #include "rsp.h" +#include "rsp_dasm.h" #include "rspcp2.h" #include "cpu/drcfe.h" @@ -138,8 +139,9 @@ void rsp_cop2_drc::cfunc_unimplemented_opcode() const uint32_t ppc = m_rsp.m_ppc; if ((m_machine.debug_flags & DEBUG_FLAG_ENABLED) != 0) { + rsp_disassembler rspd; std::ostringstream stream; - rsp_dasm_one(stream, ppc, m_rspcop2_state->op); + rspd.dasm_one(stream, ppc, m_rspcop2_state->op); const std::string stream_string = stream.str(); osd_printf_debug("%08X: %s\n", ppc, stream_string.c_str()); } diff --git a/src/devices/cpu/rsp/rspdrc.cpp b/src/devices/cpu/rsp/rspdrc.cpp index cdc10338571..3c7a1f2efab 100644 --- a/src/devices/cpu/rsp/rspdrc.cpp +++ b/src/devices/cpu/rsp/rspdrc.cpp @@ -20,6 +20,7 @@ #include "emu.h" #include "rsp.h" +#include "rsp_dasm.h" #include "rspfe.h" #include "rspcp2.h" @@ -34,8 +35,6 @@ using namespace uml; -CPU_DISASSEMBLE( rsp ); - /*************************************************************************** CONSTANTS ***************************************************************************/ @@ -1288,9 +1287,9 @@ void rsp_device::log_add_disasm_comment(drcuml_block *block, uint32_t pc, uint32 { if (m_drcuml->logging()) { - util::ovectorstream buffer; - rsp_dasm_one(buffer, pc, op); - buffer.put('\0'); - block->append_comment("%08X: %s", pc, &buffer.vec()[0]); // comment + rsp_disassembler rspd; + std::ostringstream buffer; + rspd.dasm_one(buffer, pc, op); + block->append_comment("%08X: %s", pc, buffer.str()); // comment } } diff --git a/src/devices/cpu/s2650/2650dasm.cpp b/src/devices/cpu/s2650/2650dasm.cpp index 872de095a3b..38f325e02c1 100644 --- a/src/devices/cpu/s2650/2650dasm.cpp +++ b/src/devices/cpu/s2650/2650dasm.cpp @@ -10,859 +10,543 @@ **************************************************************************/ #include "emu.h" - -static const uint8_t *rambase; -static offs_t pcbase; - -#define readarg(A) (rambase[(A) - pcbase]) - -/* Set this to 1 to disassemble using Z80 style mnemonics */ -#define HJB 0 - -/* Set this to 1 to give names to condition codes and flag bits */ -#define MNEMO 1 +#include "2650dasm.h" /* handy table to build relative offsets from HR (holding register) */ -static const int rel[0x100] = { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, - 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, - 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, - 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, +const int s2650_disassembler::rel[0x100] = { + 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, + 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, + 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, + 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, -64,-63,-62,-61,-60,-59,-58,-57,-56,-55,-54,-53,-52,-51,-50,-49, -48,-47,-46,-45,-44,-43,-42,-41,-40,-39,-38,-37,-36,-35,-34,-33, -32,-31,-30,-29,-28,-27,-26,-25,-24,-23,-22,-21,-20,-19,-18,-17, -16,-15,-14,-13,-12,-11,-10, -9, -8, -7, -6, -5, -4, -3, -2, -1, - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, - 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, - 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, - 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, + 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, + 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, + 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, + 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, -64,-63,-62,-61,-60,-59,-58,-57,-56,-55,-54,-53,-52,-51,-50,-49, -48,-47,-46,-45,-44,-43,-42,-41,-40,-39,-38,-37,-36,-35,-34,-33, -32,-31,-30,-29,-28,-27,-26,-25,-24,-23,-22,-21,-20,-19,-18,-17, -16,-15,-14,-13,-12,-11,-10, -9, -8, -7, -6, -5, -4, -3, -2, -1, }; -typedef char* (*callback) (int addr); -static callback find_symbol = nullptr; - -static char *SYM(int addr) +std::string s2650_disassembler::SYM(int addr) { - static char buff[8+1]; - char * s = nullptr; - - if (find_symbol) s = (*find_symbol)(addr); - if (s) return s; - - sprintf(buff, "$%04x", addr); - return buff; + return util::string_format("$%04x", addr); } /* format an immediate */ -static char *IMM(int pc) +std::string s2650_disassembler::IMM(offs_t pc, const data_buffer ¶ms) { - static char buff[32]; - - sprintf(buff, "$%02x", readarg(pc)); - return buff; + return util::string_format("$%02x", params.r8(pc)); } -#if MNEMO -static const char cc[4] = { 'z', 'p', 'm', 'a' }; +const char s2650_disassembler::cc[4] = { 'z', 'p', 'm', 'a' }; + +void s2650_disassembler::add(std::string &buf, std::string str) +{ + if(!buf.empty()) + buf += '+'; + buf += str; +} /* format an immediate for PSL */ -static char *IMM_PSL(int pc) +std::string s2650_disassembler::IMM_PSL(offs_t pc, const data_buffer ¶ms) { - static char buff[32]; - char *p = buff; - int v = readarg(pc); + u8 v = params.r8(pc); if (v == 0xff) { - p += sprintf(p, "all"); + return "all"; + } else { + std::string buff; switch (v & 0xc0) { - case 0x40: p += sprintf(p, "p+"); break; - case 0x80: p += sprintf(p, "m+"); break; - case 0xc0: p += sprintf(p, "cc+"); break; + case 0x40: add(buff, "p"); break; + case 0x80: add(buff, "m"); break; + case 0xc0: add(buff, "cc"); break; } if (v & 0x20) /* inter digit carry */ - p += sprintf(p, "idc+"); + add(buff, "idc"); if (v & 0x10) /* register select */ - p += sprintf(p, "rs+"); + add(buff, "rs"); if (v & 0x08) /* with carry */ - p += sprintf(p, "wc+"); + add(buff, "wc"); if (v & 0x04) /* overflow */ - p += sprintf(p, "ovf+"); + add(buff, "ovf"); if (v & 0x02) /* 2's complement comparisons */ - p += sprintf(p, "com+"); + add(buff, "com"); if (v & 0x01) /* carry */ - p += sprintf(p, "c+"); - if (p > buff) - *--p = '\0'; + add(buff, "c"); + return buff; } - return buff; } /* format an immediate for PSU (processor status upper) */ -static char *IMM_PSU(int pc) +std::string s2650_disassembler::IMM_PSU(offs_t pc, const data_buffer ¶ms) { - static char buff[32]; - char *p = buff; - int v = readarg(pc); + int v = params.r8(pc); if (v == 0xff) { - p += sprintf(p, "all"); + return "all"; } else { + std::string buff; if (v & 0x80) /* sense input */ - p += sprintf(p, "si+"); + add(buff, "si"); if (v & 0x40) /* flag output */ - p += sprintf(p, "fo+"); + add(buff, "fo"); if (v & 0x20) /* interrupt inhibit */ - p += sprintf(p, "ii+"); + add(buff, "ii"); if (v & 0x10) /* unused bit 4 */ - p += sprintf(p, "4+"); + add(buff, "4"); if (v & 0x08) /* unused bit 3 */ - p += sprintf(p, "3+"); + add(buff, "3"); if (v & 0x04) /* stack pointer bit 2 */ - p += sprintf(p, "sp2+"); + add(buff, "sp2"); if (v & 0x02) /* stack pointer bit 1 */ - p += sprintf(p, "sp1+"); + add(buff, "sp1"); if (v & 0x01) /* stack pointer bit 0 */ - p += sprintf(p, "sp0+"); - if (p > buff) - *--p = '\0'; + add(buff, "sp0"); + return buff; } - return buff; } -#else -static const char cc[4] = { '0', '1', '2', '3' }; -#define IMM_PSL IMM -#define IMM_PSU IMM -#endif /* format an relative address */ -static char *REL(int pc) +std::string s2650_disassembler::REL(offs_t pc, const data_buffer ¶ms) { -static char buff[32]; -int o = readarg(pc); - sprintf(buff, "%s%s", (o&0x80)?"*":"", SYM((pc&0x6000)+((pc+1+rel[o])&0x1fff))); - return buff; + int o = params.r8(pc); + return util::string_format("%s%s", (o&0x80)?"*":"", SYM((pc&0x6000)+((pc+1+rel[o])&0x1fff))); } /* format an relative address (implicit page 0) */ -static char *REL0(int pc) +std::string s2650_disassembler::REL0(offs_t pc, const data_buffer ¶ms) { -static char buff[32]; -int o = readarg(pc); - sprintf(buff, "%s%s", (o&0x80)?"*":"", SYM((rel[o]) & 0x1fff)); - return buff; + int o = params.r8(pc); + return util::string_format("%s%s", (o&0x80)?"*":"", SYM((rel[o]) & 0x1fff)); } /* format a destination register and an absolute address */ -static char *ABS(int load, int r, int pc) +std::string s2650_disassembler::ABS(int load, int r, offs_t pc, const data_buffer ¶ms) { - static char buff[32]; - int h = readarg(pc); - int l = readarg((pc&0x6000)+((pc+1)&0x1fff)); + int h = params.r8(pc); + int l = params.r8((pc&0x6000)+((pc+1)&0x1fff)); int a = (pc & 0x6000) + ((h & 0x1f) << 8) + l; -#if HJB - if (load) { - switch (h >> 5) { - case 0: sprintf(buff, "r%d,(%s)", r, SYM(a)); break; - case 1: sprintf(buff, "r0,(%s,r%d++)", SYM(a), r); break; - case 2: sprintf(buff, "r0,(%s,r%d--)", SYM(a), r); break; - case 3: sprintf(buff, "r0,(%s,r%d)", SYM(a), r); break; - case 4: sprintf(buff, "r%d,*(%s)", r, SYM(a)); break; - case 5: sprintf(buff, "r0,*(%s,r%d++)", SYM(a), r); break; - case 6: sprintf(buff, "r0,*(%s,r%d--)", SYM(a), r); break; - case 7: sprintf(buff, "r0,*(%s,r%d)", SYM(a), r); break; + if (m_config->get_z80_mnemonics_mode()) { + if (load) { + switch (h >> 5) { + case 0: return util::string_format("r%d,(%s)", r, SYM(a)); + case 1: return util::string_format("r0,(%s,r%d++)", SYM(a), r); + case 2: return util::string_format("r0,(%s,r%d--)", SYM(a), r); + case 3: return util::string_format("r0,(%s,r%d)", SYM(a), r); + case 4: return util::string_format("r%d,*(%s)", r, SYM(a)); + case 5: return util::string_format("r0,*(%s,r%d++)", SYM(a), r); + case 6: return util::string_format("r0,*(%s,r%d--)", SYM(a), r); + case 7: return util::string_format("r0,*(%s,r%d)", SYM(a), r); + } + } else { + switch (h >> 5) { + case 0: return util::string_format("(%s),r%d", SYM(a), r); + case 1: return util::string_format("(%s,r%d++),r0", SYM(a), r); + case 2: return util::string_format("(%s,r%d--),r0", SYM(a), r); + case 3: return util::string_format("(%s,r%d),r0", SYM(a), r); + case 4: return util::string_format("*(%s),r%d", SYM(a), r); + case 5: return util::string_format("*(%s,r%d++),r0", SYM(a), r); + case 6: return util::string_format("*(%s,r%d--),r0", SYM(a), r); + case 7: return util::string_format("*(%s,r%d),r0", SYM(a), r); + } } } else { switch (h >> 5) { - case 0: sprintf(buff, "(%s),r%d", SYM(a), r); break; - case 1: sprintf(buff, "(%s,r%d++),r0", SYM(a), r); break; - case 2: sprintf(buff, "(%s,r%d--),r0", SYM(a), r); break; - case 3: sprintf(buff, "(%s,r%d),r0", SYM(a), r); break; - case 4: sprintf(buff, "*(%s),r%d", SYM(a), r); break; - case 5: sprintf(buff, "*(%s,r%d++),r0", SYM(a), r); break; - case 6: sprintf(buff, "*(%s,r%d--),r0", SYM(a), r); break; - case 7: sprintf(buff, "*(%s,r%d),r0", SYM(a), r); break; + case 0: return util::string_format("%d %s", r, SYM(a)); + case 1: return util::string_format("0 %s,r%d+", SYM(a), r); + case 2: return util::string_format("0 %s,r%d-", SYM(a), r); + case 3: return util::string_format("0 %s,r%d", SYM(a), r); + case 4: return util::string_format("%d *%s", r, SYM(a)); + case 5: return util::string_format("0 *%s,r%d+", SYM(a), r); + case 6: return util::string_format("0 *%s,r%d-", SYM(a), r); + case 7: return util::string_format("0 *%s,r%d", SYM(a), r); } } -#else - switch (h >> 5) { - case 0: sprintf(buff, "%d %s", r, SYM(a)); break; - case 1: sprintf(buff, "0 %s,r%d+", SYM(a), r); break; - case 2: sprintf(buff, "0 %s,r%d-", SYM(a), r); break; - case 3: sprintf(buff, "0 %s,r%d", SYM(a), r); break; - case 4: sprintf(buff, "%d *%s", r, SYM(a)); break; - case 5: sprintf(buff, "0 *%s,r%d+", SYM(a), r); break; - case 6: sprintf(buff, "0 *%s,r%d-", SYM(a), r); break; - case 7: sprintf(buff, "0 *%s,r%d", SYM(a), r); break; - } -#endif - return buff; + return ""; } /* format an (branch) absolute address */ -static char *ADR(int pc) +std::string s2650_disassembler::ADR(offs_t pc, const data_buffer ¶ms) { - static char buff[32]; - int h = readarg(pc); - int l = readarg((pc&0x6000)+((pc+1)&0x1fff)); + int h = params.r8(pc); + int l = params.r8((pc&0x6000)+((pc+1)&0x1fff)); int a = ((h & 0x7f) << 8) + l; if (h & 0x80) - sprintf(buff, "*%s", SYM(a)); + return util::string_format("*%s", SYM(a)); else - sprintf(buff, "%s", SYM(a)); - return buff; + return util::string_format("%s", SYM(a)); +} + +s2650_disassembler::s2650_disassembler(config *conf) : m_config(conf) +{ } /* disassemble one instruction at PC into buff. return byte size of instr */ -CPU_DISASSEMBLE(s2650) +offs_t s2650_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { uint32_t flags = 0; int PC = pc; - int op = oprom[0]; + int op = opcodes.r8(pc); int rv = op & 3; - rambase = opram; - pcbase = PC; + bool z80 = m_config->get_z80_mnemonics_mode(); pc += 1; switch (op) { case 0x00: case 0x01: case 0x02: case 0x03: -#if HJB - util::stream_format(stream, "ld r0,r%d", rv); -#else - util::stream_format(stream, "lodz,%d", rv); -#endif + util::stream_format(stream, z80 ? "ld r0,r%d" : "lodz,%d", rv); break; case 0x04: case 0x05: case 0x06: case 0x07: -#if HJB - util::stream_format(stream, "ld r%d,%s", rv, IMM(pc)); -#else - util::stream_format(stream, "lodi,%d %s", rv, IMM(pc)); -#endif + util::stream_format(stream, z80 ? "ld r%d,%s" : "lodi,%d %s", rv, IMM(pc, params)); pc+=1; break; case 0x08: case 0x09: case 0x0a: case 0x0b: -#if HJB - util::stream_format(stream, "ld r%d,(%s)", rv, REL(pc)); -#else - util::stream_format(stream, "lodr,%d %s", rv, REL(pc)); -#endif + util::stream_format(stream, z80 ? "ld r%d,(%s)" : "lodr,%d %s", rv, REL(pc, params)); pc+=1; break; case 0x0c: case 0x0d: case 0x0e: case 0x0f: -#if HJB - util::stream_format(stream, "ld %s", ABS(1,rv,pc)); -#else - util::stream_format(stream, "loda,%s", ABS(1,rv,pc)); -#endif + util::stream_format(stream, z80 ? "ld %s" : "loda,%s", ABS(1,rv,pc, params)); pc+=2; break; case 0x10: case 0x11: -#if HJB - util::stream_format(stream, "**** $%02X",op); -#else - util::stream_format(stream, "**** $%02X",op); -#endif + util::stream_format(stream, z80 ? "**** $%02X" : "**** $%02X",op); break; case 0x12: -#if HJB - util::stream_format(stream, "ld r0,psu"); -#else - util::stream_format(stream, "spsu"); -#endif + util::stream_format(stream, z80 ? "ld r0,psu" : "spsu"); break; case 0x13: -#if HJB - util::stream_format(stream, "ld r0,psl"); -#else - util::stream_format(stream, "spsl"); -#endif + util::stream_format(stream, z80 ? "ld r0,psl" : "spsl"); break; case 0x14: case 0x15: case 0x16: case 0x17: -#if HJB - if (rv == 3) - util::stream_format(stream, "ret"); - else - util::stream_format(stream, "ret %c", cc[rv]); -#else - util::stream_format(stream, "retc %c", cc[rv]); -#endif - flags = DASMFLAG_STEP_OUT; + if (z80) { + if (rv == 3) + util::stream_format(stream, "ret"); + else + util::stream_format(stream, "ret %c", cc[rv]); + } else + util::stream_format(stream, "retc %c", cc[rv]); + flags = STEP_OUT; break; case 0x18: case 0x19: case 0x1a: case 0x1b: -#if HJB - if (rv == 3) - util::stream_format(stream, "jr %s", REL(pc)); - else - util::stream_format(stream, "jr %c,%s", cc[rv], REL(pc)); -#else - util::stream_format(stream, "bctr,%c %s", cc[rv], REL(pc)); -#endif + if (z80) { + if (rv == 3) + util::stream_format(stream, "jr %s", REL(pc, params)); + else + util::stream_format(stream, "jr %c,%s", cc[rv], REL(pc, params)); + } else + util::stream_format(stream, "bctr,%c %s", cc[rv], REL(pc, params)); pc+=1; break; case 0x1c: case 0x1d: case 0x1e: case 0x1f: -#if HJB - if (rv == 3) - util::stream_format(stream, "jp %s", ADR(pc)); - else - util::stream_format(stream, "jp %c,%s", cc[rv], ADR(pc)); -#else - util::stream_format(stream, "bcta,%c %s", cc[rv], ADR(pc)); -#endif + if (z80) { + if (rv == 3) + util::stream_format(stream, "jp %s", ADR(pc, params)); + else + util::stream_format(stream, "jp %c,%s", cc[rv], ADR(pc, params)); + } else + util::stream_format(stream, "bcta,%c %s", cc[rv], ADR(pc, params)); pc+=2; break; case 0x20: case 0x21: case 0x22: case 0x23: -#if HJB - util::stream_format(stream, "xor r0,r%d", rv); -#else - util::stream_format(stream, "eorz,%d", rv); -#endif + util::stream_format(stream, z80 ? "xor r0,r%d" : "eorz,%d", rv); break; case 0x24: case 0x25: case 0x26: case 0x27: -#if HJB - util::stream_format(stream, "xor r%d,%s", rv, IMM(pc)); -#else - util::stream_format(stream, "eori,%d %s", rv, IMM(pc)); -#endif + util::stream_format(stream, z80 ? "xor r%d,%s" : "eori,%d %s", rv, IMM(pc, params)); pc+=1; break; case 0x28: case 0x29: case 0x2a: case 0x2b: -#if HJB - util::stream_format(stream, "xor r%d,(%s)", rv, REL(pc)); -#else - util::stream_format(stream, "eorr,%d %s", rv, REL(pc)); -#endif + util::stream_format(stream, z80 ? "xor r%d,(%s)" : "eorr,%d %s", rv, REL(pc, params)); pc+=1; break; case 0x2c: case 0x2d: case 0x2e: case 0x2f: -#if HJB - util::stream_format(stream, "xor %s", ABS(1,rv,pc)); -#else - util::stream_format(stream, "eora,%s", ABS(1,rv,pc)); -#endif + util::stream_format(stream, z80 ? "xor %s" : "eora,%s", ABS(1,rv,pc, params)); pc+=2; break; case 0x30: case 0x31: case 0x32: case 0x33: -#if HJB - util::stream_format(stream, "in r%d,(ctrl)", rv); -#else - util::stream_format(stream, "redc,%d", rv); -#endif + util::stream_format(stream, z80 ? "in r%d,(ctrl)" : "redc,%d", rv); break; case 0x34: case 0x35: case 0x36: case 0x37: -#if HJB - if (rv == 3) - util::stream_format(stream, "iret"); - else - util::stream_format(stream, "iret %c", cc[rv]); -#else - util::stream_format(stream, "rete %c", cc[rv]); -#endif - flags = DASMFLAG_STEP_OUT; + if (z80) { + if (rv == 3) + util::stream_format(stream, "iret"); + else + util::stream_format(stream, "iret %c", cc[rv]); + } else + util::stream_format(stream, "rete %c", cc[rv]); + flags = STEP_OUT; break; case 0x38: case 0x39: case 0x3a: case 0x3b: -#if HJB - if (rv == 3) - util::stream_format(stream, "calr %s", REL(pc)); - else - util::stream_format(stream, "calr %c,%s", cc[rv], REL(pc)); -#else - util::stream_format(stream, "bstr,%c %s", cc[rv], REL(pc)); -#endif + if (z80) { + if (rv == 3) + util::stream_format(stream, "calr %s", REL(pc, params)); + else + util::stream_format(stream, "calr %c,%s", cc[rv], REL(pc, params)); + } else + util::stream_format(stream, "bstr,%c %s", cc[rv], REL(pc, params)); pc+=1; - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case 0x3c: case 0x3d: case 0x3e: case 0x3f: -#if HJB - if (rv == 3) - util::stream_format(stream, "call %s", ADR(pc)); - else - util::stream_format(stream, "call %c,%s", cc[rv], ADR(pc)); -#else - util::stream_format(stream, "bsta,%c %s", cc[rv], ADR(pc)); -#endif + if (z80) { + if (rv == 3) + util::stream_format(stream, "call %s", ADR(pc, params)); + else + util::stream_format(stream, "call %c,%s", cc[rv], ADR(pc, params)); + } else + util::stream_format(stream, "bsta,%c %s", cc[rv], ADR(pc, params)); pc+=2; - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case 0x40: util::stream_format(stream, "halt"); break; case 0x41: case 0x42: case 0x43: -#if HJB - util::stream_format(stream, "and r0,r%d", rv); -#else - util::stream_format(stream, "andz,%d", rv); -#endif + util::stream_format(stream, z80 ? "and r0,r%d" : "andz,%d", rv); break; case 0x44: case 0x45: case 0x46: case 0x47: -#if HJB - util::stream_format(stream, "and r%d,%s", rv, IMM(pc)); -#else - util::stream_format(stream, "andi,%d %s", rv, IMM(pc)); -#endif + util::stream_format(stream, z80 ? "and r%d,%s" : "andi,%d %s", rv, IMM(pc, params)); pc+=1; break; case 0x48: case 0x49: case 0x4a: case 0x4b: -#if HJB - util::stream_format(stream, "and r%d,(%s)", rv, REL(pc)); -#else - util::stream_format(stream, "andr,%d %s", rv, REL(pc)); -#endif + util::stream_format(stream, z80 ? "and r%d,(%s)" : "andr,%d %s", rv, REL(pc, params)); pc+=1; break; case 0x4c: case 0x4d: case 0x4e: case 0x4f: -#if HJB - util::stream_format(stream, "and %s", ABS(1,rv,pc)); -#else - util::stream_format(stream, "anda,%s", ABS(1,rv,pc)); -#endif + util::stream_format(stream, z80 ? "and %s" : "anda,%s", ABS(1,rv,pc, params)); pc+=2; break; case 0x50: case 0x51: case 0x52: case 0x53: -#if HJB - util::stream_format(stream, "ror r%d", rv); -#else - util::stream_format(stream, "rrr,%d", rv); -#endif + util::stream_format(stream, z80 ? "ror r%d" : "rrr,%d", rv); break; case 0x54: case 0x55: case 0x56: case 0x57: -#if HJB - util::stream_format(stream, "in r%d,(%s)", rv, IMM(pc)); -#else - util::stream_format(stream, "rede,%d %s", rv, IMM(pc)); -#endif + util::stream_format(stream, z80 ? "in r%d,(%s)" : "rede,%d %s", rv, IMM(pc, params)); pc+=1; break; case 0x58: case 0x59: case 0x5a: case 0x5b: -#if HJB - util::stream_format(stream, "jrnz r%d,%s", rv, REL(pc)); -#else - util::stream_format(stream, "brnr,%d %s", rv, REL(pc)); -#endif + util::stream_format(stream, z80 ? "jrnz r%d,%s" : "brnr,%d %s", rv, REL(pc, params)); pc+=1; break; case 0x5c: case 0x5d: case 0x5e: case 0x5f: -#if HJB - util::stream_format(stream, "jpnz r%d,%s", rv, ADR(pc)); -#else - util::stream_format(stream, "brna,%d %s", rv, ADR(pc)); -#endif + util::stream_format(stream, z80 ? "jpnz r%d,%s" : "brna,%d %s", rv, ADR(pc, params)); pc+=2; break; case 0x60: case 0x61: case 0x62: case 0x63: -#if HJB - util::stream_format(stream, "or r0,r%d", rv); -#else - util::stream_format(stream, "iorz,%d", rv); -#endif + util::stream_format(stream, z80 ? "or r0,r%d" : "iorz,%d", rv); break; case 0x64: case 0x65: case 0x66: case 0x67: -#if HJB - util::stream_format(stream, "or r%d,%s", rv, IMM(pc)); -#else - util::stream_format(stream, "iori,%d %s", rv, IMM(pc)); -#endif + util::stream_format(stream, z80 ? "or r%d,%s" : "iori,%d %s", rv, IMM(pc, params)); pc+=1; break; case 0x68: case 0x69: case 0x6a: case 0x6b: -#if HJB - util::stream_format(stream, "or r%d,(%s)", rv, REL(pc)); -#else - util::stream_format(stream, "iorr,%d %s", rv, REL(pc)); -#endif + util::stream_format(stream, z80 ? "or r%d,(%s)" : "iorr,%d %s", rv, REL(pc, params)); pc+=1; break; case 0x6c: case 0x6d: case 0x6e: case 0x6f: -#if HJB - util::stream_format(stream, "or %s", ABS(1,rv,pc)); -#else - util::stream_format(stream, "iora,%s", ABS(1,rv,pc)); -#endif + util::stream_format(stream, z80 ? "or %s" : "iora,%s", ABS(1,rv,pc, params)); pc+=2; break; case 0x70: case 0x71: case 0x72: case 0x73: -#if HJB - util::stream_format(stream, "in r%d,(data)", rv); -#else - util::stream_format(stream, "redd,%d", rv); -#endif + util::stream_format(stream, z80 ? "in r%d,(data)" : "redd,%d", rv); break; case 0x74: -#if HJB - util::stream_format(stream, "res psu,%s", IMM_PSU(pc)); -#else - util::stream_format(stream, "cpsu %s", IMM_PSU(pc)); -#endif + util::stream_format(stream, z80 ? "res psu,%s" : "cpsu %s", IMM_PSU(pc, params)); pc+=1; break; case 0x75: -#if HJB - util::stream_format(stream, "res psl,%s", IMM_PSL(pc)); -#else - util::stream_format(stream, "cpsl %s", IMM_PSL(pc)); -#endif + util::stream_format(stream, z80 ? "res psl,%s" : "cpsl %s", IMM_PSL(pc, params)); pc+=1; break; case 0x76: -#if HJB - util::stream_format(stream, "set psu,%s", IMM_PSU(pc)); -#else - util::stream_format(stream, "ppsu %s", IMM_PSU(pc)); -#endif + util::stream_format(stream, z80 ? "set psu,%s" : "ppsu %s", IMM_PSU(pc, params)); pc+=1; break; case 0x77: -#if HJB - util::stream_format(stream, "set psl,%s", IMM_PSL(pc)); -#else - util::stream_format(stream, "ppsl %s", IMM_PSL(pc)); -#endif + util::stream_format(stream, z80 ? "set psl,%s" : "ppsl %s", IMM_PSL(pc, params)); pc+=1; break; case 0x78: case 0x79: case 0x7a: case 0x7b: -#if HJB - util::stream_format(stream, "call r%d-nz,%s", rv, REL(pc)); -#else - util::stream_format(stream, "bsnr,%d %s", rv, REL(pc)); -#endif + util::stream_format(stream, z80 ? "call r%d-nz,%s" : "bsnr,%d %s", rv, REL(pc, params)); pc+=1; - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case 0x7c: case 0x7d: case 0x7e: case 0x7f: -#if HJB - util::stream_format(stream, "call r%d-nz,%s", rv, ADR(pc)); -#else - util::stream_format(stream, "bsna,%d %s", rv, ADR(pc)); -#endif + util::stream_format(stream, z80 ? "call r%d-nz,%s" : "bsna,%d %s", rv, ADR(pc, params)); pc+=2; - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case 0x80: case 0x81: case 0x82: case 0x83: -#if HJB - util::stream_format(stream, "add r0,r%d", rv); -#else - util::stream_format(stream, "addz,%d", rv); -#endif + util::stream_format(stream, z80 ? "add r0,r%d" : "addz,%d", rv); break; case 0x84: case 0x85: case 0x86: case 0x87: -#if HJB - util::stream_format(stream, "add r%d,%s", rv, IMM(pc)); -#else - util::stream_format(stream, "addi,%d %s", rv, IMM(pc)); -#endif + util::stream_format(stream, z80 ? "add r%d,%s" : "addi,%d %s", rv, IMM(pc, params)); pc+=1; break; case 0x88: case 0x89: case 0x8a: case 0x8b: -#if HJB - util::stream_format(stream, "add r%d,(%s)", rv, REL(pc)); -#else - util::stream_format(stream, "addr,%d %s", rv, REL(pc)); -#endif + util::stream_format(stream, z80 ? "add r%d,(%s)" : "addr,%d %s", rv, REL(pc, params)); pc+=1; break; case 0x8c: case 0x8d: case 0x8e: case 0x8f: -#if HJB - util::stream_format(stream, "add %s", ABS(1,rv,pc)); -#else - util::stream_format(stream, "adda,%s", ABS(1,rv,pc)); -#endif + util::stream_format(stream, z80 ? "add %s" : "adda,%s", ABS(1,rv,pc, params)); pc+=2; break; case 0x90: case 0x91: -#if HJB - util::stream_format(stream, "**** $%02X",op); -#else - util::stream_format(stream, "**** $%02X",op); -#endif + util::stream_format(stream, z80 ? "**** $%02X" : "**** $%02X",op); break; case 0x92: -#if HJB - util::stream_format(stream, "ld psu,r0"); -#else - util::stream_format(stream, "lpsu"); -#endif + util::stream_format(stream, z80 ? "ld psu,r0" : "lpsu"); break; case 0x93: -#if HJB - util::stream_format(stream, "ld psl,r0"); -#else - util::stream_format(stream, "lpsl"); -#endif + util::stream_format(stream, z80 ? "ld psl,r0" : "lpsl"); break; case 0x94: case 0x95: case 0x96: case 0x97: -#if HJB - util::stream_format(stream, "daa r%d", rv); -#else - util::stream_format(stream, "dar,%d", rv); -#endif + util::stream_format(stream, z80 ? "daa r%d" : "dar,%d", rv); break; case 0x98: case 0x99: case 0x9a: -#if HJB - util::stream_format(stream, "jr n%c,%s", cc[rv], REL(pc)); -#else - util::stream_format(stream, "bcfr,%c %s", cc[rv], REL(pc)); -#endif + util::stream_format(stream, z80 ? "jr n%c,%s" : "bcfr,%c %s", cc[rv], REL(pc, params)); pc+=1; break; case 0x9b: -#if HJB - util::stream_format(stream, "jr0 %s", REL0(pc)); -#else - util::stream_format(stream, "zbrr %s", REL0(pc)); -#endif + util::stream_format(stream, z80 ? "jr0 %s" : "zbrr %s", REL0(pc, params)); pc+=1; break; case 0x9c: case 0x9d: case 0x9e: -#if HJB - util::stream_format(stream, "jp n%c,%s", cc[rv], ADR(pc)); -#else - util::stream_format(stream, "bcfa,%c %s", cc[rv], ADR(pc)); -#endif + util::stream_format(stream, z80 ? "jp n%c,%s" : "bcfa,%c %s", cc[rv], ADR(pc, params)); pc+=2; break; case 0x9f: -#if HJB - util::stream_format(stream, "jp %s+r3", ADR(pc)); -#else - util::stream_format(stream, "bxa %s", ADR(pc)); -#endif + util::stream_format(stream, z80 ? "jp %s+r3" : "bxa %s", ADR(pc, params)); pc+=2; break; case 0xa0: case 0xa1: case 0xa2: case 0xa3: -#if HJB - util::stream_format(stream, "sub r0,r%d", rv); -#else - util::stream_format(stream, "subz,%d", rv); -#endif + util::stream_format(stream, z80 ? "sub r0,r%d" : "subz,%d", rv); break; case 0xa4: case 0xa5: case 0xa6: case 0xa7: -#if HJB - util::stream_format(stream, "sub r%d,%s", rv, IMM(pc)); -#else - util::stream_format(stream, "subi,%d %s", rv, IMM(pc)); -#endif + util::stream_format(stream, z80 ? "sub r%d,%s" : "subi,%d %s", rv, IMM(pc, params)); pc+=1; break; case 0xa8: case 0xa9: case 0xaa: case 0xab: -#if HJB - util::stream_format(stream, "sub r%d,(%s)", rv, REL(pc)); -#else - util::stream_format(stream, "subr,%d %s", rv, REL(pc)); -#endif + util::stream_format(stream, z80 ? "sub r%d,(%s)" : "subr,%d %s", rv, REL(pc, params)); pc+=1; break; case 0xac: case 0xad: case 0xae: case 0xaf: -#if HJB - util::stream_format(stream, "sub %s", ABS(1,rv,pc)); -#else - util::stream_format(stream, "suba,%s", ABS(1,rv,pc)); -#endif + util::stream_format(stream, z80 ? "sub %s" : "suba,%s", ABS(1,rv,pc, params)); pc+=2; break; case 0xb0: case 0xb1: case 0xb2: case 0xb3: -#if HJB - util::stream_format(stream, "out (ctrl),r%d", rv); -#else - util::stream_format(stream, "wrtc,%d", rv); -#endif + util::stream_format(stream, z80 ? "out (ctrl),r%d" : "wrtc,%d", rv); break; case 0xb4: -#if HJB - util::stream_format(stream, "bit psu,%s", IMM_PSU(pc)); -#else - util::stream_format(stream, "tpsu %s", IMM_PSU(pc)); -#endif + util::stream_format(stream, z80 ? "bit psu,%s" : "tpsu %s", IMM_PSU(pc, params)); pc+=1; break; case 0xb5: -#if HJB - util::stream_format(stream, "bit psl,%s", IMM_PSL(pc)); -#else - util::stream_format(stream, "tpsl %s", IMM_PSL(pc)); -#endif + util::stream_format(stream, z80 ? "bit psl,%s" : "tpsl %s", IMM_PSL(pc, params)); pc+=1; break; case 0xb6: case 0xb7: -#if HJB - util::stream_format(stream, "**** $%02X",op); -#else - util::stream_format(stream, "**** $%02X",op); -#endif + util::stream_format(stream, z80 ? "**** $%02X" : "**** $%02X",op); break; case 0xb8: case 0xb9: case 0xba: -#if HJB - util::stream_format(stream, "calr n%c,%s", cc[rv], REL(pc)); -#else - util::stream_format(stream, "bsfr,%c %s", cc[rv], REL(pc)); -#endif + util::stream_format(stream, z80 ? "calr n%c,%s" : "bsfr,%c %s", cc[rv], REL(pc, params)); pc+=1; - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case 0xbb: -#if HJB - util::stream_format(stream, "cal0 %s", REL0(pc)); -#else - util::stream_format(stream, "zbsr %s", REL0(pc)); -#endif + util::stream_format(stream, z80 ? "cal0 %s" : "zbsr %s", REL0(pc, params)); pc+=1; - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case 0xbc: case 0xbd: case 0xbe: -#if HJB - util::stream_format(stream, "call n%c,%s", cc[rv], ADR(pc)); -#else - util::stream_format(stream, "bsfa,%c %s", cc[rv], ADR(pc)); -#endif + util::stream_format(stream, z80 ? "call n%c,%s" : "bsfa,%c %s", cc[rv], ADR(pc, params)); pc+=2; - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case 0xbf: -#if HJB - util::stream_format(stream, "call %s+r3", ADR(pc)); -#else - util::stream_format(stream, "bsxa %s", ADR(pc)); -#endif + util::stream_format(stream, z80 ? "call %s+r3" : "bsxa %s", ADR(pc, params)); pc+=2; - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case 0xc0: util::stream_format(stream, "nop"); break; case 0xc1: case 0xc2: case 0xc3: -#if HJB - util::stream_format(stream, "ld r%d,r0", rv); -#else - util::stream_format(stream, "strz,%d", rv); -#endif + util::stream_format(stream, z80 ? "ld r%d,r0" : "strz,%d", rv); break; case 0xc4: case 0xc5: case 0xc6: case 0xc7: -#if HJB - util::stream_format(stream, "**** $%02X",op); -#else - util::stream_format(stream, "**** $%02X",op); -#endif + util::stream_format(stream, z80 ? "**** $%02X" : "**** $%02X",op); break; case 0xc8: case 0xc9: case 0xca: case 0xcb: -#if HJB - util::stream_format(stream, "ld (%s),r%d", REL(pc), rv); -#else - util::stream_format(stream, "strr,%d %s", rv, REL(pc)); -#endif + util::stream_format(stream, z80 ? "ld (%s),r%d" : "strr,%d %s", rv, REL(pc, params)); pc+=1; break; case 0xcc: case 0xcd: case 0xce: case 0xcf: -#if HJB - util::stream_format(stream, "ld %s", ABS(0,rv,pc)); -#else - util::stream_format(stream, "stra,%s", ABS(1,rv,pc)); -#endif + util::stream_format(stream, z80 ? "ld %s" : "stra,%s", ABS(1,rv,pc, params)); pc+=2; break; case 0xd0: case 0xd1: case 0xd2: case 0xd3: -#if HJB - util::stream_format(stream, "rol r%d", rv); -#else - util::stream_format(stream, "rrl,%d", rv); -#endif + util::stream_format(stream, z80 ? "rol r%d" : "rrl,%d", rv); break; case 0xd4: case 0xd5: case 0xd6: case 0xd7: -#if HJB - util::stream_format(stream, "out (%s),r%d", IMM(pc), rv); -#else - util::stream_format(stream, "wrte,%d %s", rv, IMM(pc)); -#endif + util::stream_format(stream, z80 ? "out (%s),r%d" : "wrte,%d %s", rv, IMM(pc, params)); pc+=1; break; case 0xd8: case 0xd9: case 0xda: case 0xdb: -#if HJB - util::stream_format(stream, "ijnz r%d,%s", rv, REL(pc)); -#else - util::stream_format(stream, "birr,%d %s", rv, REL(pc)); -#endif + util::stream_format(stream, z80 ? "ijnz r%d,%s" : "birr,%d %s", rv, REL(pc, params)); pc+=1; - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case 0xdc: case 0xdd: case 0xde: case 0xdf: -#if HJB - util::stream_format(stream, "ijnz r%d,%s", rv, ADR(pc)); -#else - util::stream_format(stream, "bira,%d %s", rv, ADR(pc)); -#endif + util::stream_format(stream, z80 ? "ijnz r%d,%s" : "bira,%d %s", rv, ADR(pc, params)); pc+=2; - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case 0xe0: case 0xe1: case 0xe2: case 0xe3: -#if HJB - util::stream_format(stream, "cp r0,%d", rv); -#else - util::stream_format(stream, "comz,%d", rv); -#endif + util::stream_format(stream, z80 ? "cp r0,%d" : "comz,%d", rv); break; case 0xe4: case 0xe5: case 0xe6: case 0xe7: -#if HJB - util::stream_format(stream, "cp r%d,%s", rv, IMM(pc)); -#else - util::stream_format(stream, "comi,%d %s", rv, IMM(pc)); -#endif + util::stream_format(stream, z80 ? "cp r%d,%s" : "comi,%d %s", rv, IMM(pc, params)); pc+=1; break; case 0xe8: case 0xe9: case 0xea: case 0xeb: -#if HJB - util::stream_format(stream, "cp r%d,(%s)", rv, REL(pc)); -#else - util::stream_format(stream, "comr,%d %s", rv, REL(pc)); -#endif + util::stream_format(stream, z80 ? "cp r%d,(%s)" : "comr,%d %s", rv, REL(pc, params)); pc+=1; break; case 0xec: case 0xed: case 0xee: case 0xef: -#if HJB - util::stream_format(stream, "cp %s", ABS(1,rv,pc)); -#else - util::stream_format(stream, "coma,%s", ABS(1,rv,pc)); -#endif + util::stream_format(stream, z80 ? "cp %s" : "coma,%s", ABS(1,rv,pc, params)); pc+=2; break; case 0xf0: case 0xf1: case 0xf2: case 0xf3: -#if HJB - util::stream_format(stream, "out (data),r%d", rv); -#else - util::stream_format(stream, "wrtd,%d", rv); -#endif + util::stream_format(stream, z80 ? "out (data),r%d" : "wrtd,%d", rv); break; case 0xf4: case 0xf5: case 0xf6: case 0xf7: -#if HJB - util::stream_format(stream, "test r%d,%s", rv, IMM(pc)); -#else - util::stream_format(stream, "tmi,%d %s", rv, IMM(pc)); -#endif + util::stream_format(stream, z80 ? "test r%d,%s" : "tmi,%d %s", rv, IMM(pc, params)); pc+=1; break; case 0xf8: case 0xf9: case 0xfa: case 0xfb: -#if HJB - util::stream_format(stream, "djnz r%d,%s", rv, REL(pc)); -#else - util::stream_format(stream, "bdrr,%d %s", rv, REL(pc)); -#endif + util::stream_format(stream, z80 ? "djnz r%d,%s" : "bdrr,%d %s", rv, REL(pc, params)); pc+=1; - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case 0xfc: case 0xfd: case 0xfe: case 0xff: -#if HJB - util::stream_format(stream, "djnz r%d,%s", rv, ADR(pc)); -#else - util::stream_format(stream, "bdra,%d %s", rv, ADR(pc)); -#endif + util::stream_format(stream, z80 ? "djnz r%d,%s" : "bdra,%d %s", rv, ADR(pc, params)); pc+=2; - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; } - return (pc - PC) | flags | DASMFLAG_SUPPORTED; + return (pc - PC) | flags | SUPPORTED; +} + +u32 s2650_disassembler::opcode_alignment() const +{ + return 1; } diff --git a/src/devices/cpu/s2650/2650dasm.h b/src/devices/cpu/s2650/2650dasm.h new file mode 100644 index 00000000000..bf9523255cc --- /dev/null +++ b/src/devices/cpu/s2650/2650dasm.h @@ -0,0 +1,48 @@ +// license:BSD-3-Clause +// copyright-holders:Juergen Buchmueller +/*************************************************************************** + * + * Portable Signetics 2650 disassembler + * + * Written by J. Buchmueller (pullmoll@t-online.de) + * for the MAME project + * + **************************************************************************/ + +#ifndef MAME_CPU_S2650_2650DASM_H +#define MAME_CPU_S2650_2650DASM_H + +#pragma once + +class s2650_disassembler : public util::disasm_interface +{ +public: + struct config { + virtual ~config() = default; + virtual bool get_z80_mnemonics_mode() const = 0; + }; + + s2650_disassembler(config *conf); + virtual ~s2650_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const int rel[0x100]; + static const char cc[4]; + + void add(std::string &buf, std::string str); + std::string SYM(int addr); + std::string IMM(offs_t pc, const data_buffer ¶ms); + std::string IMM_PSL(offs_t pc, const data_buffer ¶ms); + std::string IMM_PSU(offs_t pc, const data_buffer ¶ms); + std::string REL(offs_t pc, const data_buffer ¶ms); + std::string REL0(offs_t pc, const data_buffer ¶ms); + std::string ABS(int load, int r, offs_t pc, const data_buffer ¶ms); + std::string ADR(offs_t pc, const data_buffer ¶ms); + + config *m_config; +}; + +#endif diff --git a/src/devices/cpu/s2650/s2650.cpp b/src/devices/cpu/s2650/s2650.cpp index 2afc7c5b261..57aca5aec71 100644 --- a/src/devices/cpu/s2650/s2650.cpp +++ b/src/devices/cpu/s2650/s2650.cpp @@ -42,13 +42,16 @@ s2650_device::s2650_device(const machine_config &mconfig, const char *tag, devic memset(m_reg, 0x00, sizeof(m_reg)); } - -offs_t s2650_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +bool s2650_device::get_z80_mnemonics_mode() const { - extern CPU_DISASSEMBLE( s2650 ); - return CPU_DISASSEMBLE_NAME(s2650)(this, stream, pc, oprom, opram, options); + // Needs to become configurable live + return false; } +util::disasm_interface *s2650_device::create_disassembler() +{ + return new s2650_disassembler(this); +} device_memory_interface::space_config_vector s2650_device::memory_space_config() const { diff --git a/src/devices/cpu/s2650/s2650.h b/src/devices/cpu/s2650/s2650.h index 4fd297b694a..9efb9fdd7e6 100644 --- a/src/devices/cpu/s2650/s2650.h +++ b/src/devices/cpu/s2650/s2650.h @@ -5,6 +5,7 @@ #pragma once +#include "2650dasm.h" #define S2650_SENSE_LINE INPUT_LINE_IRQ1 @@ -35,7 +36,7 @@ DECLARE_DEVICE_TYPE(S2650, s2650_device) #define MCFG_S2650_INTACK_HANDLER(_devcb) \ devcb = &s2650_device::set_intack_handler(*device, DEVCB_##_devcb); -class s2650_device : public cpu_device + class s2650_device : public cpu_device, public s2650_disassembler::config { public: // construction/destruction @@ -68,9 +69,8 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 3; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; + virtual bool get_z80_mnemonics_mode() const override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/saturn/saturn.cpp b/src/devices/cpu/saturn/saturn.cpp index 2368c16ef19..a1ebd111ec7 100644 --- a/src/devices/cpu/saturn/saturn.cpp +++ b/src/devices/cpu/saturn/saturn.cpp @@ -64,11 +64,16 @@ device_memory_interface::space_config_vector saturn_device::memory_space_config( }; } +bool saturn_device::get_nonstandard_mnemonics_mode() const +{ + // Needs to become configurable live + return false; +} + -offs_t saturn_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *saturn_device::create_disassembler() { - extern CPU_DISASSEMBLE( saturn ); - return CPU_DISASSEMBLE_NAME(saturn)(this, stream, pc, oprom, opram, options); + return new saturn_disassembler(this); } diff --git a/src/devices/cpu/saturn/saturn.h b/src/devices/cpu/saturn/saturn.h index d73745a31fb..d0f9628e49b 100644 --- a/src/devices/cpu/saturn/saturn.h +++ b/src/devices/cpu/saturn/saturn.h @@ -32,6 +32,7 @@ HP38G 09/??/95 1LT8 Yorke #pragma once +#include "saturnds.h" #define SATURN_INT_NONE 0 #define SATURN_INT_IRQ 1 @@ -72,7 +73,7 @@ enum saturn_device::set_rsi_func(*device, DEVCB_##_rsi); -class saturn_device : public cpu_device +class saturn_device : public cpu_device, public saturn_disassembler::config { public: // construction/destruction @@ -109,9 +110,8 @@ protected: virtual void state_export(const device_state_entry &entry) override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 20; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; + virtual bool get_nonstandard_mnemonics_mode() const override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/saturn/saturnds.cpp b/src/devices/cpu/saturn/saturnds.cpp index a71aec2cbf6..6d3b2767f7f 100644 --- a/src/devices/cpu/saturn/saturnds.cpp +++ b/src/devices/cpu/saturn/saturnds.cpp @@ -9,19 +9,7 @@ *****************************************************************************/ #include "emu.h" -#include "debugger.h" - -#include "saturn.h" - -#define SATURN_HP_MNEMONICS - -#if defined SATURN_HP_MNEMONICS -// class/hp mnemonics -static int set=0; -#else -// readable/normal mnemonics -static int set=1; -#endif +#include "saturnds.h" #define P "P" #define WP "WP" @@ -33,551 +21,382 @@ static int set=1; #define W "W" #define A "A" -static const char *const adr_b[]= +const char *const saturn_disassembler::adr_b[]= { P, WP, XS, X, S, M, B, W }; -static const char *const adr_af[]= +const char *const saturn_disassembler::adr_af[]= { P, WP, XS, X, S, M, B, W, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, A }; -static const char *const adr_a[]= +const char *const saturn_disassembler::adr_a[]= { P, WP, XS, X, S, M, B, W }; -static const char number_2_hex[]= +const char saturn_disassembler::number_2_hex[]= { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f' }; -#define SATURN_PEEKOP_DIS8(v) v = (int8_t)( oprom[pos] | ( oprom[pos+1] << 4 ) ); pos+= 2; +#define SATURN_PEEKOP_DIS8(v) v = (int8_t)( opcodes.r8(pos) | ( opcodes.r8(pos+1) << 4 ) ); pos+= 2; -#define SATURN_PEEKOP_DIS12(v) v = oprom[pos] | ( oprom[pos+1] << 4 ) | ( oprom[pos+2] << 8 ); \ +#define SATURN_PEEKOP_DIS12(v) v = opcodes.r8(pos) | ( opcodes.r8(pos+1) << 4 ) | ( opcodes.r8(pos+2) << 8 ); \ pos += 3; \ if ( v & 0x0800 ) v = -0x1000 + v; -#define SATURN_PEEKOP_DIS16(v) v = (int16_t)( oprom[pos] | ( oprom[pos+1] << 4 ) | ( oprom[pos+2] << 8 ) | ( oprom[pos+3] << 12 ) ); pos += 4; - -#define SATURN_PEEKOP_ADR(v) v = oprom[pos] | ( oprom[pos+1] << 4 ) | ( oprom[pos+2] << 8 ) | ( oprom[pos+3] << 12 ) | ( oprom[pos+4] << 16 ); pos += 5; - - -// don't split branch and return, source relies on this ordering -enum MNEMONICS -{ - Return, ReturnSetXM, ReturnSetCarry, ReturnClearCarry, ReturnFromInterrupt, - jump3,jump4,jump, - call3,call4,call, - branchCarrySet, returnCarrySet, - branchCarryClear, returnCarryClear, - - outCS, outC, inA, inC, - unconfig, config, Cid, shutdown, cp1, reset, buscc, - CcopyP, PcopyC, sreq, CswapP, - - inton, AloadImm, buscb, - clearAbit, setAbit, - branchAbitclear, returnAbitclear, - branchAbitset, returnAbitset, - clearCbit, setCbit, - branchCbitclear, returnCbitclear, - branchCbitset, returnCbitset, - PCloadA, buscd, PCloadC, intoff, rsi, - - jumpA, jumpC, PCcopyA, PCcopyC, AcopyPC, CcopyPC, - - clearHST, - branchHSTclear, returnHSTclear, - - clearBitST, setBitST, - branchSTclear, returnSTclear, - branchSTset, returnSTset, - - - branchPdiffers, returnPdiffers, - branchPequals, returnPequals, - - branchAequalsB, returnAequalsB, - branchBequalsC, returnBequalsC, - branchAequalsC, returnAequalsC, - branchCequalsD, returnCequalsD, - branchAdiffersB, returnAdiffersB, - branchBdiffersC, returnBdiffersC, - branchAdiffersC, returnAdiffersC, - branchCdiffersD, returnCdiffersD, - branchAzero, returnAzero, - branchBzero, returnBzero, - branchCzero, returnCzero, - branchDzero, returnDzero, - branchAnotzero, returnAnotzero, - branchBnotzero, returnBnotzero, - branchCnotzero, returnCnotzero, - branchDnotzero, returnDnotzero, - - branchAgreaterB, returnAgreaterB, - branchBgreaterC, returnBgreaterC, - branchCgreaterA, returnCgreaterA, - branchDgreaterC, returnDgreaterC, - branchAlowerB, returnAlowerB, - branchBlowerC, returnBlowerC, - branchClowerA, returnClowerA, - branchDlowerC, returnDlowerC, - branchAnotlowerB, returnAnotlowerB, - branchBnotlowerC, returnBnotlowerC, - branchCnotlowerA, returnCnotlowerA, - branchDnotlowerC, returnDnotlowerC, - branchAnotgreaterB, returnAnotgreaterB, - branchBnotgreaterC, returnBnotgreaterC, - branchCnotgreaterA, returnCnotgreaterA, - branchDnotgreaterC, returnDnotgreaterC, - - SetHexMode, SetDecMode, - PushC, PopC, - - D0loadImm2, D0loadImm4, D0loadImm5, - D1loadImm2, D1loadImm4, D1loadImm5, - PloadImm, CloadImm, - - clearST, - CcopyST, STcopyC, - swapCST, - - incP, decP, - - R0copyA, R1copyA, R2copyA, R3copyA, R4copyA, - R0copyC, R1copyC, R2copyC, R3copyC, R4copyC, - - AcopyR0, AcopyR1, AcopyR2, AcopyR3, AcopyR4, - CcopyR0, CcopyR1, CcopyR2, CcopyR3, CcopyR4, - - D0copyA, D1copyA, D0copyC, D1copyC, - D0copyAShort, D1copyAShort, D0copyCShort, D1copyCShort, // other class mnemonic - - SwapAR0, SwapAR1, SwapAR2, SwapAR3, SwapAR4, - SwapCR0, SwapCR1, SwapCR2, SwapCR3, SwapCR4, - - SwapAD0, SwapAD1, SwapCD0, SwapCD1, - SwapAD0Short, SwapAD1Short, SwapCD0Short, SwapCD1Short, // other class mnemonic - - D0storeA, D1storeA, D0storeC, D1storeC, - AloadD0, AloadD1, CloadD0, CloadD1, - - D0addImm, D1addImm, D0subImm, D1subImm, - AaddImm, BaddImm, CaddImm, DaddImm, - AsubImm, BsubImm, CsubImm, DsubImm, - - AandB, BandC, CandA, DandC, BandA, CandB, AandC, CandD, - AorB, BorC, CorA, DorC, BorA, CorB, AorC, CorD, - - Ashiftrightbit, Bshiftrightbit, Cshiftrightbit, Dshiftrightbit, - - AshiftleftCarry, BshiftleftCarry, CshiftleftCarry, DshiftleftCarry, - AshiftrightCarry, BshiftrightCarry, CshiftrightCarry, DshiftrightCarry, - - AaddB, BaddC, CaddA, DaddC, AaddA, BaddB, CaddC, DaddD, - BaddA, CaddB, AaddC, CaddD, decA, decB, decC, decD, - - AsubB, BsubC, CsubA, DsubC, incA, incB, incC, incD, - BsubA, CsubB, AsubC, CsubD, AsubnB, BsubnC, CsubnA, DsubnC, - - clearA, clearB, clearC, clearD, - AcopyB, BcopyC, CcopyA, DcopyC, BcopyA, CcopyB, AcopyC, CcopyD, - AswapB, BswapC, CswapA, DswapC, - - Ashiftleft, Bshiftleft, Cshiftleft, Dshiftleft, - Ashiftright, Bshiftright, Cshiftright, Dshiftright, - negateA, negateB, negateC, negateD, - notA, notB, notC, notD - -}; - -static const struct { - const char *name[2]; -} mnemonics[]={ - { { "rtn", "RET" } }, - { { "rtnsXM", "RETSETXM" } }, - { { "rtnsC", "RETSETC" } }, - { { "rtncC", "RETCLRC" } }, - { { "rti", "RETI" } }, - { { "goto %05x", "JUMP.3 %05x" } }, - { { "goto %05x", "JUMP.4 %05x" } }, - { { "goto %05x", "JUMP %05x" } }, - { { "gosub %05x", "CALL.3 %05x" } }, - { { "gosub %05x", "CALL.4 %05x" } }, - { { "gosub %05x", "CALL %05x" } }, - { { "goC %05x", "BRCS %05x" } }, - { { "rtnC", "RETCS" } }, - { { "gonC %05x", "BRCC %05x" } }, - { { "rtnnC", "RETCC" } }, - - { { "OUT=CS", "OUT.S C" } }, - { { "OUT=C", "OUT.X C" } }, - { { "A=IN", "IN.4 A" } }, - { { "C=IN", "IN.4 C" } }, - { { "uncnfg", "UNCNFG" } }, - { { "config", "CONFIG" } }, - { { "C=id", "MOVE.A ID,C" } }, - { { "!shutdn", "!SHUTDN" } }, - { { "C+P+1", "ADD.A P+1,C" } }, - { { "reset", "RESET" } }, - { { "!buscc", "!BUSCC" } }, - { { "C=P %x", "MOVE.1 P,C,%x" } }, - { { "P=C %x", "MOVE.1 C,%x,P" } }, - { { "!sreq?", "!SREQ" } }, - { { "CPex %x", "SWAP.1 P,C,%x" } }, - - { { "!inton", "!INTON" } }, - { { "LA %-2x %s", "MOVE.P%-2x %s,A" } }, - { { "!buscb", "!BUSCB" } }, - { { "Abit=0 %x", "CLRB %x,A" } }, - { { "Abit=1 %x", "SETB %x,A" } }, - { { "?Abit=0 %x,%05x", "BRBC %x,A,%05x" } }, - { { "?Abit=0 %x,rtn", "RETBC %x,A" } }, - { { "?Abit=1 %x,%05x", "BRBS %x,A,%05x" } }, - { { "?Abit=1 %x,rtn", "RETBS %x,A" } }, - { { "Cbit=0 %x", "CLRB %x,C" } }, - { { "Cbit=1 %x", "SETB %x,C" } }, - { { "?Cbit=0 %x,%05x", "BRBC %x,C,%05x" } }, - { { "?Cbit=0 %x,rtn", "RETBC %x,C" } }, - { { "?Cbit=1 %x,%05x", "BRBS %x,C,%05x" } }, - { { "?Cbit=1 %x,rtn", "RETBS %x,C" } }, - { { "PC=(A)", "JUMP.A @A" } }, - { { "!buscd", "!BUSCD" } }, - { { "PC=(C)", "JUMP.A @C" } }, - { { "!intoff", "!INTOFF" } }, - { { "!rsi", "!RSI" } }, - - { { "PC=A", "JUMP.A A" } }, - { { "PC=C", "JUMP.A C" } }, - { { "A=PC", "MOVE.A PC,A" } }, - { { "C=PC", "MOVE.A PC,C" } }, - { { "APCex", "SWAP.A A,PC" } }, - { { "CPCex", "SWAP.A C,PC" } }, - - { { "HST=0 %x", "CLRHST %x" } }, - { { "?HST=0 %x,%05x", "BRBCHST %x,%05x" } }, - { { "?HST=0 %x,rtn", "RETBCHST %x" } }, - { { "ST=0 %x", "CLRB %x,ST" } }, - { { "ST=1 %x", "SETB %x,ST" } }, - { { "?ST=0 %x,%05x", "BRBC ST,%x,%05x" } }, - { { "?ST=0 %x,rtn", "RETBC ST,%x" } }, - { { "?ST=1 %x,%05x", "BRBS ST,%x,%05x" } }, - { { "?ST=1 %x,rtn", "RETBS ST,%x" } }, - { { "?P# %x,%05x", "BRNE P,%x,%05x" } }, - { { "?P# %x,rtn", "RETNE P,%x" } }, - { { "?P= %x,%05x", "BREQ P,%x,%05x" } }, - { { "?P= %x,rtn", "RETEQ P,%x" } }, - - { { "?A=B %s,%05x", "BREQ.%-2s A,B,%05x" } }, - { { "?A=B %s,rtn", "RETEQ.%-2s A,B" } }, - { { "?B=C %s,%05x", "BREQ.%-2s B,C,%05x" } }, - { { "?B=C %s,rtn", "RETEQ.%-2s B,C" } }, - { { "?A=C %s,%05x", "BREQ.%-2s A,C,%05x" } }, - { { "?A=C %s,rtn", "RETEQ.%-2s A,C" } }, - { { "?C=D %s,%05x", "BREQ.%-2s C,D,%05x" } }, - { { "?C=D %s,rtn", "RETEQ.%-2s C,D" } }, - { { "?A#B %s,%05x", "BRNE.%-2s A,B,%05x" } }, - { { "?A#B %s,rtn", "RETNE.%-2s A,B" } }, - { { "?B#C %s,%05x", "BRNE.%-2s B,C,%05x" } }, - { { "?B#C %s,rtn", "RETNE.%-2s B,C" } }, - { { "?A#C %s,%05x", "BRNE.%-2s A,C,%05x" } }, - { { "?A#C %s,rtn", "RETNE.%-2s A,C" } }, - { { "?C#D %s,%05x", "BRNE.%-2s C,D,%05x" } }, - { { "?C#D %s,rtn", "RETNE.%-2s C,D" } }, - { { "?A=0 %s,%05x", "BRZ.%-2s A,%05x" } }, - { { "?A=0 %s,rtn", "RETZ.%-2s A" } }, - { { "?B=0 %s,%05x", "BRZ.%-2s B,%05x" } }, - { { "?B=0 %s,rtn", "RETZ.%-2s B" } }, - { { "?C=0 %s,%05x", "BRZ.%-2s C,%05x" } }, - { { "?C=0 %s,rtn", "RETZ.%-2s C" } }, - { { "?D=0 %s,%05x", "BRZ.%-2s D,%05x" } }, - { { "?D=0 %s,rtn", "RETZ.%-2s D" } }, - { { "?A#0 %s,%05x", "BRNZ.%-2s A,%05x" } }, - { { "?A#0 %s,rtn", "RETNZ.%-2s A" } }, - { { "?B#0 %s,%05x", "BRNZ.%-2s B,%05x" } }, - { { "?B#0 %s,rtn", "RETNZ.%-2s B" } }, - { { "?C#0 %s,%05x", "BRNZ.%-2s C,%05x" } }, - { { "?C#0 %s,rtn", "RETNZ.%-2s C" } }, - { { "?D#0 %s,%05x", "BRNZ.%-2s D,%05x" } }, - { { "?D#0 %s,rtn", "RETNZ.%-2s D" } }, - - { { "?A>B %s,%05x", "BRGT.%-2s A,B,%05x" } }, - { { "?A>B %s,rtn", "RETGT.%-2s A,B" } }, - { { "?B>C %s,%05x", "BRGT.%-2s B,C,%05x" } }, - { { "?B>C %s,rtn", "RETGT.%-2s B,C" } }, - { { "?C>A %s,%05x", "BRGT.%-2s C,A,%05x" } }, - { { "?C>A %s,rtn", "RETGT.%-2s C,A" } }, - { { "?D>C %s,%05x", "BRGT.%-2s D,C,%05x" } }, - { { "?D>C %s,rtn", "RETGT.%-2s D,C" } }, - { { "?A=B %s,%05x", "BRGE.%-2s A,B,%05x" } }, - { { "?A>=B %s,rtn", "RETGE.%-2s A,B" } }, - { { "?B>=C %s,%05x", "BRGE.%-2s B,C,%05x" } }, - { { "?B>=C %s,rtn", "RETGE.%-2s B,C" } }, - { { "?C>=A %s,%05x", "BRGE.%-2s C,A,%05x" } }, - { { "?C>=A %s,rtn", "RETGE.%-2s C,A" } }, - { { "?D>=C %s,%05x", "BRGE.%-2s D,C,%05x" } }, - { { "?D>=C %s,rtn", "RETGE.%-2s D,C" } }, - { { "?A<=B %s,%05x", "BRLE.%-2s A,B,%05x" } }, - { { "?A<=B %s,rtn", "RETLE.%-2s A,B" } }, - { { "?B<=C %s,%05x", "BRLE.%-2s B,C,%05x" } }, - { { "?B<=C %s,rtn", "RETLE.%-2s B,C" } }, - { { "?C<=A %s,%05x", "BRLE.%-2s C,A,%05x" } }, - { { "?C<=A %s,rtn", "RETLE.%-2s C,A" } }, - { { "?D<=C %s,%05x", "BRLE.%-2s D,C,%05x" } }, - { { "?D<=C %s,rtn", "RETLE.%-2s D,C" } }, - - { { "sethex", "SETHEX" } }, - { { "setdec", "SETDEC" } }, - { { "RSTK=C", "PUSH.A C" } }, - { { "C=RSTK", "POP.A C" } }, +#define SATURN_PEEKOP_DIS16(v) v = (int16_t)( opcodes.r8(pos) | ( opcodes.r8(pos+1) << 4 ) | ( opcodes.r8(pos+2) << 8 ) | ( opcodes.r8(pos+3) << 12 ) ); pos += 4; + +#define SATURN_PEEKOP_ADR(v) v = opcodes.r8(pos) | ( opcodes.r8(pos+1) << 4 ) | ( opcodes.r8(pos+2) << 8 ) | ( opcodes.r8(pos+3) << 12 ) | ( opcodes.r8(pos+4) << 16 ); pos += 5; + + +const char *const saturn_disassembler::mnemonics[][2] = { + { "rtn", "RET" }, + { "rtnsXM", "RETSETXM" }, + { "rtnsC", "RETSETC" }, + { "rtncC", "RETCLRC" }, + { "rti", "RETI" }, + { "goto %05x", "JUMP.3 %05x" }, + { "goto %05x", "JUMP.4 %05x" }, + { "goto %05x", "JUMP %05x" }, + { "gosub %05x", "CALL.3 %05x" }, + { "gosub %05x", "CALL.4 %05x" }, + { "gosub %05x", "CALL %05x" }, + { "goC %05x", "BRCS %05x" }, + { "rtnC", "RETCS" }, + { "gonC %05x", "BRCC %05x" }, + { "rtnnC", "RETCC" }, + + { "OUT=CS", "OUT.S C" }, + { "OUT=C", "OUT.X C" }, + { "A=IN", "IN.4 A" }, + { "C=IN", "IN.4 C" }, + { "uncnfg", "UNCNFG" }, + { "config", "CONFIG" }, + { "C=id", "MOVE.A ID,C" }, + { "!shutdn", "!SHUTDN" }, + { "C+P+1", "ADD.A P+1,C" }, + { "reset", "RESET" }, + { "!buscc", "!BUSCC" }, + { "C=P %x", "MOVE.1 P,C,%x" }, + { "P=C %x", "MOVE.1 C,%x,P" }, + { "!sreq?", "!SREQ" }, + { "CPex %x", "SWAP.1 P,C,%x" }, + + { "!inton", "!INTON" }, + { "LA %-2x %s", "MOVE.P%-2x %s,A" }, + { "!buscb", "!BUSCB" }, + { "Abit=0 %x", "CLRB %x,A" }, + { "Abit=1 %x", "SETB %x,A" }, + { "?Abit=0 %x,%05x", "BRBC %x,A,%05x" }, + { "?Abit=0 %x,rtn", "RETBC %x,A" }, + { "?Abit=1 %x,%05x", "BRBS %x,A,%05x" }, + { "?Abit=1 %x,rtn", "RETBS %x,A" }, + { "Cbit=0 %x", "CLRB %x,C" }, + { "Cbit=1 %x", "SETB %x,C" }, + { "?Cbit=0 %x,%05x", "BRBC %x,C,%05x" }, + { "?Cbit=0 %x,rtn", "RETBC %x,C" }, + { "?Cbit=1 %x,%05x", "BRBS %x,C,%05x" }, + { "?Cbit=1 %x,rtn", "RETBS %x,C" }, + { "PC=(A)", "JUMP.A @A" }, + { "!buscd", "!BUSCD" }, + { "PC=(C)", "JUMP.A @C" }, + { "!intoff", "!INTOFF" }, + { "!rsi", "!RSI" }, + + { "PC=A", "JUMP.A A" }, + { "PC=C", "JUMP.A C" }, + { "A=PC", "MOVE.A PC,A" }, + { "C=PC", "MOVE.A PC,C" }, + { "APCex", "SWAP.A A,PC" }, + { "CPCex", "SWAP.A C,PC" }, + + { "HST=0 %x", "CLRHST %x" }, + { "?HST=0 %x,%05x", "BRBCHST %x,%05x" }, + { "?HST=0 %x,rtn", "RETBCHST %x" }, + { "ST=0 %x", "CLRB %x,ST" }, + { "ST=1 %x", "SETB %x,ST" }, + { "?ST=0 %x,%05x", "BRBC ST,%x,%05x" }, + { "?ST=0 %x,rtn", "RETBC ST,%x" }, + { "?ST=1 %x,%05x", "BRBS ST,%x,%05x" }, + { "?ST=1 %x,rtn", "RETBS ST,%x" }, + { "?P# %x,%05x", "BRNE P,%x,%05x" }, + { "?P# %x,rtn", "RETNE P,%x" }, + { "?P= %x,%05x", "BREQ P,%x,%05x" }, + { "?P= %x,rtn", "RETEQ P,%x" }, + + { "?A=B %s,%05x", "BREQ.%-2s A,B,%05x" }, + { "?A=B %s,rtn", "RETEQ.%-2s A,B" }, + { "?B=C %s,%05x", "BREQ.%-2s B,C,%05x" }, + { "?B=C %s,rtn", "RETEQ.%-2s B,C" }, + { "?A=C %s,%05x", "BREQ.%-2s A,C,%05x" }, + { "?A=C %s,rtn", "RETEQ.%-2s A,C" }, + { "?C=D %s,%05x", "BREQ.%-2s C,D,%05x" }, + { "?C=D %s,rtn", "RETEQ.%-2s C,D" }, + { "?A#B %s,%05x", "BRNE.%-2s A,B,%05x" }, + { "?A#B %s,rtn", "RETNE.%-2s A,B" }, + { "?B#C %s,%05x", "BRNE.%-2s B,C,%05x" }, + { "?B#C %s,rtn", "RETNE.%-2s B,C" }, + { "?A#C %s,%05x", "BRNE.%-2s A,C,%05x" }, + { "?A#C %s,rtn", "RETNE.%-2s A,C" }, + { "?C#D %s,%05x", "BRNE.%-2s C,D,%05x" }, + { "?C#D %s,rtn", "RETNE.%-2s C,D" }, + { "?A=0 %s,%05x", "BRZ.%-2s A,%05x" }, + { "?A=0 %s,rtn", "RETZ.%-2s A" }, + { "?B=0 %s,%05x", "BRZ.%-2s B,%05x" }, + { "?B=0 %s,rtn", "RETZ.%-2s B" }, + { "?C=0 %s,%05x", "BRZ.%-2s C,%05x" }, + { "?C=0 %s,rtn", "RETZ.%-2s C" }, + { "?D=0 %s,%05x", "BRZ.%-2s D,%05x" }, + { "?D=0 %s,rtn", "RETZ.%-2s D" }, + { "?A#0 %s,%05x", "BRNZ.%-2s A,%05x" }, + { "?A#0 %s,rtn", "RETNZ.%-2s A" }, + { "?B#0 %s,%05x", "BRNZ.%-2s B,%05x" }, + { "?B#0 %s,rtn", "RETNZ.%-2s B" }, + { "?C#0 %s,%05x", "BRNZ.%-2s C,%05x" }, + { "?C#0 %s,rtn", "RETNZ.%-2s C" }, + { "?D#0 %s,%05x", "BRNZ.%-2s D,%05x" }, + { "?D#0 %s,rtn", "RETNZ.%-2s D" }, + + { "?A>B %s,%05x", "BRGT.%-2s A,B,%05x" }, + { "?A>B %s,rtn", "RETGT.%-2s A,B" }, + { "?B>C %s,%05x", "BRGT.%-2s B,C,%05x" }, + { "?B>C %s,rtn", "RETGT.%-2s B,C" }, + { "?C>A %s,%05x", "BRGT.%-2s C,A,%05x" }, + { "?C>A %s,rtn", "RETGT.%-2s C,A" }, + { "?D>C %s,%05x", "BRGT.%-2s D,C,%05x" }, + { "?D>C %s,rtn", "RETGT.%-2s D,C" }, + { "?A=B %s,%05x", "BRGE.%-2s A,B,%05x" }, + { "?A>=B %s,rtn", "RETGE.%-2s A,B" }, + { "?B>=C %s,%05x", "BRGE.%-2s B,C,%05x" }, + { "?B>=C %s,rtn", "RETGE.%-2s B,C" }, + { "?C>=A %s,%05x", "BRGE.%-2s C,A,%05x" }, + { "?C>=A %s,rtn", "RETGE.%-2s C,A" }, + { "?D>=C %s,%05x", "BRGE.%-2s D,C,%05x" }, + { "?D>=C %s,rtn", "RETGE.%-2s D,C" }, + { "?A<=B %s,%05x", "BRLE.%-2s A,B,%05x" }, + { "?A<=B %s,rtn", "RETLE.%-2s A,B" }, + { "?B<=C %s,%05x", "BRLE.%-2s B,C,%05x" }, + { "?B<=C %s,rtn", "RETLE.%-2s B,C" }, + { "?C<=A %s,%05x", "BRLE.%-2s C,A,%05x" }, + { "?C<=A %s,rtn", "RETLE.%-2s C,A" }, + { "?D<=C %s,%05x", "BRLE.%-2s D,C,%05x" }, + { "?D<=C %s,rtn", "RETLE.%-2s D,C" }, + + { "sethex", "SETHEX" }, + { "setdec", "SETDEC" }, + { "RSTK=C", "PUSH.A C" }, + { "C=RSTK", "POP.A C" }, // load immediate - { { "D0= %02x", "MOVE.2 %02x,D0" } }, - { { "D0= %04x", "MOVE.4 %04x,D0" } }, - { { "D0= %05x", "MOVE.5 %05x,D0" } }, + { "D0= %02x", "MOVE.2 %02x,D0" }, + { "D0= %04x", "MOVE.4 %04x,D0" }, + { "D0= %05x", "MOVE.5 %05x,D0" }, - { { "D1= %02x", "MOVE.2 %02x,D1" } }, - { { "D1= %04x", "MOVE.4 %04x,D1" } }, - { { "D1= %05x", "MOVE.5 %05x,D1" } }, + { "D1= %02x", "MOVE.2 %02x,D1" }, + { "D1= %04x", "MOVE.4 %04x,D1" }, + { "D1= %05x", "MOVE.5 %05x,D1" }, - { { "P= %x", "MOVE %x,P" } }, - { { "lC %-2x %s", "MOVE.P%-2x %s,C" } }, + { "P= %x", "MOVE %x,P" }, + { "lC %-2x %s", "MOVE.P%-2x %s,C" }, - { { "clrST", "CLR.X ST" } }, - { { "C=ST", "MOVE.X ST,C" } }, - { { "ST=C", "MOVE.X C,ST" } }, - { { "CSTex", "SWAP.X C,ST" } }, + { "clrST", "CLR.X ST" }, + { "C=ST", "MOVE.X ST,C" }, + { "ST=C", "MOVE.X C,ST" }, + { "CSTex", "SWAP.X C,ST" }, - { { "P=P+1", "INC P" } }, - { { "P=P-1", "DEC P" } }, + { "P=P+1", "INC P" }, + { "P=P-1", "DEC P" }, // copy - { { "R0=A %s", "MOVE.%-2s A,R0" } }, - { { "R1=A %s", "MOVE.%-2s A,R1" } }, - { { "R2=A %s", "MOVE.%-2s A,R2" } }, - { { "R3=A %s", "MOVE.%-2s A,R3" } }, - { { "R4=A %s", "MOVE.%-2s A,R4" } }, - - { { "R0=C %s", "MOVE.%-2s C,R0" } }, - { { "R1=C %s", "MOVE.%-2s C,R1" } }, - { { "R2=C %s", "MOVE.%-2s C,R2" } }, - { { "R3=C %s", "MOVE.%-2s C,R3" } }, - { { "R4=C %s", "MOVE.%-2s C,R4" } }, - - { { "A=R0 %s", "MOVE.%-2s R0,A" } }, - { { "A=R1 %s", "MOVE.%-2s R1,A" } }, - { { "A=R2 %s", "MOVE.%-2s R2,A" } }, - { { "A=R3 %s", "MOVE.%-2s R3,A" } }, - { { "A=R4 %s", "MOVE.%-2s R4,A" } }, - - { { "C=R0 %s", "MOVE.%-2s R0,C" } }, - { { "C=R1 %s", "MOVE.%-2s R1,C" } }, - { { "C=R2 %s", "MOVE.%-2s R2,C" } }, - { { "C=R3 %s", "MOVE.%-2s R3,C" } }, - { { "C=R4 %s", "MOVE.%-2s R4,C" } }, - - { { "D0=A", "MOVE.A A,D0" } }, - { { "D1=A", "MOVE.A A,D1" } }, - { { "D0=C", "MOVE.A C,D0" } }, - { { "D1=C", "MOVE.A C,D1" } }, - { { "D0=As", "MOVE.S A,D0" } }, - { { "D1=As", "MOVE.S A,D1" } }, - { { "D0=Cs", "MOVE.S C,D0" } }, - { { "D1=Cs", "MOVE.S C,D1" } }, + { "R0=A %s", "MOVE.%-2s A,R0" }, + { "R1=A %s", "MOVE.%-2s A,R1" }, + { "R2=A %s", "MOVE.%-2s A,R2" }, + { "R3=A %s", "MOVE.%-2s A,R3" }, + { "R4=A %s", "MOVE.%-2s A,R4" }, + + { "R0=C %s", "MOVE.%-2s C,R0" }, + { "R1=C %s", "MOVE.%-2s C,R1" }, + { "R2=C %s", "MOVE.%-2s C,R2" }, + { "R3=C %s", "MOVE.%-2s C,R3" }, + { "R4=C %s", "MOVE.%-2s C,R4" }, + + { "A=R0 %s", "MOVE.%-2s R0,A" }, + { "A=R1 %s", "MOVE.%-2s R1,A" }, + { "A=R2 %s", "MOVE.%-2s R2,A" }, + { "A=R3 %s", "MOVE.%-2s R3,A" }, + { "A=R4 %s", "MOVE.%-2s R4,A" }, + + { "C=R0 %s", "MOVE.%-2s R0,C" }, + { "C=R1 %s", "MOVE.%-2s R1,C" }, + { "C=R2 %s", "MOVE.%-2s R2,C" }, + { "C=R3 %s", "MOVE.%-2s R3,C" }, + { "C=R4 %s", "MOVE.%-2s R4,C" }, + + { "D0=A", "MOVE.A A,D0" }, + { "D1=A", "MOVE.A A,D1" }, + { "D0=C", "MOVE.A C,D0" }, + { "D1=C", "MOVE.A C,D1" }, + { "D0=As", "MOVE.S A,D0" }, + { "D1=As", "MOVE.S A,D1" }, + { "D0=Cs", "MOVE.S C,D0" }, + { "D1=Cs", "MOVE.S C,D1" }, // swap operations - { { "AR0ex %s", "SWAP.%-2s A,R0" } }, - { { "AR1ex %s", "SWAP.%-2s A,R1" } }, - { { "AR2ex %s", "SWAP.%-2s A,R2" } }, - { { "AR3ex %s", "SWAP.%-2s A,R3" } }, - { { "AR4ex %s", "SWAP.%-2s A,R4" } }, - - { { "CR0ex %s", "SWAP.%-2s C,R0" } }, - { { "CR1ex %s", "SWAP.%-2s C,R1" } }, - { { "CR2ex %s", "SWAP.%-2s C,R2" } }, - { { "CR3ex %s", "SWAP.%-2s C,R3" } }, - { { "CR4ex %s", "SWAP.%-2s C,R4" } }, - - { { "AD0ex", "SWAP.A A,D0" } }, - { { "AD1ex", "SWAP.A A,D1" } }, - { { "CD0ex", "SWAP.A C,D0" } }, - { { "CD1ex", "SWAP.A C,D1" } }, - { { "AD0xs", "SWAP.S A,D0" } }, - { { "AD1xs", "SWAP.S A,D1" } }, - { { "CD0xs", "SWAP.S C,D0" } }, - { { "CD1xs", "SWAP.S C,D1" } }, + { "AR0ex %s", "SWAP.%-2s A,R0" }, + { "AR1ex %s", "SWAP.%-2s A,R1" }, + { "AR2ex %s", "SWAP.%-2s A,R2" }, + { "AR3ex %s", "SWAP.%-2s A,R3" }, + { "AR4ex %s", "SWAP.%-2s A,R4" }, + + { "CR0ex %s", "SWAP.%-2s C,R0" }, + { "CR1ex %s", "SWAP.%-2s C,R1" }, + { "CR2ex %s", "SWAP.%-2s C,R2" }, + { "CR3ex %s", "SWAP.%-2s C,R3" }, + { "CR4ex %s", "SWAP.%-2s C,R4" }, + + { "AD0ex", "SWAP.A A,D0" }, + { "AD1ex", "SWAP.A A,D1" }, + { "CD0ex", "SWAP.A C,D0" }, + { "CD1ex", "SWAP.A C,D1" }, + { "AD0xs", "SWAP.S A,D0" }, + { "AD1xs", "SWAP.S A,D1" }, + { "CD0xs", "SWAP.S C,D0" }, + { "CD1xs", "SWAP.S C,D1" }, // store - { { "Dat0=A %s", "MOVE.%-2s A,@D0" } }, - { { "Dat1=A %s", "MOVE.%-2s A,@D0" } }, - { { "Dat0=C %s", "MOVE.%-2s C,@D0" } }, - { { "Dat1=C %s", "MOVE.%-2s C,@D0" } }, + { "Dat0=A %s", "MOVE.%-2s A,@D0" }, + { "Dat1=A %s", "MOVE.%-2s A,@D0" }, + { "Dat0=C %s", "MOVE.%-2s C,@D0" }, + { "Dat1=C %s", "MOVE.%-2s C,@D0" }, // load - { { "A=Dat0 %s", "MOVE.%-2s @D0,A" } }, - { { "A=Dat1 %s", "MOVE.%-2s @D0,A" } }, - { { "C=Dat0 %s", "MOVE.%-2s @D0,C" } }, - { { "C=Dat1 %s", "MOVE.%-2s @D0,C" } }, + { "A=Dat0 %s", "MOVE.%-2s @D0,A" }, + { "A=Dat1 %s", "MOVE.%-2s @D0,A" }, + { "C=Dat0 %s", "MOVE.%-2s @D0,C" }, + { "C=Dat1 %s", "MOVE.%-2s @D0,C" }, // add/sub immediate - { { "D0=D0+ %x", "ADD.A %x,D0" } }, - { { "D1=D1+ %x", "ADD.A %x,D1" } }, - { { "D0=D0- %x", "SUB.A %x,D0" } }, - { { "D1=D1- %x", "SUB.A %x,D1" } }, - - { { "A=A+ %s,%x", "ADD.%-2s %x,A" } }, - { { "B=B+ %s,%x", "ADD.%-2s %x,B" } }, - { { "C=C+ %s,%x", "ADD.%-2s %x,C" } }, - { { "D=D+ %s,%x", "ADD.%-2s %x,D" } }, - { { "A=A- %s,%x", "SUB.%-2s %x,A" } }, - { { "B=B- %s,%x", "SUB.%-2s %x,B" } }, - { { "C=C- %s,%x", "SUB.%-2s %x,C" } }, - { { "D=D- %s,%x", "SUB.%-2s %x,D" } }, - - { { "A=A&B %s", "AND.%-2s B,A" } }, - { { "B=B&C %s", "AND.%-2s C,B" } }, - { { "C=C&A %s", "AND.%-2s A,C" } }, - { { "D=D&C %s", "AND.%-2s C,D" } }, - { { "B=B&A %s", "AND.%-2s A,B" } }, - { { "C=C&B %s", "AND.%-2s B,C" } }, - { { "A=A&C %s", "AND.%-2s C,A" } }, - { { "C=C&D %s", "AND.%-2s D,C" } }, - - { { "A=A!B %s", "OR.%-2s B,A" } }, - { { "B=B!C %s", "OR.%-2s C,B" } }, - { { "C=C!A %s", "OR.%-2s A,C" } }, - { { "D=D!C %s", "OR.%-2s C,D" } }, - { { "B=B!A %s", "OR.%-2s A,B" } }, - { { "C=C!B %s", "OR.%-2s B,C" } }, - { { "A=A!C %s", "OR.%-2s C,A" } }, - { { "C=C!D %s", "OR.%-2s D,C" } }, - - { { "Asrb %s", "SRB.%-2s A" } }, - { { "Bsrb %s", "SRB.%-2s B" } }, - { { "Csrb %s", "SRB.%-2s C" } }, - { { "Dsrb %s", "SRB.%-2s D" } }, - - { { "Aslc %s", "RLN.%-2s A" } }, - { { "Bslc %s", "RLN.%-2s B" } }, - { { "Cslc %s", "RLN.%-2s C" } }, - { { "Dslc %s", "RLN.%-2s D" } }, - { { "Asrc %s", "RRN.%-2s A" } }, - { { "Bsrc %s", "RRN.%-2s B" } }, - { { "Csrc %s", "RRN.%-2s C" } }, - { { "Dsrc %s", "RRN.%-2s D" } }, - - { { "A=A+B %s", "ADD.%-2s B,A" } }, - { { "B=B+C %s", "ADD.%-2s C,B" } }, - { { "C=C+A %s", "ADD.%-2s A,C" } }, - { { "D=D+C %s", "ADD.%-2s C,D" } }, - { { "A=A+A %s", "ADD.%-2s A,A" } }, - { { "B=B+B %s", "ADD.%-2s B,B" } }, - { { "C=C+C %s", "ADD.%-2s C,C" } }, - { { "D=D+C %s", "ADD.%-2s D,D" } }, - { { "B=B+A %s", "ADD.%-2s A,B" } }, - { { "C=C+B %s", "ADD.%-2s B,C" } }, - { { "A=A+C %s", "ADD.%-2s C,A" } }, - { { "C=C+D %s", "ADD.%-2s D,C" } }, - { { "A=A-1 %s", "DEC.%-2s A" } }, - { { "B=B-1 %s", "DEC.%-2s B" } }, - { { "C=C-1 %s", "DEC.%-2s C" } }, - { { "D=D-1 %s", "DEC.%-2s D" } }, - - { { "A=A-B %s", "ADD.%-2s B,A" } }, - { { "B=B-C %s", "ADD.%-2s C,B" } }, - { { "C=C-A %s", "ADD.%-2s A,C" } }, - { { "D=D-C %s", "ADD.%-2s C,D" } }, - { { "A=A+1 %s", "INC.%-2s A" } }, - { { "B=B+1 %s", "INC.%-2s B" } }, - { { "C=C+1 %s", "INC.%-2s C" } }, - { { "D=D+1 %s", "INC.%-2s D" } }, - { { "B=B-A %s", "SUB.%-2s A,B" } }, - { { "C=C-B %s", "SUB.%-2s B,C" } }, - { { "A=A-C %s", "SUB.%-2s C,A" } }, - { { "C=C-D %s", "SUB.%-2s D,C" } }, - { { "A=B-A %s", "SUBN.%-2s B,A" } }, - { { "B=C-B %s", "SUBN.%-2s C,B" } }, - { { "C=A-C %s", "SUBN.%-2s A,C" } }, - { { "D=C-D %s", "SUBN.%-2s C,D" } }, - - { { "A=0 %s", "CLR.%-2s A" } }, - { { "B=0 %s", "CLR.%-2s B" } }, - { { "C=0 %s", "CLR.%-2s C" } }, - { { "D=0 %s", "CLR.%-2s D" } }, - { { "A=B %s", "MOVE.%-2s B,A" } }, - { { "B=C %s", "MOVE.%-2s C,B" } }, - { { "C=A %s", "MOVE.%-2s A,C" } }, - { { "D=C %s", "MOVE.%-2s C,D" } }, - { { "B=A %s", "MOVE.%-2s A,B" } }, - { { "C=B %s", "MOVE.%-2s B,C" } }, - { { "A=C %s", "MOVE.%-2s C,A" } }, - { { "C=D %s", "MOVE.%-2s D,C" } }, - { { "ABex %s", "SWAP.%-2s A,B" } }, - { { "BCex %s", "SWAP.%-2s B,C" } }, - { { "ACex %s", "SWAP.%-2s A,C" } }, - { { "CDex %s", "SWAP.%-2s C,D" } }, - - { { "Asl %s", "SLN.%-2s A" } }, - { { "Bsl %s", "SLN.%-2s B" } }, - { { "Csl %s", "SLN.%-2s C" } }, - { { "Dsl %s", "SLN.%-2s D" } }, - { { "Asr %s", "SRN.%-2s A" } }, - { { "Bsr %s", "SRN.%-2s B" } }, - { { "Csr %s", "SRN.%-2s C" } }, - { { "Dsr %s", "SRN.%-2s D" } }, - { { "A=-A %s", "NEG.%-2s A" } }, - { { "B=-B %s", "NEG.%-2s B" } }, - { { "C=-C %s", "NEG.%-2s C" } }, - { { "D=-D %s", "NEG.%-2s D" } }, - { { "A=-A-1 %s", "NOT.%-2s A" } }, - { { "B=-B-1 %s", "NOT.%-2s B" } }, - { { "C=-C-1 %s", "NOT.%-2s C" } }, - { { "D=-D-1 %s", "NOT.%-2s D" } } - + { "D0=D0+ %x", "ADD.A %x,D0" }, + { "D1=D1+ %x", "ADD.A %x,D1" }, + { "D0=D0- %x", "SUB.A %x,D0" }, + { "D1=D1- %x", "SUB.A %x,D1" }, + + { "A=A+ %s,%x", "ADD.%-2s %x,A" }, + { "B=B+ %s,%x", "ADD.%-2s %x,B" }, + { "C=C+ %s,%x", "ADD.%-2s %x,C" }, + { "D=D+ %s,%x", "ADD.%-2s %x,D" }, + { "A=A- %s,%x", "SUB.%-2s %x,A" }, + { "B=B- %s,%x", "SUB.%-2s %x,B" }, + { "C=C- %s,%x", "SUB.%-2s %x,C" }, + { "D=D- %s,%x", "SUB.%-2s %x,D" }, + + { "A=A&B %s", "AND.%-2s B,A" }, + { "B=B&C %s", "AND.%-2s C,B" }, + { "C=C&A %s", "AND.%-2s A,C" }, + { "D=D&C %s", "AND.%-2s C,D" }, + { "B=B&A %s", "AND.%-2s A,B" }, + { "C=C&B %s", "AND.%-2s B,C" }, + { "A=A&C %s", "AND.%-2s C,A" }, + { "C=C&D %s", "AND.%-2s D,C" }, + + { "A=A!B %s", "OR.%-2s B,A" }, + { "B=B!C %s", "OR.%-2s C,B" }, + { "C=C!A %s", "OR.%-2s A,C" }, + { "D=D!C %s", "OR.%-2s C,D" }, + { "B=B!A %s", "OR.%-2s A,B" }, + { "C=C!B %s", "OR.%-2s B,C" }, + { "A=A!C %s", "OR.%-2s C,A" }, + { "C=C!D %s", "OR.%-2s D,C" }, + + { "Asrb %s", "SRB.%-2s A" }, + { "Bsrb %s", "SRB.%-2s B" }, + { "Csrb %s", "SRB.%-2s C" }, + { "Dsrb %s", "SRB.%-2s D" }, + + { "Aslc %s", "RLN.%-2s A" }, + { "Bslc %s", "RLN.%-2s B" }, + { "Cslc %s", "RLN.%-2s C" }, + { "Dslc %s", "RLN.%-2s D" }, + { "Asrc %s", "RRN.%-2s A" }, + { "Bsrc %s", "RRN.%-2s B" }, + { "Csrc %s", "RRN.%-2s C" }, + { "Dsrc %s", "RRN.%-2s D" }, + + { "A=A+B %s", "ADD.%-2s B,A" }, + { "B=B+C %s", "ADD.%-2s C,B" }, + { "C=C+A %s", "ADD.%-2s A,C" }, + { "D=D+C %s", "ADD.%-2s C,D" }, + { "A=A+A %s", "ADD.%-2s A,A" }, + { "B=B+B %s", "ADD.%-2s B,B" }, + { "C=C+C %s", "ADD.%-2s C,C" }, + { "D=D+C %s", "ADD.%-2s D,D" }, + { "B=B+A %s", "ADD.%-2s A,B" }, + { "C=C+B %s", "ADD.%-2s B,C" }, + { "A=A+C %s", "ADD.%-2s C,A" }, + { "C=C+D %s", "ADD.%-2s D,C" }, + { "A=A-1 %s", "DEC.%-2s A" }, + { "B=B-1 %s", "DEC.%-2s B" }, + { "C=C-1 %s", "DEC.%-2s C" }, + { "D=D-1 %s", "DEC.%-2s D" }, + + { "A=A-B %s", "ADD.%-2s B,A" }, + { "B=B-C %s", "ADD.%-2s C,B" }, + { "C=C-A %s", "ADD.%-2s A,C" }, + { "D=D-C %s", "ADD.%-2s C,D" }, + { "A=A+1 %s", "INC.%-2s A" }, + { "B=B+1 %s", "INC.%-2s B" }, + { "C=C+1 %s", "INC.%-2s C" }, + { "D=D+1 %s", "INC.%-2s D" }, + { "B=B-A %s", "SUB.%-2s A,B" }, + { "C=C-B %s", "SUB.%-2s B,C" }, + { "A=A-C %s", "SUB.%-2s C,A" }, + { "C=C-D %s", "SUB.%-2s D,C" }, + { "A=B-A %s", "SUBN.%-2s B,A" }, + { "B=C-B %s", "SUBN.%-2s C,B" }, + { "C=A-C %s", "SUBN.%-2s A,C" }, + { "D=C-D %s", "SUBN.%-2s C,D" }, + + { "A=0 %s", "CLR.%-2s A" }, + { "B=0 %s", "CLR.%-2s B" }, + { "C=0 %s", "CLR.%-2s C" }, + { "D=0 %s", "CLR.%-2s D" }, + { "A=B %s", "MOVE.%-2s B,A" }, + { "B=C %s", "MOVE.%-2s C,B" }, + { "C=A %s", "MOVE.%-2s A,C" }, + { "D=C %s", "MOVE.%-2s C,D" }, + { "B=A %s", "MOVE.%-2s A,B" }, + { "C=B %s", "MOVE.%-2s B,C" }, + { "A=C %s", "MOVE.%-2s C,A" }, + { "C=D %s", "MOVE.%-2s D,C" }, + { "ABex %s", "SWAP.%-2s A,B" }, + { "BCex %s", "SWAP.%-2s B,C" }, + { "ACex %s", "SWAP.%-2s A,C" }, + { "CDex %s", "SWAP.%-2s C,D" }, + + { "Asl %s", "SLN.%-2s A" }, + { "Bsl %s", "SLN.%-2s B" }, + { "Csl %s", "SLN.%-2s C" }, + { "Dsl %s", "SLN.%-2s D" }, + { "Asr %s", "SRN.%-2s A" }, + { "Bsr %s", "SRN.%-2s B" }, + { "Csr %s", "SRN.%-2s C" }, + { "Dsr %s", "SRN.%-2s D" }, + { "A=-A %s", "NEG.%-2s A" }, + { "B=-B %s", "NEG.%-2s B" }, + { "C=-C %s", "NEG.%-2s C" }, + { "D=-D %s", "NEG.%-2s D" }, + { "A=-A-1 %s", "NOT.%-2s A" }, + { "B=-B-1 %s", "NOT.%-2s B" }, + { "C=-C-1 %s", "NOT.%-2s C" }, + { "D=-D-1 %s", "NOT.%-2s D" } }; -enum opcode_sel -{ - Complete=-1, - Illegal, - Opcode0, Opcode0E, Opcode0Ea, - Opcode1, Opcode10, Opcode11, Opcode12, Opcode13, Opcode14, Opcode15, - Opcode8, Opcode80, Opcode808, Opcode8081, - Opcode81, Opcode818, Opcode818a, Opcode819, Opcode819a, - Opcode81A, Opcode81Aa, Opcode81Aa0,Opcode81Aa1, Opcode81Aa2, Opcode81B, - Opcode8A, Opcode8B, - Opcode9, Opcode9a, Opcode9b, - OpcodeA, OpcodeAa, OpcodeAb, - OpcodeB, OpcodeBa, OpcodeBb, - OpcodeC, - OpcodeD, - OpcodeE, - OpcodeF -}; - -enum opcode_adr -{ - AdrNone, - AdrAF, AdrA, AdrB, AdrCount, - BranchReturn, TestBranchRet, ImmBranch, - ABranchReturn, // address field A - xBranchReturn, // address field specified in previous opcode entry - Imm, ImmCount, ImmCload, Imm2, Imm4, Imm5, - Dis3, Dis3Call, Dis4, Dis4Call, Abs, - FieldP, FieldWP, FieldXS, FieldX, FieldS, FieldM, FieldB, FieldW, FieldA, - AdrImmCount -}; -struct OPCODE -{ - opcode_sel sel; - opcode_adr adr; - MNEMONICS mnemonic; -}; -static const char *field_2_string(int adr_enum) +const char *saturn_disassembler::field_2_string(int adr_enum) { switch (adr_enum) { case FieldP: return P; @@ -593,7 +412,7 @@ static const char *field_2_string(int adr_enum) return nullptr; } -static const OPCODE opcodes[][0x10]= { +const saturn_disassembler::OPCODE saturn_disassembler::opcs[][0x10]= { { // first digit { Opcode0 }, @@ -805,7 +624,7 @@ static const OPCODE opcodes[][0x10]= { { Complete, AdrNone, inA }, { Complete, AdrNone, inC }, { Complete, AdrNone, unconfig }, - { Complete, AdrNone, config }, + { Complete, AdrNone, xconfig }, { Complete, AdrNone, Cid }, { Complete, AdrNone, shutdown }, { Opcode808 }, @@ -1258,31 +1077,42 @@ static const OPCODE opcodes[][0x10]= { } }; -static const int field_adr_af[]= +const int saturn_disassembler::field_adr_af[]= { FieldP, FieldWP, FieldXS, FieldX, FieldS, FieldM, FieldB, FieldW, 0, 0, 0, 0, 0, 0, 0, FieldA }; -static const int field_adr_a[]= +const int saturn_disassembler::field_adr_a[]= { FieldP, FieldWP, FieldXS, FieldX, FieldS, FieldM, FieldB, FieldW}; -static const int field_adr_b[]= +const int saturn_disassembler::field_adr_b[]= { FieldP, FieldWP, FieldXS, FieldX, FieldS, FieldM, FieldB, FieldW }; -CPU_DISASSEMBLE(saturn) +saturn_disassembler::saturn_disassembler(config *conf) : m_config(conf) +{ +} + +u32 saturn_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t saturn_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { int adr=0; int cont=1; // operation still not complete disassembled char bin[10]; int binsize=0; // protocollizing fetched nibbles char number[17]; - const OPCODE *level=opcodes[0]; //pointer to current digit + const OPCODE *level=opcs[0]; //pointer to current digit int op; // currently fetched nibble - int pos = 0; + offs_t pos = pc; int i,c,v; + int mnemonics_bank = m_config->get_nonstandard_mnemonics_mode() ? 1 : 0; + while (cont) { - op = oprom[pos++] & 0xf; + op = opcodes.r8(pos++) & 0xf; level+=op; switch (level->sel) { case Illegal: @@ -1316,155 +1146,155 @@ CPU_DISASSEMBLE(saturn) cont=0; switch (level->adr==AdrNone?adr:level->adr) { case AdrNone: - stream << mnemonics[level->mnemonic].name[set]; + stream << mnemonics[level->mnemonic][mnemonics_bank]; break; case Imm: - util::stream_format(stream, mnemonics[level->mnemonic].name[set], oprom[pos++]); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], opcodes.r8(pos++)); break; case ImmCount: - util::stream_format(stream, mnemonics[level->mnemonic].name[set], oprom[pos++]+1); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], opcodes.r8(pos++)+1); break; case AdrImmCount: - util::stream_format(stream, mnemonics[level->mnemonic].name[set], field_2_string(adr), oprom[pos++]+1); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], field_2_string(adr), opcodes.r8(pos++)+1); break; case AdrCount: // mnemonics have string %s for address field - snprintf(number,sizeof(number),"%x",oprom[pos++]+1); - util::stream_format(stream, mnemonics[level->mnemonic].name[set], number); + snprintf(number,sizeof(number),"%x",opcodes.r8(pos++)+1); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], number); break; case Imm2: - v=oprom[pos++]; - v|=oprom[pos++]<<4; - util::stream_format(stream, mnemonics[level->mnemonic].name[set], v); + v=opcodes.r8(pos++); + v|=opcodes.r8(pos++)<<4; + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], v); break; case Imm4: - v=oprom[pos++]; - v|=oprom[pos++]<<4; - v|=oprom[pos++]<<8; - v|=oprom[pos++]<<12; - util::stream_format(stream, mnemonics[level->mnemonic].name[set], v); + v=opcodes.r8(pos++); + v|=opcodes.r8(pos++)<<4; + v|=opcodes.r8(pos++)<<8; + v|=opcodes.r8(pos++)<<12; + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], v); break; case Imm5: - v=oprom[pos++]; - v|=oprom[pos++]<<4; - v|=oprom[pos++]<<8; - v|=oprom[pos++]<<12; - v|=oprom[pos++]<<16; - util::stream_format(stream, mnemonics[level->mnemonic].name[set], v); + v=opcodes.r8(pos++); + v|=opcodes.r8(pos++)<<4; + v|=opcodes.r8(pos++)<<8; + v|=opcodes.r8(pos++)<<12; + v|=opcodes.r8(pos++)<<16; + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], v); break; case ImmCload: - c=i=oprom[pos++] & 0xf; + c=i=opcodes.r8(pos++) & 0xf; number[i+1]=0; - for (;i>=0; i--) number[i]=number_2_hex[oprom[pos++] & 0xf]; - util::stream_format(stream, mnemonics[level->mnemonic].name[set], c+1, number); + for (;i>=0; i--) number[i]=number_2_hex[opcodes.r8(pos++) & 0xf]; + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], c+1, number); break; case Dis3: SATURN_PEEKOP_DIS12(v); c=(pc+pos-3+v)&0xfffff; - util::stream_format(stream, mnemonics[level->mnemonic].name[set], c ); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], c ); break; case Dis3Call: SATURN_PEEKOP_DIS12(v); c=(pc+pos+v)&0xfffff; - util::stream_format(stream, mnemonics[level->mnemonic].name[set], c ); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], c ); break; case Dis4: SATURN_PEEKOP_DIS16(v); c=(pc+pos-4+v)&0xfffff; - util::stream_format(stream, mnemonics[level->mnemonic].name[set], c ); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], c ); break; case Dis4Call: SATURN_PEEKOP_DIS16(v); c=(pc+pos+v)&0xfffff; - util::stream_format(stream, mnemonics[level->mnemonic].name[set], c ); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], c ); break; case Abs: SATURN_PEEKOP_ADR(v); - util::stream_format(stream, mnemonics[level->mnemonic].name[set], v ); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], v ); break; case BranchReturn: SATURN_PEEKOP_DIS8(v); if (v==0) { - stream << mnemonics[level->mnemonic+1].name[set]; + stream << mnemonics[level->mnemonic+1][mnemonics_bank]; } else { c=(pc+pos-2+v)&0xfffff; - util::stream_format(stream, mnemonics[level->mnemonic].name[set], c); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], c); } break; case ABranchReturn: SATURN_PEEKOP_DIS8(v); if (v==0) { - util::stream_format(stream, mnemonics[level->mnemonic+1].name[set], A); + util::stream_format(stream, mnemonics[level->mnemonic+1][mnemonics_bank], A); } else { c=(pc+pos-2+v)&0xfffff; - util::stream_format(stream, mnemonics[level->mnemonic].name[set], A, c); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], A, c); } break; case xBranchReturn: SATURN_PEEKOP_DIS8(v); if (v==0) { - util::stream_format(stream, mnemonics[level->mnemonic+1].name[set], field_2_string(adr)); + util::stream_format(stream, mnemonics[level->mnemonic+1][mnemonics_bank], field_2_string(adr)); } else { c=(pc+pos-2+v)&0xfffff; - util::stream_format(stream, mnemonics[level->mnemonic].name[set], field_2_string(adr), c); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], field_2_string(adr), c); } break; case TestBranchRet: - i=oprom[pos++]; + i=opcodes.r8(pos++); SATURN_PEEKOP_DIS8(v); if (v==0) { - util::stream_format(stream, mnemonics[level->mnemonic+1].name[set], i); + util::stream_format(stream, mnemonics[level->mnemonic+1][mnemonics_bank], i); } else { c=(pc+pos-2+v)&0xfffff; - util::stream_format(stream, mnemonics[level->mnemonic].name[set], i, c); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], i, c); } break; case ImmBranch: - i=oprom[pos++]; + i=opcodes.r8(pos++); SATURN_PEEKOP_DIS8(v); c=(pc+pos-2+v)&0xfffff; - util::stream_format(stream, mnemonics[level->mnemonic].name[set], i, c); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], i, c); break; case FieldP: - util::stream_format(stream, mnemonics[level->mnemonic].name[set], P ); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], P ); break; case FieldWP: - util::stream_format(stream, mnemonics[level->mnemonic].name[set], WP ); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], WP ); break; case FieldXS: - util::stream_format(stream, mnemonics[level->mnemonic].name[set], XS ); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], XS ); break; case FieldX: - util::stream_format(stream, mnemonics[level->mnemonic].name[set], X ); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], X ); break; case FieldS: - util::stream_format(stream, mnemonics[level->mnemonic].name[set], S ); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], S ); break; case FieldM: - util::stream_format(stream, mnemonics[level->mnemonic].name[set], M ); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], M ); break; case FieldB: - util::stream_format(stream, mnemonics[level->mnemonic].name[set], B ); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], B ); break; case FieldA: - util::stream_format(stream, mnemonics[level->mnemonic].name[set], A ); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], A ); break; case FieldW: - util::stream_format(stream, mnemonics[level->mnemonic].name[set], W ); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], W ); break; case AdrA: - util::stream_format(stream, mnemonics[level->mnemonic].name[set], adr_a[oprom[pos++] & 0x7] ); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], adr_a[opcodes.r8(pos++) & 0x7] ); break; case AdrAF: - util::stream_format(stream, mnemonics[level->mnemonic].name[set], adr_af[oprom[pos++] & 0xf] ); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], adr_af[opcodes.r8(pos++) & 0xf] ); break; case AdrB: - util::stream_format(stream, mnemonics[level->mnemonic].name[set], adr_b[oprom[pos++] & 0x7] ); + util::stream_format(stream, mnemonics[level->mnemonic][mnemonics_bank], adr_b[opcodes.r8(pos++) & 0x7] ); break; } break; } - level = opcodes[level->sel]; + level = opcs[level->sel]; } - return pos; + return pos - pc; } diff --git a/src/devices/cpu/saturn/saturnds.h b/src/devices/cpu/saturn/saturnds.h new file mode 100644 index 00000000000..676f59ff290 --- /dev/null +++ b/src/devices/cpu/saturn/saturnds.h @@ -0,0 +1,215 @@ +// license:BSD-3-Clause +// copyright-holders:Peter Trauner,Antoine Mine +/***************************************************************************** + * + * saturnds.c + * portable saturn emulator interface + * (hp calculators) + * + *****************************************************************************/ + +#ifndef MAME_CPU_SATURN_SATURNDS_H +#define MAME_CPU_SATURN_SATURNDS_H + +#pragma once + +class saturn_disassembler : public util::disasm_interface +{ +public: + struct config { + virtual ~config() = default; + virtual bool get_nonstandard_mnemonics_mode() const = 0; + }; + + saturn_disassembler(config *conf); + virtual ~saturn_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + // don't split branch and return, source relies on this ordering + enum MNEMONICS + { + Return, ReturnSetXM, ReturnSetCarry, ReturnClearCarry, ReturnFromInterrupt, + jump3,jump4,jump, + call3,call4,call, + branchCarrySet, returnCarrySet, + branchCarryClear, returnCarryClear, + + outCS, outC, inA, inC, + unconfig, xconfig, Cid, shutdown, cp1, reset, buscc, + CcopyP, PcopyC, sreq, CswapP, + + inton, AloadImm, buscb, + clearAbit, setAbit, + branchAbitclear, returnAbitclear, + branchAbitset, returnAbitset, + clearCbit, setCbit, + branchCbitclear, returnCbitclear, + branchCbitset, returnCbitset, + PCloadA, buscd, PCloadC, intoff, rsi, + + jumpA, jumpC, PCcopyA, PCcopyC, AcopyPC, CcopyPC, + + clearHST, + branchHSTclear, returnHSTclear, + + clearBitST, setBitST, + branchSTclear, returnSTclear, + branchSTset, returnSTset, + + branchPdiffers, returnPdiffers, + branchPequals, returnPequals, + + branchAequalsB, returnAequalsB, + branchBequalsC, returnBequalsC, + branchAequalsC, returnAequalsC, + branchCequalsD, returnCequalsD, + branchAdiffersB, returnAdiffersB, + branchBdiffersC, returnBdiffersC, + branchAdiffersC, returnAdiffersC, + branchCdiffersD, returnCdiffersD, + branchAzero, returnAzero, + branchBzero, returnBzero, + branchCzero, returnCzero, + branchDzero, returnDzero, + branchAnotzero, returnAnotzero, + branchBnotzero, returnBnotzero, + branchCnotzero, returnCnotzero, + branchDnotzero, returnDnotzero, + + branchAgreaterB, returnAgreaterB, + branchBgreaterC, returnBgreaterC, + branchCgreaterA, returnCgreaterA, + branchDgreaterC, returnDgreaterC, + branchAlowerB, returnAlowerB, + branchBlowerC, returnBlowerC, + branchClowerA, returnClowerA, + branchDlowerC, returnDlowerC, + branchAnotlowerB, returnAnotlowerB, + branchBnotlowerC, returnBnotlowerC, + branchCnotlowerA, returnCnotlowerA, + branchDnotlowerC, returnDnotlowerC, + branchAnotgreaterB, returnAnotgreaterB, + branchBnotgreaterC, returnBnotgreaterC, + branchCnotgreaterA, returnCnotgreaterA, + branchDnotgreaterC, returnDnotgreaterC, + + SetHexMode, SetDecMode, + PushC, PopC, + + D0loadImm2, D0loadImm4, D0loadImm5, + D1loadImm2, D1loadImm4, D1loadImm5, + PloadImm, CloadImm, + + clearST, + CcopyST, STcopyC, + swapCST, + + incP, decP, + + R0copyA, R1copyA, R2copyA, R3copyA, R4copyA, + R0copyC, R1copyC, R2copyC, R3copyC, R4copyC, + + AcopyR0, AcopyR1, AcopyR2, AcopyR3, AcopyR4, + CcopyR0, CcopyR1, CcopyR2, CcopyR3, CcopyR4, + + D0copyA, D1copyA, D0copyC, D1copyC, + D0copyAShort, D1copyAShort, D0copyCShort, D1copyCShort, // other class mnemonic + + SwapAR0, SwapAR1, SwapAR2, SwapAR3, SwapAR4, + SwapCR0, SwapCR1, SwapCR2, SwapCR3, SwapCR4, + + SwapAD0, SwapAD1, SwapCD0, SwapCD1, + SwapAD0Short, SwapAD1Short, SwapCD0Short, SwapCD1Short, // other class mnemonic + + D0storeA, D1storeA, D0storeC, D1storeC, + AloadD0, AloadD1, CloadD0, CloadD1, + + D0addImm, D1addImm, D0subImm, D1subImm, + AaddImm, BaddImm, CaddImm, DaddImm, + AsubImm, BsubImm, CsubImm, DsubImm, + + AandB, BandC, CandA, DandC, BandA, CandB, AandC, CandD, + AorB, BorC, CorA, DorC, BorA, CorB, AorC, CorD, + + Ashiftrightbit, Bshiftrightbit, Cshiftrightbit, Dshiftrightbit, + + AshiftleftCarry, BshiftleftCarry, CshiftleftCarry, DshiftleftCarry, + AshiftrightCarry, BshiftrightCarry, CshiftrightCarry, DshiftrightCarry, + + AaddB, BaddC, CaddA, DaddC, AaddA, BaddB, CaddC, DaddD, + BaddA, CaddB, AaddC, CaddD, decA, decB, decC, decD, + + AsubB, BsubC, CsubA, DsubC, incA, incB, incC, incD, + BsubA, CsubB, AsubC, CsubD, AsubnB, BsubnC, CsubnA, DsubnC, + + clearA, clearB, clearC, clearD, + AcopyB, BcopyC, CcopyA, DcopyC, BcopyA, CcopyB, AcopyC, CcopyD, + AswapB, BswapC, CswapA, DswapC, + + Ashiftleft, Bshiftleft, Cshiftleft, Dshiftleft, + Ashiftright, Bshiftright, Cshiftright, Dshiftright, + negateA, negateB, negateC, negateD, + notA, notB, notC, notD + }; + + enum opcode_sel + { + Complete=-1, + Illegal, + Opcode0, Opcode0E, Opcode0Ea, + Opcode1, Opcode10, Opcode11, Opcode12, Opcode13, Opcode14, Opcode15, + Opcode8, Opcode80, Opcode808, Opcode8081, + Opcode81, Opcode818, Opcode818a, Opcode819, Opcode819a, + Opcode81A, Opcode81Aa, Opcode81Aa0,Opcode81Aa1, Opcode81Aa2, Opcode81B, + Opcode8A, Opcode8B, + Opcode9, Opcode9a, Opcode9b, + OpcodeA, OpcodeAa, OpcodeAb, + OpcodeB, OpcodeBa, OpcodeBb, + OpcodeC, + OpcodeD, + OpcodeE, + OpcodeF + }; + + enum opcode_adr + { + AdrNone, + AdrAF, AdrA, AdrB, AdrCount, + BranchReturn, TestBranchRet, ImmBranch, + ABranchReturn, // address field A + xBranchReturn, // address field specified in previous opcode entry + Imm, ImmCount, ImmCload, Imm2, Imm4, Imm5, + Dis3, Dis3Call, Dis4, Dis4Call, Abs, + FieldP, FieldWP, FieldXS, FieldX, FieldS, FieldM, FieldB, FieldW, FieldA, + AdrImmCount + }; + + struct OPCODE + { + opcode_sel sel; + opcode_adr adr; + MNEMONICS mnemonic; + }; + + config *m_config; + + static const char *const adr_b[]; + static const char *const adr_af[]; + static const char *const adr_a[]; + static const char number_2_hex[]; + + static const char *const mnemonics[][2]; + static const OPCODE opcs[][0x10]; + + static const int field_adr_af[]; + static const int field_adr_a[]; + static const int field_adr_b[]; + + const char *field_2_string(int adr_enum); + +}; + +#endif diff --git a/src/devices/cpu/sc61860/sc61860.cpp b/src/devices/cpu/sc61860/sc61860.cpp index a4f82ccdedc..01b5533cfce 100644 --- a/src/devices/cpu/sc61860/sc61860.cpp +++ b/src/devices/cpu/sc61860/sc61860.cpp @@ -19,7 +19,7 @@ #include "emu.h" #include "sc61860.h" - +#include "scdasm.h" #include "debugger.h" @@ -69,11 +69,9 @@ device_memory_interface::space_config_vector sc61860_device::memory_space_config }; } - -offs_t sc61860_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *sc61860_device::create_disassembler() { - extern CPU_DISASSEMBLE( sc61860 ); - return CPU_DISASSEMBLE_NAME(sc61860)(this, stream, pc, oprom, opram, options); + return new sc61860_disassembler; } diff --git a/src/devices/cpu/sc61860/sc61860.h b/src/devices/cpu/sc61860/sc61860.h index de7653b73be..61eb370d404 100644 --- a/src/devices/cpu/sc61860/sc61860.h +++ b/src/devices/cpu/sc61860/sc61860.h @@ -109,9 +109,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/sc61860/scdasm.cpp b/src/devices/cpu/sc61860/scdasm.cpp index 050dfaa3b1d..8b14a920d62 100644 --- a/src/devices/cpu/sc61860/scdasm.cpp +++ b/src/devices/cpu/sc61860/scdasm.cpp @@ -11,9 +11,7 @@ *****************************************************************************/ #include "emu.h" -#include "debugger.h" - -#include "sc61860.h" +#include "scdasm.h" /* new: @@ -67,21 +65,7 @@ ex exchange */ - -enum Adr -{ - Ill, - Imp, - Imm, ImmW, - RelP, RelM, - Abs, - Ptc, - Etc, - Cal, - Lp -}; - -static const struct { const char *mnemonic; Adr adr; } table[]={ +const sc61860_disassembler::opcode sc61860_disassembler::table[]={ { "LII", Imm }, { "LIJ", Imm }, { "LIA", Imm }, { "LIB", Imm }, { "IX", Imp }, { "DX", Imp }, { "IY", Imp }, { "DY", Imp }, { "MVW", Imp }, { "EXW", Imp }, { "MVB", Imp }, { "EXB", Imp }, @@ -152,10 +136,15 @@ static const struct { const char *mnemonic; Adr adr; } table[]={ { nullptr }, { nullptr }, { nullptr }, { nullptr }, { nullptr }, { nullptr }, { nullptr }, { nullptr }, }; -CPU_DISASSEMBLE(sc61860) +u32 sc61860_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t sc61860_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - const uint8_t *base_oprom = oprom; - int oper=*(oprom++); + offs_t pos = pc; + int oper=opcodes.r8(pos++); int t; uint16_t adr; @@ -167,32 +156,32 @@ CPU_DISASSEMBLE(sc61860) switch(oper&0xe0) { case 0xe0: util::stream_format(stream,"%-6s%04x",table[oper&0xe0].mnemonic, - *(oprom++)|((oper&0x1f)<<8)); + opcodes.r8(pos++)|((oper&0x1f)<<8)); break; default: switch (table[oper].adr) { case Ill: util::stream_format(stream,"?%02x",oper);break; case Imp: util::stream_format(stream,"%s",table[oper].mnemonic); break; - case Imm: util::stream_format(stream,"%-6s%02x",table[oper].mnemonic, *(oprom++)); break; + case Imm: util::stream_format(stream,"%-6s%02x",table[oper].mnemonic, opcodes.r8(pos++)); break; case ImmW: - adr=(oprom[0]<<8)|oprom[1];oprom+=2; + adr=opcodes.r16(pos); pos+=2; util::stream_format(stream,"%-6s%04x",table[oper].mnemonic, adr); break; case Abs: - adr=(oprom[0]<<8)|oprom[1];oprom+=2; + adr=opcodes.r16(pos); pos+=2; util::stream_format(stream,"%-6s%04x",table[oper].mnemonic, adr); break; case RelM: - adr=pc-*(oprom++); + adr=pc-opcodes.r8(pos++); util::stream_format(stream,"%-6s%04x",table[oper].mnemonic, adr&0xffff); break; case RelP: - adr=pc+*(oprom++); + adr=pc+opcodes.r8(pos++); util::stream_format(stream,"%-6s%04x",table[oper].mnemonic, adr&0xffff); break; case Ptc: - t=*(oprom++); - adr=(oprom[0]<<8)|oprom[1];oprom+=2; + t=opcodes.r8(pos++); + adr=opcodes.r16(pos); pos+=2; util::stream_format(stream,"%-6s%02x,%04x",table[oper].mnemonic,t, adr); break; case Etc: @@ -206,5 +195,5 @@ CPU_DISASSEMBLE(sc61860) } break; } - return oprom - base_oprom; + return pos - pc; } diff --git a/src/devices/cpu/sc61860/scdasm.h b/src/devices/cpu/sc61860/scdasm.h new file mode 100644 index 00000000000..575106ac2c8 --- /dev/null +++ b/src/devices/cpu/sc61860/scdasm.h @@ -0,0 +1,50 @@ +// license:BSD-3-Clause +// copyright-holders:Peter Trauner +/***************************************************************************** + * + * scdasm.c + * portable sharp 61860 emulator interface + * (sharp pocket computers) + * + * Copyright Peter Trauner, all rights reserved. + * + *****************************************************************************/ + +#ifndef MAME_CPU_SC61860_SCDASM_H +#define MAME_CPU_SC61860_SCDASM_H + +#pragma once + +class sc61860_disassembler : public util::disasm_interface +{ +public: + sc61860_disassembler() = default; + virtual ~sc61860_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum Adr + { + Ill, + Imp, + Imm, ImmW, + RelP, RelM, + Abs, + Ptc, + Etc, + Cal, + Lp + }; + + struct opcode { + const char *mnemonic; + Adr adr; + }; + + static const opcode table[]; + +}; + +#endif diff --git a/src/devices/cpu/scmp/scmp.cpp b/src/devices/cpu/scmp/scmp.cpp index 94bcb3fcf6c..4ed579eb7b6 100644 --- a/src/devices/cpu/scmp/scmp.cpp +++ b/src/devices/cpu/scmp/scmp.cpp @@ -10,6 +10,7 @@ #include "emu.h" #include "scmp.h" +#include "scmpdasm.h" #include "debugger.h" @@ -54,10 +55,9 @@ ins8060_device::ins8060_device(const machine_config &mconfig, const char *tag, d } -offs_t scmp_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *scmp_device::create_disassembler() { - extern CPU_DISASSEMBLE( scmp ); - return CPU_DISASSEMBLE_NAME(scmp)(this, stream, pc, oprom, opram, options); + return new scmp_disassembler; } diff --git a/src/devices/cpu/scmp/scmp.h b/src/devices/cpu/scmp/scmp.h index 553af2dad0f..85695a90c75 100644 --- a/src/devices/cpu/scmp/scmp.h +++ b/src/devices/cpu/scmp/scmp.h @@ -54,9 +54,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 2; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/scmp/scmpdasm.cpp b/src/devices/cpu/scmp/scmpdasm.cpp index 2f77afc519d..1a906218a38 100644 --- a/src/devices/cpu/scmp/scmpdasm.cpp +++ b/src/devices/cpu/scmp/scmpdasm.cpp @@ -9,21 +9,24 @@ *****************************************************************************/ #include "emu.h" +#include "scmpdasm.h" -#define OP(A) oprom[(A) - PC] -#define ARG(A) opram[(A) - PC] +u32 scmp_disassembler::opcode_alignment() const +{ + return 1; +} -CPU_DISASSEMBLE(scmp) +offs_t scmp_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { unsigned PC = pc; - uint8_t op = OP(pc++); + uint8_t op = opcodes.r8(pc++); uint8_t ptr = op & 3; if (BIT(op,7)) { // two bytes instructions char as[10]; char aspr[10]; - uint8_t arg = ARG(pc); pc++; + uint8_t arg = params.r8(pc); pc++; if (arg==0x80) { sprintf(as,"E"); } else { diff --git a/src/devices/cpu/scmp/scmpdasm.h b/src/devices/cpu/scmp/scmpdasm.h new file mode 100644 index 00000000000..915f74ee848 --- /dev/null +++ b/src/devices/cpu/scmp/scmpdasm.h @@ -0,0 +1,26 @@ +// license:BSD-3-Clause +// copyright-holders:Miodrag Milanovic +/***************************************************************************** + * + * scmpdasm.c + * + * National Semiconductor SC/MP CPU Disassembly + * + *****************************************************************************/ + +#ifndef MAME_CPU_SCMP_SCMPDASM_H +#define MAME_CPU_SCMP_SCMPDASM_H + +#pragma once + +class scmp_disassembler : public util::disasm_interface +{ +public: + scmp_disassembler() = default; + virtual ~scmp_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/score/score.cpp b/src/devices/cpu/score/score.cpp index f346fd93dc1..c3d9bba72d4 100644 --- a/src/devices/cpu/score/score.cpp +++ b/src/devices/cpu/score/score.cpp @@ -10,6 +10,7 @@ #include "emu.h" #include "debugger.h" #include "score.h" +#include "scoredsm.h" //************************************************************************** @@ -1348,3 +1349,8 @@ void score7_cpu_device::unemulated_op(const char * op) { fatalerror("%s: unemulated %s (PC=0x%08x)\n", tag(), op, m_ppc); } + +util::disasm_interface *score7_cpu_device::create_disassembler() +{ + return new score7_disassembler; +} diff --git a/src/devices/cpu/score/score.h b/src/devices/cpu/score/score.h index 48d832f3ada..1e85cbbf54f 100644 --- a/src/devices/cpu/score/score.h +++ b/src/devices/cpu/score/score.h @@ -54,9 +54,7 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: // helpers @@ -73,9 +71,6 @@ private: void check_irq(); void gen_exception(int cause, uint32_t param = 0); - offs_t disasm(std::ostream &stream, offs_t pc, uint32_t opcode); - void disasm32(std::ostream &stream, offs_t pc, uint32_t opcode); - void disasm16(std::ostream &stream, offs_t pc, uint16_t opcode); void unemulated_op(const char * op); // 32-bit opcodes @@ -130,19 +125,6 @@ private: typedef void (score7_cpu_device::*op_handler)(); static const op_handler s_opcode32_table[4*8]; static const op_handler s_opcode16_table[8]; - - // mnemonics - static const char *const m_cond[16]; - static const char *const m_tcs[4]; - static const char *const m_rix1_op[8]; - static const char *const m_rix2_op[8]; - static const char *const m_r2_op[16]; - static const char *const m_i1_op[8]; - static const char *const m_i2_op[8]; - static const char *const m_ls_op[8]; - static const char *const m_i1a_op[8]; - static const char *const m_i1b_op[8]; - static const char *const m_cr_op[2]; }; DECLARE_DEVICE_TYPE(SCORE7, score7_cpu_device) diff --git a/src/devices/cpu/score/scoredsm.cpp b/src/devices/cpu/score/scoredsm.cpp index d4b5ddbf78a..5e5b6b4e8ac 100644 --- a/src/devices/cpu/score/scoredsm.cpp +++ b/src/devices/cpu/score/scoredsm.cpp @@ -7,23 +7,29 @@ ******************************************************************************/ #include "emu.h" -#include "score.h" +#include "scoredsm.h" #include "scorem.h" -const char *const score7_cpu_device::m_cond[16] = { "cs", "cc", "gtu", "leu", "eq", "ne", "gt", "le", "ge", "lt", "mi", "pl", "vs", "vc", "cnz", "" }; -const char *const score7_cpu_device::m_tcs[4] = { "teq", "tmi", "", ""}; -const char *const score7_cpu_device::m_rix1_op[8] = { "lw" ,"lh" ,"lhu" ,"lb" ,"sw" ,"sh" ,"lbu" ,"sb" }; -const char *const score7_cpu_device::m_rix2_op[8] = { "lw", "lh", "lhu", "lb", "sw", "sh", "lbu", "sb" }; -const char *const score7_cpu_device::m_r2_op[16] = { "add", "sub", "neg", "cmp", "and", "or", "not", "xor", "lw", "lh", "pop", "lbu", "sw", "sh", "push", "sb" }; -const char *const score7_cpu_device::m_i1_op[8] = { "addi", "", "cmpi", "", "andi", "ori", "ldi", "" }; -const char *const score7_cpu_device::m_i2_op[8] = { "addis", "", "cmpis", "", "andis", "oris", "ldis", "" }; -const char *const score7_cpu_device::m_ls_op[8] = { "lw", "lh", "lhu", "lb", "sw", "sh", "lbu", "sb" }; -const char *const score7_cpu_device::m_i1a_op[8] = { "addei", "slli", "sdbbp", "srli", "bitclr", "bitset", "bittst", "" }; -const char *const score7_cpu_device::m_i1b_op[8] = { "lwp", "lhp", "", "lbup", "swp", "shp", "", "sbp" }; -const char *const score7_cpu_device::m_cr_op[2] = { "mtcr", "mfcr" }; +const char *const score7_disassembler::m_cond[16] = { "cs", "cc", "gtu", "leu", "eq", "ne", "gt", "le", "ge", "lt", "mi", "pl", "vs", "vc", "cnz", "" }; +const char *const score7_disassembler::m_tcs[4] = { "teq", "tmi", "", ""}; +const char *const score7_disassembler::m_rix1_op[8] = { "lw" ,"lh" ,"lhu" ,"lb" ,"sw" ,"sh" ,"lbu" ,"sb" }; +const char *const score7_disassembler::m_rix2_op[8] = { "lw", "lh", "lhu", "lb", "sw", "sh", "lbu", "sb" }; +const char *const score7_disassembler::m_r2_op[16] = { "add", "sub", "neg", "cmp", "and", "or", "not", "xor", "lw", "lh", "pop", "lbu", "sw", "sh", "push", "sb" }; +const char *const score7_disassembler::m_i1_op[8] = { "addi", "", "cmpi", "", "andi", "ori", "ldi", "" }; +const char *const score7_disassembler::m_i2_op[8] = { "addis", "", "cmpis", "", "andis", "oris", "ldis", "" }; +const char *const score7_disassembler::m_ls_op[8] = { "lw", "lh", "lhu", "lb", "sw", "sh", "lbu", "sb" }; +const char *const score7_disassembler::m_i1a_op[8] = { "addei", "slli", "sdbbp", "srli", "bitclr", "bitset", "bittst", "" }; +const char *const score7_disassembler::m_i1b_op[8] = { "lwp", "lhp", "", "lbup", "swp", "shp", "", "sbp" }; +const char *const score7_disassembler::m_cr_op[2] = { "mtcr", "mfcr" }; +int32_t score7_disassembler::sign_extend(uint32_t data, uint8_t len) +{ + data &= (1 << len) - 1; + uint32_t sign = 1 << (len - 1); + return (data ^ sign) - sign; +} -void score7_cpu_device::disasm32(std::ostream &stream, offs_t pc, uint32_t opcode) +void score7_disassembler::disasm32(std::ostream &stream, offs_t pc, uint32_t opcode) { switch((opcode >> 25) & 0x1f) { @@ -178,7 +184,7 @@ void score7_cpu_device::disasm32(std::ostream &stream, offs_t pc, uint32_t opcod } } -void score7_cpu_device::disasm16(std::ostream &stream, offs_t pc, uint16_t opcode) +void score7_disassembler::disasm16(std::ostream &stream, offs_t pc, uint16_t opcode) { switch((opcode >> 12) & 0x07) { @@ -252,7 +258,7 @@ void score7_cpu_device::disasm16(std::ostream &stream, offs_t pc, uint16_t opcod } } -offs_t score7_cpu_device::disasm(std::ostream &stream, offs_t pc, uint32_t opcode) +offs_t score7_disassembler::disasm(std::ostream &stream, offs_t pc, uint32_t opcode) { uint8_t p = (pc & 0x02) ? 0 : (((opcode>>30) & 2) | ((opcode>>15) & 1)); @@ -278,13 +284,16 @@ offs_t score7_cpu_device::disasm(std::ostream &stream, offs_t pc, uint32_t opcod //------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t score7_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +offs_t score7_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - uint32_t opcode = oprom[0] | (oprom[1] << 8) | (oprom[2] << 16) | (oprom[3] << 24); + return disasm(stream, pc, opcodes.r32(pc)); +} - return disasm(stream, pc, opcode); +u32 score7_disassembler::opcode_alignment() const +{ + return 2; } diff --git a/src/devices/cpu/score/scoredsm.h b/src/devices/cpu/score/scoredsm.h new file mode 100644 index 00000000000..a9f870d2b42 --- /dev/null +++ b/src/devices/cpu/score/scoredsm.h @@ -0,0 +1,43 @@ +// license:BSD-3-Clause +// copyright-holders:Sandro Ronco +/****************************************************************************** + + Sunplus Technology S+core disassembler + +******************************************************************************/ + +#ifndef MAME_CPU_SCORE_SCOREDSM_H +#define MAME_CPU_SCORE_SCOREDSM_H + +#pragma once + +class score7_disassembler : public util::disasm_interface +{ +public: + score7_disassembler() = default; + virtual ~score7_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + // mnemonics + static const char *const m_cond[16]; + static const char *const m_tcs[4]; + static const char *const m_rix1_op[8]; + static const char *const m_rix2_op[8]; + static const char *const m_r2_op[16]; + static const char *const m_i1_op[8]; + static const char *const m_i2_op[8]; + static const char *const m_ls_op[8]; + static const char *const m_i1a_op[8]; + static const char *const m_i1b_op[8]; + static const char *const m_cr_op[2]; + + int32_t sign_extend(uint32_t data, uint8_t len); + offs_t disasm(std::ostream &stream, offs_t pc, uint32_t opcode); + void disasm32(std::ostream &stream, offs_t pc, uint32_t opcode); + void disasm16(std::ostream &stream, offs_t pc, uint16_t opcode); +}; + +#endif diff --git a/src/devices/cpu/scudsp/scudsp.cpp b/src/devices/cpu/scudsp/scudsp.cpp index 5c2d64e6082..5a1b7c0eb99 100644 --- a/src/devices/cpu/scudsp/scudsp.cpp +++ b/src/devices/cpu/scudsp/scudsp.cpp @@ -92,6 +92,7 @@ #include "emu.h" #include "scudsp.h" +#include "scudspdasm.h" #include "debugger.h" @@ -1050,8 +1051,7 @@ void scudsp_cpu_device::state_string_export(const device_state_entry &entry, std } -offs_t scudsp_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *scudsp_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( scudsp ); - return CPU_DISASSEMBLE_NAME(scudsp)(this, stream, pc, oprom, opram, options); + return new scudsp_disassembler; } diff --git a/src/devices/cpu/scudsp/scudsp.h b/src/devices/cpu/scudsp/scudsp.h index f0ae8df33de..866a98f7df0 100644 --- a/src/devices/cpu/scudsp/scudsp.h +++ b/src/devices/cpu/scudsp/scudsp.h @@ -88,9 +88,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 4; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; devcb_write_line m_out_irq_cb; devcb_read16 m_in_dma_cb; @@ -157,7 +155,4 @@ private: DECLARE_DEVICE_TYPE(SCUDSP, scudsp_cpu_device) - -CPU_DISASSEMBLE( scudsp ); - #endif // MAME_CPU_SCUDSP_SCUDSP_H diff --git a/src/devices/cpu/scudsp/scudspdasm.cpp b/src/devices/cpu/scudsp/scudspdasm.cpp index 584073aceca..a29712a0448 100644 --- a/src/devices/cpu/scudsp/scudspdasm.cpp +++ b/src/devices/cpu/scudsp/scudspdasm.cpp @@ -1,10 +1,9 @@ // license:BSD-3-Clause // copyright-holders:Angelo Salese, Mariusz Wojcieszek #include "emu.h" -#include "debugger.h" -#include "scudsp.h" +#include "scudspdasm.h" -static const char *const ALU_Commands[] = +const char *const scudsp_disassembler::ALU_Commands[] = { " ", /* 0000 */ "AND ", /* 0001 */ @@ -24,7 +23,7 @@ static const char *const ALU_Commands[] = "RL8 ", /* 1111 */ }; -static const char *const X_Commands[] = +const char *const scudsp_disassembler::X_Commands[] = { "", /* 000 */ "", /* 001 */ /* NOP? check instruction @ 0x0B */ @@ -33,7 +32,7 @@ static const char *const X_Commands[] = "MOV %s,X", /* 100 */ }; -static const char *const Y_Commands[] = +const char *const scudsp_disassembler::Y_Commands[] = { "", /* 000 */ "CLR A", /* 001 */ @@ -42,7 +41,7 @@ static const char *const Y_Commands[] = "MOV %s,Y", /* 100 */ }; -static const char *const D1_Commands[] = +const char *const scudsp_disassembler::D1_Commands[] = { "", /* 00 */ "MOV %I8,%d", /* 01 */ @@ -50,7 +49,7 @@ static const char *const D1_Commands[] = "MOV %S,%d", /* 11 */ }; -static const char *const SourceMemory[] = +const char *const scudsp_disassembler::SourceMemory[] = { "M0", /* 000 */ "M1", /* 001 */ @@ -62,7 +61,7 @@ static const char *const SourceMemory[] = "MC3", /* 111 */ }; -static const char *const SourceMemory2[] = +const char *const scudsp_disassembler::SourceMemory2[] = { "M0", /* 0000 */ "M1", /* 0001 */ @@ -82,7 +81,7 @@ static const char *const SourceMemory2[] = "???", /* 1111 */ }; -static const char *const DestMemory[] = +const char *const scudsp_disassembler::DestMemory[] = { "MC0", /* 0000 */ "MC1", /* 0001 */ @@ -102,7 +101,7 @@ static const char *const DestMemory[] = "CT3", /* 1111 */ }; -static const char *const DestDMAMemory[] = +const char *const scudsp_disassembler::DestDMAMemory[] = { "M0", /* 000 */ "M1", /* 001 */ @@ -114,19 +113,19 @@ static const char *const DestDMAMemory[] = "???", /* 111 */ }; -static const char *const MVI_Command[] = +const char *const scudsp_disassembler::MVI_Command[] = { "MVI %I,%d", /* 0 */ "MVI %I,%d,%f", /* 1 */ }; -static const char *const JMP_Command[] = +const char *const scudsp_disassembler::JMP_Command[] = { "JMP %IA", "JMP %f,%IA", }; -static const char *const DMA_Command[] = +const char *const scudsp_disassembler::DMA_Command[] = { "DMA%H%A D0,%M,%I", "DMA%H%A %s,D0,%I", @@ -135,8 +134,9 @@ static const char *const DMA_Command[] = }; -static void scudsp_dasm_prefix( const char* format, char* buffer, uint32_t *data ) +std::string scudsp_disassembler::scudsp_dasm_prefix( const char* format, uint32_t *data ) { + std::string result; for ( ; *format; format++ ) { if ( *format == '%' ) @@ -145,104 +145,82 @@ static void scudsp_dasm_prefix( const char* format, char* buffer, uint32_t *data { case 'H': if ( *data ) - { - strcpy( buffer, "H" ); - } - else - { - *buffer = 0; - } + result += 'H'; break; case 'A': if ( *data == 0 ) - { - strcpy( buffer, "0" ); - } - else if ( *data == 1 ) - { - *buffer = 0; - } - else - { - sprintf( buffer, "%d", 1 << (*data - 1) ); - } + result += '0'; + else if ( *data != 1 ) + result += util::string_format("%d", 1 << (*data - 1) ); break; case 's': - strcpy( buffer, SourceMemory[ *data & 0x7 ] ); + result += SourceMemory[ *data & 0x7 ]; break; case 'd': - strcpy( buffer, DestMemory[ *data & 0xf ] ); + result += DestMemory[ *data & 0xf ]; break; case 'S': - strcpy( buffer, SourceMemory2[ *data & 0xf ] ); + result += SourceMemory2[ *data & 0xf ]; break; case 'I': ++format; if ( *format == '8' ) - { - sprintf( buffer, "#$%x", *data ); - } + result += util::string_format("#$%x", *data ); else if ( *format == 'A' ) - { - sprintf( buffer, "$%X", *data ); - } + result += util::string_format("$%X", *data ); else { --format; - sprintf( buffer, "#$%X", *data ); + result += util::string_format("#$%X", *data ); } break; case 'f': if ( !(*data & 0x20) ) - { - strcpy( buffer, "N" ); - buffer++; - } + result += 'N'; switch( *data & 0xf ) { case 0x3: - strcpy( buffer, "ZS" ); + result += "ZS"; break; case 0x2: - strcpy( buffer, "S" ); + result += 'S'; break; case 0x4: - strcpy( buffer, "C" ); + result += 'C'; break; case 0x8: - strcpy( buffer, "T0" ); + result += "T0"; break; case 0x1: - strcpy( buffer, "Z" ); + result += 'Z'; break; default: - strcpy( buffer, "?" ); + result += '?'; break; } break; case 'M': - strcpy( buffer, DestDMAMemory[ *data ] ); + result += DestDMAMemory[ *data ]; break; } data++; - buffer += strlen( buffer ); } else - { - *buffer++ = *format; - } + result += *format; } - *buffer = 0; + return result; } +u32 scudsp_disassembler::opcode_alignment() const +{ + return 1; +} -CPU_DISASSEMBLE(scudsp) +offs_t scudsp_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - uint32_t op = oprom[0]<<24|oprom[1]<<16|oprom[2]<<8|oprom[3]<<0; + uint32_t op = opcodes.r32(pc); unsigned size = 1; -// const char *sym, *sym2; - char temp_buffer[64]; uint32_t data[4]; switch( op >> 30 ) @@ -260,31 +238,15 @@ CPU_DISASSEMBLE(scudsp) /* X-Bus */ data[0] = (op & 0x700000) >> 20; if ( op & 0x2000000 ) - { - scudsp_dasm_prefix( X_Commands[ 4 ], temp_buffer, data ); - } - else - { - *temp_buffer = 0; - } - util::stream_format(stream, "%s", temp_buffer); + stream << scudsp_dasm_prefix( X_Commands[ 4 ], data ); - scudsp_dasm_prefix( X_Commands[ (op & 0x1800000) >> 23 ], temp_buffer, data ); - util::stream_format(stream, "%s", temp_buffer); + stream << scudsp_dasm_prefix( X_Commands[ (op & 0x1800000) >> 23 ], data ); data[0] = (op & 0x1C000 ) >> 14 ; if ( op & 0x80000 ) - { - scudsp_dasm_prefix( Y_Commands[4], temp_buffer, data ); - } - else - { - *temp_buffer = 0; - } - util::stream_format(stream, "%s", temp_buffer); + stream << scudsp_dasm_prefix( Y_Commands[4], data ); - scudsp_dasm_prefix( Y_Commands[ (op & 0x60000) >> 17 ], temp_buffer, data ); - util::stream_format(stream, "%s", temp_buffer); + stream << scudsp_dasm_prefix( Y_Commands[ (op & 0x60000) >> 17 ], data ); /* D1-Bus */ switch( (op & 0x3000) >> 12 ) @@ -299,8 +261,7 @@ CPU_DISASSEMBLE(scudsp) break; } - scudsp_dasm_prefix( D1_Commands[ (op & 0x3000) >> 12 ], temp_buffer, data); - util::stream_format(stream, "%s", temp_buffer); + stream << scudsp_dasm_prefix( D1_Commands[ (op & 0x3000) >> 12 ], data); break; case 2: if ( (op & 0x2000000) ) @@ -308,15 +269,13 @@ CPU_DISASSEMBLE(scudsp) data[0] = op & 0x7FFFF; data[1] = (op & 0x3C000000) >> 26; data[2] = (op & 0x3F80000 ) >> 19; - scudsp_dasm_prefix( MVI_Command[1], temp_buffer, data); /* TODO: bad mem*/ - stream << temp_buffer; + stream << scudsp_dasm_prefix( MVI_Command[1], data); /* TODO: bad mem*/ } else { data[0] = op & 0x1FFFFFF; data[1] = (op & 0x3C000000) >> 26; - scudsp_dasm_prefix( MVI_Command[0], temp_buffer, data ); /* TODO: bad mem*/ - stream << temp_buffer; + stream << scudsp_dasm_prefix( MVI_Command[0], data ); /* TODO: bad mem*/ } break; case 3: @@ -327,22 +286,19 @@ CPU_DISASSEMBLE(scudsp) data[1] = (op & 0x38000) >> 15; /* A */ data[2] = (op & 0x700) >> 8; /* Mem */ data[3] = (op & 0xff); - scudsp_dasm_prefix( DMA_Command[(op & 0x3000) >> 12], temp_buffer, data ); - stream << temp_buffer; + stream << scudsp_dasm_prefix( DMA_Command[(op & 0x3000) >> 12], data ); break; case 1: if ( op & 0x3F80000 ) { data[0] = (op & 0x3F80000) >> 19; data[1] = op & 0xff; - scudsp_dasm_prefix( JMP_Command[1], temp_buffer, data ); - stream << temp_buffer; + stream << scudsp_dasm_prefix( JMP_Command[1], data ); } else { data[0] = op & 0xff; - scudsp_dasm_prefix( JMP_Command[0], temp_buffer, data ); - stream << temp_buffer; + stream << scudsp_dasm_prefix( JMP_Command[0], data ); } break; case 2: diff --git a/src/devices/cpu/scudsp/scudspdasm.h b/src/devices/cpu/scudsp/scudspdasm.h new file mode 100644 index 00000000000..7f86d0366aa --- /dev/null +++ b/src/devices/cpu/scudsp/scudspdasm.h @@ -0,0 +1,33 @@ +// license:BSD-3-Clause +// copyright-holders:Angelo Salese, Mariusz Wojcieszek + +#ifndef MAME_CPU_SCUDSP_SCUDSPDASM_H +#define MAME_CPU_SCUDSP_SCUDSPDASM_H + +#pragma once + +class scudsp_disassembler : public util::disasm_interface +{ +public: + scudsp_disassembler() = default; + virtual ~scudsp_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *const ALU_Commands[]; + static const char *const X_Commands[]; + static const char *const Y_Commands[]; + static const char *const D1_Commands[]; + static const char *const SourceMemory[]; + static const char *const SourceMemory2[]; + static const char *const DestMemory[]; + static const char *const DestDMAMemory[]; + static const char *const MVI_Command[]; + static const char *const JMP_Command[]; + static const char *const DMA_Command[]; + std::string scudsp_dasm_prefix( const char* format, uint32_t *data ); +}; + +#endif diff --git a/src/devices/cpu/se3208/se3208.cpp b/src/devices/cpu/se3208/se3208.cpp index 45bb8a30c45..a1a8b0ba546 100644 --- a/src/devices/cpu/se3208/se3208.cpp +++ b/src/devices/cpu/se3208/se3208.cpp @@ -2,6 +2,7 @@ // copyright-holders:ElSemi #include "emu.h" #include "se3208.h" +#include "se3208dis.h" #include "debugger.h" @@ -1847,8 +1848,7 @@ void se3208_device::execute_set_input( int line, int state ) m_IRQ=state; } -offs_t se3208_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *se3208_device::create_disassembler() { - extern CPU_DISASSEMBLE( se3208 ); - return CPU_DISASSEMBLE_NAME(se3208)(this, stream, pc, oprom, opram, options); + return new se3208_disassembler; } diff --git a/src/devices/cpu/se3208/se3208.h b/src/devices/cpu/se3208/se3208.h index 69cddd0175b..e08804f26df 100644 --- a/src/devices/cpu/se3208/se3208.h +++ b/src/devices/cpu/se3208/se3208.h @@ -39,9 +39,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 2; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/se3208/se3208dis.cpp b/src/devices/cpu/se3208/se3208dis.cpp index ca7d3761d61..0ce74883cae 100644 --- a/src/devices/cpu/se3208/se3208dis.cpp +++ b/src/devices/cpu/se3208/se3208dis.cpp @@ -1,22 +1,13 @@ // license:BSD-3-Clause // copyright-holders:ElSemi #include "emu.h" -#include "debugger.h" -#include "se3208.h" - - -static struct -{ - uint32_t PC; - uint32_t SR; - uint32_t ER; -} Context; +#include "se3208dis.h" #define FLAG_E 0x0800 -#define CLRFLAG(f) Context.SR&=~(f); -#define SETFLAG(f) Context.SR|=(f); -#define TESTFLAG(f) (Context.SR&(f)) +#define CLRFLAG(f) SR&=~(f); +#define SETFLAG(f) SR|=(f); +#define TESTFLAG(f) (SR&(f)) #define EXTRACT(val,sbit,ebit) (((val)>>sbit)&((1<<((ebit-sbit)+1))-1)) #define SEX8(val) ((val&0x80)?(val|0xFFFFFF00):(val&0xFF)) @@ -25,8 +16,8 @@ static struct #define ZEX16(val) ((val)&0xFFFF) #define SEX(bits,val) ((val)&(1<<(bits-1))?((val)|(~((1<*DecodeOp(Opcode))(Opcode, stream)) | SUPPORTED; } diff --git a/src/devices/cpu/se3208/se3208dis.h b/src/devices/cpu/se3208/se3208dis.h new file mode 100644 index 00000000000..ffe66c602c7 --- /dev/null +++ b/src/devices/cpu/se3208/se3208dis.h @@ -0,0 +1,103 @@ +// license:BSD-3-Clause +// copyright-holders:ElSemi + +#ifndef MAME_CPU_SE3208_SE3208DIS_H +#define MAME_CPU_SE3208_SE3208DIS_H + +#pragma once + +class se3208_disassembler : public util::disasm_interface +{ +public: + se3208_disassembler() = default; + virtual ~se3208_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + typedef uint32_t (se3208_disassembler::*_OP)(uint16_t Opcode, std::ostream &stream); + + uint32_t INVALIDOP(uint16_t Opcode, std::ostream &stream); + uint32_t LDB(uint16_t Opcode, std::ostream &stream); + uint32_t STB(uint16_t Opcode, std::ostream &stream); + uint32_t LDS(uint16_t Opcode, std::ostream &stream); + uint32_t STS(uint16_t Opcode, std::ostream &stream); + uint32_t LD(uint16_t Opcode, std::ostream &stream); + uint32_t ST(uint16_t Opcode, std::ostream &stream); + uint32_t LDBU(uint16_t Opcode, std::ostream &stream); + uint32_t LDSU(uint16_t Opcode, std::ostream &stream); + uint32_t LERI(uint16_t Opcode, std::ostream &stream); + uint32_t LDSP(uint16_t Opcode, std::ostream &stream); + uint32_t STSP(uint16_t Opcode, std::ostream &stream); + uint32_t PUSH(uint16_t Opcode, std::ostream &stream); + uint32_t POP(uint16_t Opcode, std::ostream &stream); + uint32_t LEATOSP(uint16_t Opcode, std::ostream &stream); + uint32_t LEAFROMSP(uint16_t Opcode, std::ostream &stream); + uint32_t LEASPTOSP(uint16_t Opcode, std::ostream &stream); + uint32_t MOV(uint16_t Opcode, std::ostream &stream); + uint32_t LDI(uint16_t Opcode, std::ostream &stream); + uint32_t LDBSP(uint16_t Opcode, std::ostream &stream); + uint32_t STBSP(uint16_t Opcode, std::ostream &stream); + uint32_t LDSSP(uint16_t Opcode, std::ostream &stream); + uint32_t STSSP(uint16_t Opcode, std::ostream &stream); + uint32_t LDBUSP(uint16_t Opcode, std::ostream &stream); + uint32_t LDSUSP(uint16_t Opcode, std::ostream &stream); + uint32_t ADDI(uint16_t Opcode, std::ostream &stream); + uint32_t SUBI(uint16_t Opcode, std::ostream &stream); + uint32_t ADCI(uint16_t Opcode, std::ostream &stream); + uint32_t SBCI(uint16_t Opcode, std::ostream &stream); + uint32_t ANDI(uint16_t Opcode, std::ostream &stream); + uint32_t ORI(uint16_t Opcode, std::ostream &stream); + uint32_t XORI(uint16_t Opcode, std::ostream &stream); + uint32_t CMPI(uint16_t Opcode, std::ostream &stream); + uint32_t TSTI(uint16_t Opcode, std::ostream &stream); + uint32_t ADD(uint16_t Opcode, std::ostream &stream); + uint32_t SUB(uint16_t Opcode, std::ostream &stream); + uint32_t ADC(uint16_t Opcode, std::ostream &stream); + uint32_t SBC(uint16_t Opcode, std::ostream &stream); + uint32_t AND(uint16_t Opcode, std::ostream &stream); + uint32_t OR(uint16_t Opcode, std::ostream &stream); + uint32_t XOR(uint16_t Opcode, std::ostream &stream); + uint32_t CMP(uint16_t Opcode, std::ostream &stream); + uint32_t TST(uint16_t Opcode, std::ostream &stream); + uint32_t MULS(uint16_t Opcode, std::ostream &stream); + uint32_t NEG(uint16_t Opcode, std::ostream &stream); + uint32_t CALL(uint16_t Opcode, std::ostream &stream); + uint32_t JV(uint16_t Opcode, std::ostream &stream); + uint32_t JNV(uint16_t Opcode, std::ostream &stream); + uint32_t JC(uint16_t Opcode, std::ostream &stream); + uint32_t JNC(uint16_t Opcode, std::ostream &stream); + uint32_t JP(uint16_t Opcode, std::ostream &stream); + uint32_t JM(uint16_t Opcode, std::ostream &stream); + uint32_t JNZ(uint16_t Opcode, std::ostream &stream); + uint32_t JZ(uint16_t Opcode, std::ostream &stream); + uint32_t JGE(uint16_t Opcode, std::ostream &stream); + uint32_t JLE(uint16_t Opcode, std::ostream &stream); + uint32_t JHI(uint16_t Opcode, std::ostream &stream); + uint32_t JLS(uint16_t Opcode, std::ostream &stream); + uint32_t JGT(uint16_t Opcode, std::ostream &stream); + uint32_t JLT(uint16_t Opcode, std::ostream &stream); + uint32_t JMP(uint16_t Opcode, std::ostream &stream); + uint32_t JR(uint16_t Opcode, std::ostream &stream); + uint32_t CALLR(uint16_t Opcode, std::ostream &stream); + uint32_t ASR(uint16_t Opcode, std::ostream &stream); + uint32_t LSR(uint16_t Opcode, std::ostream &stream); + uint32_t ASL(uint16_t Opcode, std::ostream &stream); + uint32_t EXTB(uint16_t Opcode, std::ostream &stream); + uint32_t EXTS(uint16_t Opcode, std::ostream &stream); + uint32_t SET(uint16_t Opcode, std::ostream &stream); + uint32_t CLR(uint16_t Opcode, std::ostream &stream); + uint32_t SWI(uint16_t Opcode, std::ostream &stream); + uint32_t HALT(uint16_t Opcode, std::ostream &stream); + uint32_t MVTC(uint16_t Opcode, std::ostream &stream); + uint32_t MVFC(uint16_t Opcode, std::ostream &stream); + + _OP DecodeOp(uint16_t Opcode); + + uint32_t PC; + uint32_t SR; + uint32_t ER; +}; + +#endif diff --git a/src/devices/cpu/sh/sh.cpp b/src/devices/cpu/sh/sh.cpp index cfdd919227b..f89f260c322 100644 --- a/src/devices/cpu/sh/sh.cpp +++ b/src/devices/cpu/sh/sh.cpp @@ -3,6 +3,7 @@ #include "emu.h" #include "sh.h" +#include "sh_dasm.h" void sh_common_execution::device_start() { @@ -2229,7 +2230,10 @@ void sh_common_execution::log_opcode_desc(drcuml_state *drcuml, const opcode_des if (desclist->flags & OPFLAG_VIRTUAL_NOOP) stream << ""; else - DasmSH2(stream, desclist->pc, desclist->opptr.w[0]); + { + sh_disassembler sh2d(false); + sh2d.dasm_one(stream, desclist->pc, desclist->opptr.w[0]); + } } else stream << "???"; @@ -2259,8 +2263,9 @@ void sh_common_execution::log_add_disasm_comment(drcuml_block *block, uint32_t p { if (m_drcuml->logging()) { + sh_disassembler sh2d(false); std::ostringstream stream; - DasmSH2(stream, pc, op); + sh2d.dasm_one(stream, pc, op); block->append_comment("%08X: %s", pc, stream.str().c_str()); } } diff --git a/src/devices/cpu/sh/sh.h b/src/devices/cpu/sh/sh.h index 87b6ca9d311..0ba8a4b6b26 100644 --- a/src/devices/cpu/sh/sh.h +++ b/src/devices/cpu/sh/sh.h @@ -99,8 +99,6 @@ #define R32(reg) m_regmap[reg] -extern unsigned DasmSH2(std::ostream &stream, unsigned pc, uint16_t opcode); - enum { SH4_PC = 1, SH_SR, SH4_PR, SH4_GBR, SH4_VBR, SH4_DBR, SH4_MACH, SH4_MACL, diff --git a/src/devices/cpu/sh/sh2.cpp b/src/devices/cpu/sh/sh2.cpp index 9a9b28b306d..4678ad5ffca 100644 --- a/src/devices/cpu/sh/sh2.cpp +++ b/src/devices/cpu/sh/sh2.cpp @@ -95,7 +95,7 @@ #include "emu.h" #include "sh2.h" #include "sh2comn.h" - +#include "sh_dasm.h" #include "debugger.h" //#define VERBOSE 1 @@ -200,13 +200,11 @@ device_memory_interface::space_config_vector sh2_device::memory_space_config() c }; } -offs_t sh2_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *sh2_device::create_disassembler() { - extern CPU_DISASSEMBLE( sh2 ); - return CPU_DISASSEMBLE_NAME( sh2 )(this, stream, pc, oprom, opram, options); + return new sh_disassembler(false); } - uint8_t sh2_device::RB(offs_t A) { if((A & 0xf0000000) == 0 || (A & 0xf0000000) == 0x20000000) diff --git a/src/devices/cpu/sh/sh2.h b/src/devices/cpu/sh/sh2.h index 3ea520b74ea..7c15b82d5e4 100644 --- a/src/devices/cpu/sh/sh2.h +++ b/src/devices/cpu/sh/sh2.h @@ -109,9 +109,8 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 2; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; + address_space *m_decrypted_program; private: diff --git a/src/devices/cpu/sh/sh4.cpp b/src/devices/cpu/sh/sh4.cpp index fc30fa2c8e8..881a1ddee94 100644 --- a/src/devices/cpu/sh/sh4.cpp +++ b/src/devices/cpu/sh/sh4.cpp @@ -30,14 +30,10 @@ #include "sh4comn.h" #include "sh3comn.h" #include "sh4tmu.h" - +#include "sh_dasm.h" #include "debugger.h" -CPU_DISASSEMBLE( sh4 ); -CPU_DISASSEMBLE( sh4be ); - - DEFINE_DEVICE_TYPE(SH3LE, sh3_device, "sh3le", "SH-3 (little)") DEFINE_DEVICE_TYPE(SH3BE, sh3be_device, "sh3be", "SH-3 (big)") DEFINE_DEVICE_TYPE(SH4LE, sh4_device, "sh4le", "SH-4 (little)") @@ -144,27 +140,9 @@ sh4be_device::sh4be_device(const machine_config &mconfig, const char *tag, devic } -offs_t sh34_base_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) -{ - extern CPU_DISASSEMBLE( sh4 ); - - return CPU_DISASSEMBLE_NAME(sh4)(this, stream, pc, oprom, opram, options); -} - - -offs_t sh3be_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *sh34_base_device::create_disassembler() { - extern CPU_DISASSEMBLE( sh4be ); - - return CPU_DISASSEMBLE_NAME(sh4be)(this, stream, pc, oprom, opram, options); -} - - -offs_t sh4be_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) -{ - extern CPU_DISASSEMBLE( sh4be ); - - return CPU_DISASSEMBLE_NAME(sh4be)(this, stream, pc, oprom, opram, options); + return new sh_disassembler(true); } diff --git a/src/devices/cpu/sh/sh4.h b/src/devices/cpu/sh/sh4.h index 22a52c0c0f3..6f3c37e862a 100644 --- a/src/devices/cpu/sh/sh4.h +++ b/src/devices/cpu/sh/sh4.h @@ -316,9 +316,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 2; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; address_space_config m_program_config; address_space_config m_io_config; @@ -810,7 +808,6 @@ public: protected: virtual void execute_run() override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; }; @@ -839,7 +836,6 @@ public: protected: virtual void execute_run() override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; }; class sh4_frontend : public sh_frontend diff --git a/src/devices/cpu/sh/sh_dasm.cpp b/src/devices/cpu/sh/sh_dasm.cpp index b52c6969f65..a2e6dd67496 100644 --- a/src/devices/cpu/sh/sh_dasm.cpp +++ b/src/devices/cpu/sh/sh_dasm.cpp @@ -1,13 +1,14 @@ // license:BSD-3-Clause // copyright-holders:Juergen Buchmueller, R. Belmont #include "emu.h" -#include "debugger.h" -#include "sh2.h" +#include "sh_dasm.h" #define SIGNX8(x) (((int32_t)(x) << 24) >> 24) #define SIGNX12(x) (((int32_t)(x) << 20) >> 20) +#define Rn ((opcode>>8)&15) +#define Rm ((opcode>>4)&15) -static const char *const regname[16] = { +const char *const sh_disassembler::regname[16] = { "R0", "R1", "R2", "R3", "R4", "R5", "R6", "R7", "R8", "R9", "R10","R11","R12","R13","R14", // The old SH2 dasm used 'SP' here, the old SH4 used 'R15' @@ -15,7 +16,7 @@ static const char *const regname[16] = { "R15" }; -static uint32_t op0000(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op0000(std::ostream &stream, uint32_t pc, uint16_t opcode) { uint32_t flags = 0; switch(opcode & 0x3f) @@ -37,7 +38,7 @@ static uint32_t op0000(std::ostream &stream, uint32_t pc, uint16_t opcode) break; case 0x0B: stream << "RTS"; - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; case 0x12: util::stream_format(stream, "STS GBR,%s", regname[Rn]); @@ -71,7 +72,7 @@ static uint32_t op0000(std::ostream &stream, uint32_t pc, uint16_t opcode) break; case 0x2B: stream << "RTE"; - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; default: switch(opcode & 15) @@ -129,13 +130,13 @@ static uint32_t op0000(std::ostream &stream, uint32_t pc, uint16_t opcode) return flags; } -static uint32_t op0001(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op0001(std::ostream &stream, uint32_t pc, uint16_t opcode) { util::stream_format(stream, "MOV.L %s,@($%02X,%s)", regname[Rm], (opcode & 15) * 4, regname[Rn]); return 0; } -static uint32_t op0010(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op0010(std::ostream &stream, uint32_t pc, uint16_t opcode) { switch (opcode & 15) { @@ -191,7 +192,7 @@ static uint32_t op0010(std::ostream &stream, uint32_t pc, uint16_t opcode) return 0; } -static uint32_t op0011(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op0011(std::ostream &stream, uint32_t pc, uint16_t opcode) { switch (opcode & 15) { @@ -247,7 +248,7 @@ static uint32_t op0011(std::ostream &stream, uint32_t pc, uint16_t opcode) return 0; } -static uint32_t op0100(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op0100(std::ostream &stream, uint32_t pc, uint16_t opcode) { uint32_t flags = 0; switch(opcode & 0x3F) @@ -287,7 +288,7 @@ static uint32_t op0100(std::ostream &stream, uint32_t pc, uint16_t opcode) break; case 0x0b: util::stream_format(stream, "JSR %s", regname[Rn]); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; case 0x0e: util::stream_format(stream, "LDC %s,SR", regname[Rn]); @@ -376,13 +377,13 @@ static uint32_t op0100(std::ostream &stream, uint32_t pc, uint16_t opcode) return flags; } -static uint32_t op0101(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op0101(std::ostream &stream, uint32_t pc, uint16_t opcode) { util::stream_format(stream, "MOV.L @($%02X,%s),%s", (opcode & 15) * 4, regname[Rm], regname[Rn]); return 0; } -static uint32_t op0110(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op0110(std::ostream &stream, uint32_t pc, uint16_t opcode) { switch(opcode & 0xF) @@ -439,13 +440,13 @@ static uint32_t op0110(std::ostream &stream, uint32_t pc, uint16_t opcode) return 0; } -static uint32_t op0111(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op0111(std::ostream &stream, uint32_t pc, uint16_t opcode) { util::stream_format(stream, "ADD #$%02X,%s", opcode & 0xff, regname[Rn]); return 0; } -static uint32_t op1000(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op1000(std::ostream &stream, uint32_t pc, uint16_t opcode) { switch((opcode >> 8) & 15) { @@ -482,25 +483,25 @@ static uint32_t op1000(std::ostream &stream, uint32_t pc, uint16_t opcode) return 0; } -static uint32_t op1001(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op1001(std::ostream &stream, uint32_t pc, uint16_t opcode) { util::stream_format(stream, "MOV.W @($%04X,PC),%s [%08X]", (opcode & 0xff) * 2, regname[Rn], pc+((opcode & 0xff) * 2)+2); return 0; } -static uint32_t op1010(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op1010(std::ostream &stream, uint32_t pc, uint16_t opcode) { util::stream_format(stream, "BRA $%08X", SIGNX12(opcode & 0xfff) * 2 + pc + 2); return 0; } -static uint32_t op1011(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op1011(std::ostream &stream, uint32_t pc, uint16_t opcode) { util::stream_format(stream, "BSR $%08X", SIGNX12(opcode & 0xfff) * 2 + pc + 2); - return DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + return STEP_OVER | step_over_extra(1); } -static uint32_t op1100(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op1100(std::ostream &stream, uint32_t pc, uint16_t opcode) { uint32_t flags = 0; switch((opcode >> 8) & 15) @@ -516,7 +517,7 @@ static uint32_t op1100(std::ostream &stream, uint32_t pc, uint16_t opcode) break; case 3: util::stream_format(stream, "TRAPA #$%02X", opcode & 0xff); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case 4: util::stream_format(stream, "MOV.B @($%02X,GBR),R0", opcode & 0xff); @@ -558,61 +559,29 @@ static uint32_t op1100(std::ostream &stream, uint32_t pc, uint16_t opcode) return flags; } -static uint32_t op1101(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op1101(std::ostream &stream, uint32_t pc, uint16_t opcode) { util::stream_format(stream, "MOV.L @($%04X,PC),%s [%08X]", (opcode & 0xff) * 4, regname[Rn], ((pc + 2) & ~3) + (opcode & 0xff) * 4); return 0; } -static uint32_t op1110(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op1110(std::ostream &stream, uint32_t pc, uint16_t opcode) { util::stream_format(stream, "MOV #$%02X,%s", (opcode & 0xff), regname[Rn]); return 0; } -static uint32_t op1111(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op1111(std::ostream &stream, uint32_t pc, uint16_t opcode) { util::stream_format(stream, "unknown $%04X", opcode); return 0; } -unsigned DasmSH2(std::ostream &stream, unsigned pc, uint16_t opcode) -{ - uint32_t flags; - - pc += 2; - - switch ((opcode >> 12) & 15) - { - case 0: flags = op0000(stream, pc, opcode); break; - case 1: flags = op0001(stream, pc, opcode); break; - case 2: flags = op0010(stream, pc, opcode); break; - case 3: flags = op0011(stream, pc, opcode); break; - case 4: flags = op0100(stream, pc, opcode); break; - case 5: flags = op0101(stream, pc, opcode); break; - case 6: flags = op0110(stream, pc, opcode); break; - case 7: flags = op0111(stream, pc, opcode); break; - case 8: flags = op1000(stream, pc, opcode); break; - case 9: flags = op1001(stream, pc, opcode); break; - case 10: flags = op1010(stream, pc, opcode); break; - case 11: flags = op1011(stream, pc, opcode); break; - case 12: flags = op1100(stream, pc, opcode); break; - case 13: flags = op1101(stream, pc, opcode); break; - case 14: flags = op1110(stream, pc, opcode); break; - default: flags = op1111(stream, pc, opcode); break; - } - return 2 | flags | DASMFLAG_SUPPORTED; -} - -CPU_DISASSEMBLE(sh2) -{ - return DasmSH2(stream, pc, (oprom[0] << 8) | oprom[1]); -} /* SH4 specifics */ -static uint32_t op0000_sh34(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op0000_sh34(std::ostream &stream, uint32_t pc, uint16_t opcode) { uint32_t flags = 0; switch (opcode & 0xF) @@ -739,14 +708,14 @@ static uint32_t op0000_sh34(std::ostream &stream, uint32_t pc, uint16_t opcode) { case 0x00: stream << "RTS"; - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; case 0x10: stream << "SLEEP"; break; case 0x20: stream << "RTE"; - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; } break; @@ -767,7 +736,7 @@ static uint32_t op0000_sh34(std::ostream &stream, uint32_t pc, uint16_t opcode) } -static uint32_t op0100_sh34(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op0100_sh34(std::ostream &stream, uint32_t pc, uint16_t opcode) { uint32_t flags = 0; switch (opcode & 0xF) @@ -978,7 +947,7 @@ static uint32_t op0100_sh34(std::ostream &stream, uint32_t pc, uint16_t opcode) { case 0x00: util::stream_format(stream, "JSR %s", regname[Rn]); - flags = DASMFLAG_STEP_OVER | DASMFLAG_STEP_OVER_EXTRA(1); + flags = STEP_OVER | step_over_extra(1); break; case 0x10: util::stream_format(stream, "TAS %s", regname[Rn]); @@ -1026,7 +995,7 @@ static uint32_t op0100_sh34(std::ostream &stream, uint32_t pc, uint16_t opcode) } -static uint32_t op1111_sh34(std::ostream &stream, uint32_t pc, uint16_t opcode) +uint32_t sh_disassembler::op1111_sh34(std::ostream &stream, uint32_t pc, uint16_t opcode) { switch (opcode & 0xf) { @@ -1149,40 +1118,73 @@ static uint32_t op1111_sh34(std::ostream &stream, uint32_t pc, uint16_t opcode) return 0; } -unsigned DasmSH4(std::ostream &stream, unsigned pc, uint16_t opcode) +offs_t sh_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + u16 opcode = opcodes.r16(pc); + return dasm_one(stream, pc, opcode); +} + +offs_t sh_disassembler::dasm_one(std::ostream &stream, offs_t pc, u16 opcode) { uint32_t flags; pc += 2; - switch ((opcode >> 12) & 15) + if (m_is_sh34) { - case 0: flags = op0000_sh34(stream, pc, opcode); break; - case 1: flags = op0001(stream, pc, opcode); break; - case 2: flags = op0010(stream, pc, opcode); break; - case 3: flags = op0011(stream, pc, opcode); break; - case 4: flags = op0100_sh34(stream, pc, opcode); break; - case 5: flags = op0101(stream, pc, opcode); break; - case 6: flags = op0110(stream, pc, opcode); break; - case 7: flags = op0111(stream, pc, opcode); break; - case 8: flags = op1000(stream, pc, opcode); break; - case 9: flags = op1001(stream, pc, opcode); break; - case 10: flags = op1010(stream, pc, opcode); break; - case 11: flags = op1011(stream, pc, opcode); break; - case 12: flags = op1100(stream, pc, opcode); break; - case 13: flags = op1101(stream, pc, opcode); break; - case 14: flags = op1110(stream, pc, opcode); break; - default: flags = op1111_sh34(stream, pc, opcode); break; + switch ((opcode >> 12) & 15) + { + case 0: flags = op0000_sh34(stream, pc, opcode); break; + case 1: flags = op0001(stream, pc, opcode); break; + case 2: flags = op0010(stream, pc, opcode); break; + case 3: flags = op0011(stream, pc, opcode); break; + case 4: flags = op0100_sh34(stream, pc, opcode); break; + case 5: flags = op0101(stream, pc, opcode); break; + case 6: flags = op0110(stream, pc, opcode); break; + case 7: flags = op0111(stream, pc, opcode); break; + case 8: flags = op1000(stream, pc, opcode); break; + case 9: flags = op1001(stream, pc, opcode); break; + case 10: flags = op1010(stream, pc, opcode); break; + case 11: flags = op1011(stream, pc, opcode); break; + case 12: flags = op1100(stream, pc, opcode); break; + case 13: flags = op1101(stream, pc, opcode); break; + case 14: flags = op1110(stream, pc, opcode); break; + default: flags = op1111_sh34(stream, pc, opcode); break; + } } - return 2 | flags | DASMFLAG_SUPPORTED; + else + { + switch ((opcode >> 12) & 15) + { + case 0: flags = op0000(stream, pc, opcode); break; + case 1: flags = op0001(stream, pc, opcode); break; + case 2: flags = op0010(stream, pc, opcode); break; + case 3: flags = op0011(stream, pc, opcode); break; + case 4: flags = op0100(stream, pc, opcode); break; + case 5: flags = op0101(stream, pc, opcode); break; + case 6: flags = op0110(stream, pc, opcode); break; + case 7: flags = op0111(stream, pc, opcode); break; + case 8: flags = op1000(stream, pc, opcode); break; + case 9: flags = op1001(stream, pc, opcode); break; + case 10: flags = op1010(stream, pc, opcode); break; + case 11: flags = op1011(stream, pc, opcode); break; + case 12: flags = op1100(stream, pc, opcode); break; + case 13: flags = op1101(stream, pc, opcode); break; + case 14: flags = op1110(stream, pc, opcode); break; + default: flags = op1111(stream, pc, opcode); break; + } + } + + return 2 | flags | SUPPORTED; } -CPU_DISASSEMBLE(sh4) + +u32 sh_disassembler::opcode_alignment() const { - return DasmSH4(stream, pc, (oprom[1] << 8) | oprom[0]); + return 2; } -CPU_DISASSEMBLE(sh4be) +sh_disassembler::sh_disassembler(bool is_sh34) : m_is_sh34(is_sh34) { - return DasmSH4(stream, pc, (oprom[0] << 8) | oprom[1]); } + diff --git a/src/devices/cpu/sh/sh_dasm.h b/src/devices/cpu/sh/sh_dasm.h new file mode 100644 index 00000000000..52d6b2eb723 --- /dev/null +++ b/src/devices/cpu/sh/sh_dasm.h @@ -0,0 +1,45 @@ +// license:BSD-3-Clause +// copyright-holders:Juergen Buchmueller, R. Belmont + +#ifndef MAME_CPU_SH_SHDASM_H +#define MAME_CPU_SH_SHDASM_H + +#pragma once + +class sh_disassembler : public util::disasm_interface +{ +public: + sh_disassembler(bool is_sh34); + virtual ~sh_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + + offs_t dasm_one(std::ostream &stream, offs_t pc, u16 opcode); + +private: + static const char *const regname[16]; + uint32_t op0000(std::ostream &stream, uint32_t pc, uint16_t opcode); + uint32_t op0001(std::ostream &stream, uint32_t pc, uint16_t opcode); + uint32_t op0010(std::ostream &stream, uint32_t pc, uint16_t opcode); + uint32_t op0011(std::ostream &stream, uint32_t pc, uint16_t opcode); + uint32_t op0100(std::ostream &stream, uint32_t pc, uint16_t opcode); + uint32_t op0101(std::ostream &stream, uint32_t pc, uint16_t opcode); + uint32_t op0110(std::ostream &stream, uint32_t pc, uint16_t opcode); + uint32_t op0111(std::ostream &stream, uint32_t pc, uint16_t opcode); + uint32_t op1000(std::ostream &stream, uint32_t pc, uint16_t opcode); + uint32_t op1001(std::ostream &stream, uint32_t pc, uint16_t opcode); + uint32_t op1010(std::ostream &stream, uint32_t pc, uint16_t opcode); + uint32_t op1011(std::ostream &stream, uint32_t pc, uint16_t opcode); + uint32_t op1100(std::ostream &stream, uint32_t pc, uint16_t opcode); + uint32_t op1101(std::ostream &stream, uint32_t pc, uint16_t opcode); + uint32_t op1110(std::ostream &stream, uint32_t pc, uint16_t opcode); + uint32_t op1111(std::ostream &stream, uint32_t pc, uint16_t opcode); + uint32_t op0000_sh34(std::ostream &stream, uint32_t pc, uint16_t opcode); + uint32_t op0100_sh34(std::ostream &stream, uint32_t pc, uint16_t opcode); + uint32_t op1111_sh34(std::ostream &stream, uint32_t pc, uint16_t opcode); + + bool m_is_sh34; +}; + +#endif diff --git a/src/devices/cpu/sharc/sharc.cpp b/src/devices/cpu/sharc/sharc.cpp index b8f3b104eb0..bbcd194b47b 100644 --- a/src/devices/cpu/sharc/sharc.cpp +++ b/src/devices/cpu/sharc/sharc.cpp @@ -8,6 +8,7 @@ #include "emu.h" #include "sharc.h" #include "sharcfe.h" +#include "sharcdsm.h" #include "debugger.h" @@ -96,10 +97,9 @@ device_memory_interface::space_config_vector adsp21062_device::memory_space_conf }; } -offs_t adsp21062_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *adsp21062_device::create_disassembler() { - extern CPU_DISASSEMBLE( sharc ); - return CPU_DISASSEMBLE_NAME(sharc)(this, stream, pc, oprom, opram, options); + return new sharc_disassembler; } void adsp21062_device::enable_recompiler() diff --git a/src/devices/cpu/sharc/sharc.h b/src/devices/cpu/sharc/sharc.h index 806b3053ee4..d4a56e1d525 100644 --- a/src/devices/cpu/sharc/sharc.h +++ b/src/devices/cpu/sharc/sharc.h @@ -220,10 +220,7 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - static constexpr uint32_t OPCODE_BYTES = 8; // actually 6, but emulation requires padding to 64 bits - virtual uint32_t disasm_min_opcode_bytes() const override { return OPCODE_BYTES; } - virtual uint32_t disasm_max_opcode_bytes() const override { return OPCODE_BYTES; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: struct alignas(16) SHARC_DAG diff --git a/src/devices/cpu/sharc/sharcdsm.cpp b/src/devices/cpu/sharc/sharcdsm.cpp index 7d570c13e87..ebab8add599 100644 --- a/src/devices/cpu/sharc/sharcdsm.cpp +++ b/src/devices/cpu/sharc/sharcdsm.cpp @@ -9,8 +9,76 @@ #include "emu.h" #include "sharcdsm.h" -static uint32_t (* sharcdasm_table[256])(uint32_t, uint64_t); -static int dasm_table_built = 0; +const char sharc_disassembler::ureg_names[256][16] = +{ + "R0", "R1", "R2", "R3", "R4", "R5", "R6", "R7", + "R8", "R9", "R10", "R11", "R12", "R13", "R14", "R15", + "I0", "I1", "I2", "I3", "I4", "I5", "I6", "I7", + "I8", "I9", "I10", "I11", "I12", "I13", "I14", "I15", + "M0", "M1", "M2", "M3", "M4", "M5", "M6", "M7", + "M8", "M9", "M10", "M11", "M12", "M13", "M14", "M15", + "L0", "L1", "L2", "L3", "L4", "L5", "L6", "L7", + "L8", "L9", "L10", "L11", "L12", "L13", "L14", "L15", + "B0", "B1", "B2", "B3", "B4", "B5", "B6", "B7", + "B8", "B9", "B10", "B11", "B12", "B13", "B14", "B15", + "???", "???", "???", "???", "???", "???", "???", "???", + "???", "???", "???", "???", "???", "???", "???", "???", + "FADDR", "DADDR", "???", "PC", "PCSTK", "PCSTKP", "LADDR", "CURLCNTR", + "LCNTR", "???", "???", "???", "???", "???", "???", "???", + "USTAT1", "USTAT2", "???", "???", "???", "???", "???", "???", + "???", "IRPTL", "MODE2", "MODE1", "ASTAT", "IMASK", "STKY", "IMASKP", + "???", "???", "???", "???", "???", "???", "???", "???", + "???", "???", "???", "???", "???", "???", "???", "???", + "???", "???", "???", "???", "???", "???", "???", "???", + "???", "???", "???", "???", "???", "???", "???", "???", + "???", "???", "???", "???", "???", "???", "???", "???", + "???", "???", "???", "???", "???", "???", "???", "???", + "???", "???", "???", "???", "???", "???", "???", "???", + "???", "???", "???", "???", "???", "???", "???", "???", + "???", "???", "???", "???", "???", "???", "???", "???", + "???", "???", "???", "???", "???", "???", "???", "???", + "???", "???", "???", "???", "???", "???", "???", "???", + "???", "???", "???", "PX", "PX1", "PX2", "TPERIOD", "TCOUNT", + "???", "???", "???", "???", "???", "???", "???", "???", + "???", "???", "???", "???", "???", "???", "???", "???", + "???", "???", "???", "???", "???", "???", "???", "???", + "???", "???", "???", "???", "???", "???", "???", "???" +}; + +const char sharc_disassembler::bopnames[8][8] = +{ + "SET", "CLEAR", "TOGGLE", "???", "TEST", "XOR", "???", "???" +}; + +const char sharc_disassembler::condition_codes_if[32][32] = +{ + "EQ", "LT", "LE", "AC", + "AV", "MV", "MS", "SV", + "SZ", "FLAG0_IN", "FLAG1_IN", "FLAG2_IN", + "FLAG3_IN", "TF", "BM", "NOT LCE", + "NE", "GE", "GT", "NOT AC", + "NOT AV", "NOT MV", "NOT MS", "NOT SV", + "NOT SZ", "NOT FLAG0_IN", "NOT FLAG1_IN", "NOT FLAG2_IN", + "NOT FLAG3_IN", "NOT TF", "NBM", "" +}; + +const char sharc_disassembler::condition_codes_do[32][32] = +{ + "EQ", "LT", "LE", "AC", + "AV", "MV", "MS", "SV", + "SZ", "FLAG0_IN", "FLAG1_IN", "FLAG2_IN", + "FLAG3_IN", "TF", "BM", "LCE", + "NE", "GE", "GT", "NOT AC", + "NOT AV", "NOT MV", "NOT MS", "NOT SV", + "NOT SZ", "NOT FLAG0_IN", "NOT FLAG1_IN", "NOT FLAG2_IN", + "NOT FLAG3_IN", "NOT TF", "NBM", "FOREVER" +}; + +const char sharc_disassembler::mr_regnames[16][8] = +{ + "MR0F", "MR1F", "MR2F", "MR0B", "MR1B", "MR2B", "???", "???", + "???", "???", "???", "???", "???", "???", "???", "???" +}; #define GET_UREG(x) (ureg_names[x]) #define GET_SREG(x) (GET_UREG(0x70 | (x & 0xf))) @@ -28,19 +96,7 @@ static int dasm_table_built = 0; #define SIGN_EXTEND24(x) ((x & 0x800000) ? (0xff000000 | x) : x) -static char *output; -static void ATTR_PRINTF(1,2) print(const char *fmt, ...) -{ - va_list vl; - - va_start(vl, fmt); - output += vsprintf(output, fmt, vl); - va_end(vl); -} - - - -static void compute(uint32_t opcode) +void sharc_disassembler::compute(std::ostream &stream, uint32_t opcode) { int op = (opcode >> 12) & 0xff; int cu = (opcode >> 20) & 0x3; @@ -61,41 +117,41 @@ static void compute(uint32_t opcode) switch(multiop) { - case 0x04: print("R%d = R%d * R%d (SSFR), R%d = R%d + R%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x05: print("R%d = R%d * R%d (SSFR), R%d = R%d - R%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x06: print("R%d = R%d * R%d (SSFR), R%d = (R%d + R%d)/2", rm, rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x08: print("MRF = MRF + R%d * R%d (SSF), R%d = R%d + R%d", rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x09: print("MRF = MRF + R%d * R%d (SSF), R%d = R%d - R%d", rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x0a: print("MRF = MRF + R%d * R%d (SSF), R%d = (R%d + R%d)/2", rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x0c: print("R%d = MRF + R%d * R%d (SSFR), R%d = R%d + R%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x0d: print("R%d = MRF + R%d * R%d (SSFR), R%d = R%d - R%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x0e: print("R%d = MRF + R%d * R%d (SSFR), R%d = (R%d + R%d)/2", rm, rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x10: print("MRF = MRF - R%d * R%d (SSF), R%d = R%d + R%d", rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x11: print("MRF = MRF - R%d * R%d (SSF), R%d = R%d - R%d", rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x12: print("MRF = MRF - R%d * R%d (SSF), R%d = (R%d + R%d)/2", rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x14: print("R%d = MRF - R%d * R%d (SSFR), R%d = R%d + R%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x15: print("R%d = MRF - R%d * R%d (SSFR), R%d = R%d - R%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x16: print("R%d = MRF - R%d * R%d (SSFR), R%d = (R%d + R%d)/2", rm, rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x18: print("F%d = F%d * F%d, F%d = F%d + F%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x19: print("F%d = F%d * F%d, F%d = F%d - F%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x1a: print("F%d = F%d * F%d, F%d = FLOAT F%d BY F%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x1b: print("F%d = F%d * F%d, F%d = FIX F%d BY F%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x1c: print("F%d = F%d * F%d, F%d = (F%d + F%d)/2", rm, rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x1d: print("F%d = F%d * F%d, F%d = ABS F%d", rm, rxm, rym+4, ra, rxa+8); break; - case 0x1e: print("F%d = F%d * F%d, F%d = MAX(F%d, F%d)", rm, rxm, rym+4, ra, rxa+8, rya+12); break; - case 0x1f: print("F%d = F%d * F%d, F%d = MIN(F%d, F%d)", rm, rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x04: util::stream_format(stream, "R%d = R%d * R%d (SSFR), R%d = R%d + R%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x05: util::stream_format(stream, "R%d = R%d * R%d (SSFR), R%d = R%d - R%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x06: util::stream_format(stream, "R%d = R%d * R%d (SSFR), R%d = (R%d + R%d)/2", rm, rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x08: util::stream_format(stream, "MRF = MRF + R%d * R%d (SSF), R%d = R%d + R%d", rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x09: util::stream_format(stream, "MRF = MRF + R%d * R%d (SSF), R%d = R%d - R%d", rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x0a: util::stream_format(stream, "MRF = MRF + R%d * R%d (SSF), R%d = (R%d + R%d)/2", rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x0c: util::stream_format(stream, "R%d = MRF + R%d * R%d (SSFR), R%d = R%d + R%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x0d: util::stream_format(stream, "R%d = MRF + R%d * R%d (SSFR), R%d = R%d - R%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x0e: util::stream_format(stream, "R%d = MRF + R%d * R%d (SSFR), R%d = (R%d + R%d)/2", rm, rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x10: util::stream_format(stream, "MRF = MRF - R%d * R%d (SSF), R%d = R%d + R%d", rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x11: util::stream_format(stream, "MRF = MRF - R%d * R%d (SSF), R%d = R%d - R%d", rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x12: util::stream_format(stream, "MRF = MRF - R%d * R%d (SSF), R%d = (R%d + R%d)/2", rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x14: util::stream_format(stream, "R%d = MRF - R%d * R%d (SSFR), R%d = R%d + R%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x15: util::stream_format(stream, "R%d = MRF - R%d * R%d (SSFR), R%d = R%d - R%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x16: util::stream_format(stream, "R%d = MRF - R%d * R%d (SSFR), R%d = (R%d + R%d)/2", rm, rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x18: util::stream_format(stream, "F%d = F%d * F%d, F%d = F%d + F%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x19: util::stream_format(stream, "F%d = F%d * F%d, F%d = F%d - F%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x1a: util::stream_format(stream, "F%d = F%d * F%d, F%d = FLOAT F%d BY F%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x1b: util::stream_format(stream, "F%d = F%d * F%d, F%d = FIX F%d BY F%d", rm, rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x1c: util::stream_format(stream, "F%d = F%d * F%d, F%d = (F%d + F%d)/2", rm, rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x1d: util::stream_format(stream, "F%d = F%d * F%d, F%d = ABS F%d", rm, rxm, rym+4, ra, rxa+8); break; + case 0x1e: util::stream_format(stream, "F%d = F%d * F%d, F%d = MAX(F%d, F%d)", rm, rxm, rym+4, ra, rxa+8, rya+12); break; + case 0x1f: util::stream_format(stream, "F%d = F%d * F%d, F%d = MIN(F%d, F%d)", rm, rxm, rym+4, ra, rxa+8, rya+12); break; case 0x20: case 0x21: case 0x22: case 0x23: case 0x24: case 0x25: case 0x26: case 0x27: case 0x28: case 0x29: case 0x2a: case 0x2b: case 0x2c: case 0x2d: case 0x2e: case 0x2f: { - print("R%d = R%d * R%d (SSFR), R%d = R%d + R%d, R%d = R%d - R%d", rm, rxm, rym+4, ra, rxa+8, rya+12, (opcode >> 16) & 0xf, rxa+8, rya+12); + util::stream_format(stream, "R%d = R%d * R%d (SSFR), R%d = R%d + R%d, R%d = R%d - R%d", rm, rxm, rym+4, ra, rxa+8, rya+12, (opcode >> 16) & 0xf, rxa+8, rya+12); break; } case 0x30: case 0x31: case 0x32: case 0x33: case 0x34: case 0x35: case 0x36: case 0x37: case 0x38: case 0x39: case 0x3a: case 0x3b: case 0x3c: case 0x3d: case 0x3e: case 0x3f: { - print("F%d = F%d * F%d, F%d = F%d + F%d, F%d = F%d - F%d", rm, rxm, rym+4, ra, rxa+8, rya+12, (opcode >> 16) & 0xf, rxa+8, rya+12); + util::stream_format(stream, "F%d = F%d * F%d, F%d = F%d + F%d, F%d = F%d - F%d", rm, rxm, rym+4, ra, rxa+8, rya+12, (opcode >> 16) & 0xf, rxa+8, rya+12); break; } @@ -103,20 +159,20 @@ static void compute(uint32_t opcode) { int rk = (opcode >> 8) & 0xf; int ai = (opcode >> 12) & 0xf; - print("R%d = %s", rk, mr_regnames[ai]); + util::stream_format(stream, "R%d = %s", rk, mr_regnames[ai]); break; } case 0x01: { int rk = (opcode >> 8) & 0xf; int ai = (opcode >> 12) & 0xf; - print("%s = R%d", mr_regnames[ai], rk); + util::stream_format(stream, "%s = R%d", mr_regnames[ai], rk); break; } default: { - print("??? (COMPUTE, MULTIOP)"); + util::stream_format(stream, "??? (COMPUTE, MULTIOP)"); break; } } @@ -133,68 +189,68 @@ static void compute(uint32_t opcode) switch(op) { /* Fixed-point */ - case 0x01: print("R%d = R%d + R%d", rn, rx, ry); break; - case 0x02: print("R%d = R%d - R%d", rn, rx, ry); break; - case 0x05: print("R%d = R%d + R%d + CI", rn, rx, ry); break; - case 0x06: print("R%d = R%d - R%d + CI - 1", rn, rx, ry); break; - case 0x09: print("R%d = (R%d + R%d)/2", rn, rx, ry); break; - case 0x0a: print("COMP(R%d, R%d)", rx, ry); break; - case 0x25: print("R%d = R%d + CI", rn, rx); break; - case 0x26: print("R%d = R%d + CI - 1", rn, rx); break; - case 0x29: print("R%d = R%d + 1", rn, rx); break; - case 0x2a: print("R%d = R%d - 1", rn, rx); break; - case 0x22: print("R%d = -R%d", rn, rx); break; - case 0x30: print("R%d = ABS R%d", rn, rx); break; - case 0x21: print("R%d = PASS R%d", rn, rx); break; - case 0x40: print("R%d = R%d AND R%d", rn, rx, ry); break; - case 0x41: print("R%d = R%d OR R%d", rn, rx, ry); break; - case 0x42: print("R%d = R%d XOR R%d", rn, rx, ry); break; - case 0x43: print("R%d = NOT R%d", rn, rx); break; - case 0x61: print("R%d = MIN(R%d, R%d)", rn, rx, ry); break; - case 0x62: print("R%d = MAX(R%d, R%d)", rn, rx, ry); break; - case 0x63: print("R%d = CLIP R%d BY R%d", rn, rx, ry); break; + case 0x01: util::stream_format(stream, "R%d = R%d + R%d", rn, rx, ry); break; + case 0x02: util::stream_format(stream, "R%d = R%d - R%d", rn, rx, ry); break; + case 0x05: util::stream_format(stream, "R%d = R%d + R%d + CI", rn, rx, ry); break; + case 0x06: util::stream_format(stream, "R%d = R%d - R%d + CI - 1", rn, rx, ry); break; + case 0x09: util::stream_format(stream, "R%d = (R%d + R%d)/2", rn, rx, ry); break; + case 0x0a: util::stream_format(stream, "COMP(R%d, R%d)", rx, ry); break; + case 0x25: util::stream_format(stream, "R%d = R%d + CI", rn, rx); break; + case 0x26: util::stream_format(stream, "R%d = R%d + CI - 1", rn, rx); break; + case 0x29: util::stream_format(stream, "R%d = R%d + 1", rn, rx); break; + case 0x2a: util::stream_format(stream, "R%d = R%d - 1", rn, rx); break; + case 0x22: util::stream_format(stream, "R%d = -R%d", rn, rx); break; + case 0x30: util::stream_format(stream, "R%d = ABS R%d", rn, rx); break; + case 0x21: util::stream_format(stream, "R%d = PASS R%d", rn, rx); break; + case 0x40: util::stream_format(stream, "R%d = R%d AND R%d", rn, rx, ry); break; + case 0x41: util::stream_format(stream, "R%d = R%d OR R%d", rn, rx, ry); break; + case 0x42: util::stream_format(stream, "R%d = R%d XOR R%d", rn, rx, ry); break; + case 0x43: util::stream_format(stream, "R%d = NOT R%d", rn, rx); break; + case 0x61: util::stream_format(stream, "R%d = MIN(R%d, R%d)", rn, rx, ry); break; + case 0x62: util::stream_format(stream, "R%d = MAX(R%d, R%d)", rn, rx, ry); break; + case 0x63: util::stream_format(stream, "R%d = CLIP R%d BY R%d", rn, rx, ry); break; /* Floating-point */ - case 0x81: print("F%d = F%d + F%d", rn, rx, ry); break; - case 0x82: print("F%d = F%d - F%d", rn, rx, ry); break; - case 0x91: print("F%d = ABS(F%d + F%d)", rn, rx, ry); break; - case 0x92: print("F%d = ABS(F%d - F%d)", rn, rx, ry); break; - case 0x89: print("F%d = (F%d + F%d)/2", rn, rx, ry); break; - case 0x8a: print("COMP(F%d, F%d)", rx, ry); break; - case 0xa2: print("F%d = -F%d", rn, rx); break; - case 0xb0: print("F%d = ABS F%d", rn, rx); break; - case 0xa1: print("F%d = PASS F%d", rn, rx); break; - case 0xa5: print("F%d = RND R%d", rn, rx); break; - case 0xbd: print("F%d = SCALB F%d BY R%d", rn, rx, ry); break; - case 0xad: print("R%d = MANT F%d", rn, rx); break; - case 0xc1: print("R%d = LOGB F%d", rn, rx); break; - case 0xd9: print("R%d = FIX F%d BY R%d", rn, rx, ry); break; - case 0xc9: print("R%d = FIX F%d", rn, rx); break; - case 0xdd: print("R%d = TRUNC F%d BY R%d", rn, rx, ry); break; - case 0xcd: print("R%d = TRUNC F%d", rn, rx); break; - case 0xda: print("F%d = FLOAT R%d BY R%d", rn, rx, ry); break; - case 0xca: print("F%d = FLOAT R%d", rn, rx); break; - case 0xc4: print("F%d = RECIPS F%d", rn, rx); break; - case 0xc5: print("F%d = RSQRTS F%d", rn, rx); break; - case 0xe0: print("F%d = F%d COPYSIGN F%d", rn, rx, ry); break; - case 0xe1: print("F%d = MIN(F%d, F%d)", rn, rx, ry); break; - case 0xe2: print("F%d = MAX(F%d, F%d)", rn, rx, ry); break; - case 0xe3: print("F%d = CLIP F%d BY F%d", rn, rx, ry); break; + case 0x81: util::stream_format(stream, "F%d = F%d + F%d", rn, rx, ry); break; + case 0x82: util::stream_format(stream, "F%d = F%d - F%d", rn, rx, ry); break; + case 0x91: util::stream_format(stream, "F%d = ABS(F%d + F%d)", rn, rx, ry); break; + case 0x92: util::stream_format(stream, "F%d = ABS(F%d - F%d)", rn, rx, ry); break; + case 0x89: util::stream_format(stream, "F%d = (F%d + F%d)/2", rn, rx, ry); break; + case 0x8a: util::stream_format(stream, "COMP(F%d, F%d)", rx, ry); break; + case 0xa2: util::stream_format(stream, "F%d = -F%d", rn, rx); break; + case 0xb0: util::stream_format(stream, "F%d = ABS F%d", rn, rx); break; + case 0xa1: util::stream_format(stream, "F%d = PASS F%d", rn, rx); break; + case 0xa5: util::stream_format(stream, "F%d = RND R%d", rn, rx); break; + case 0xbd: util::stream_format(stream, "F%d = SCALB F%d BY R%d", rn, rx, ry); break; + case 0xad: util::stream_format(stream, "R%d = MANT F%d", rn, rx); break; + case 0xc1: util::stream_format(stream, "R%d = LOGB F%d", rn, rx); break; + case 0xd9: util::stream_format(stream, "R%d = FIX F%d BY R%d", rn, rx, ry); break; + case 0xc9: util::stream_format(stream, "R%d = FIX F%d", rn, rx); break; + case 0xdd: util::stream_format(stream, "R%d = TRUNC F%d BY R%d", rn, rx, ry); break; + case 0xcd: util::stream_format(stream, "R%d = TRUNC F%d", rn, rx); break; + case 0xda: util::stream_format(stream, "F%d = FLOAT R%d BY R%d", rn, rx, ry); break; + case 0xca: util::stream_format(stream, "F%d = FLOAT R%d", rn, rx); break; + case 0xc4: util::stream_format(stream, "F%d = RECIPS F%d", rn, rx); break; + case 0xc5: util::stream_format(stream, "F%d = RSQRTS F%d", rn, rx); break; + case 0xe0: util::stream_format(stream, "F%d = F%d COPYSIGN F%d", rn, rx, ry); break; + case 0xe1: util::stream_format(stream, "F%d = MIN(F%d, F%d)", rn, rx, ry); break; + case 0xe2: util::stream_format(stream, "F%d = MAX(F%d, F%d)", rn, rx, ry); break; + case 0xe3: util::stream_format(stream, "F%d = CLIP F%d BY F%d", rn, rx, ry); break; case 0x70: case 0x71: case 0x72: case 0x73: case 0x74: case 0x75: case 0x76: case 0x77: case 0x78: case 0x79: case 0x7a: case 0x7b: case 0x7c: case 0x7d: case 0x7e: case 0x7f: { - print("R%d = R%d + R%d, R%d = R%d - R%d", ra, rx, ry, rs, rx, ry); + util::stream_format(stream, "R%d = R%d + R%d, R%d = R%d - R%d", ra, rx, ry, rs, rx, ry); break; } case 0xf0: case 0xf1: case 0xf2: case 0xf3: case 0xf4: case 0xf5: case 0xf6: case 0xf7: case 0xf8: case 0xf9: case 0xfa: case 0xfb: case 0xfc: case 0xfd: case 0xfe: case 0xff: { - print("F%d = F%d + F%d, F%d = F%d - F%d", ra, rx, ry, rs, rx, ry); + util::stream_format(stream, "F%d = F%d + F%d, F%d = F%d - F%d", ra, rx, ry, rs, rx, ry); break; } default: { - print("??? (COMPUTE, ALU)"); + util::stream_format(stream, "??? (COMPUTE, ALU)"); break; } } @@ -207,44 +263,44 @@ static void compute(uint32_t opcode) case 1: { if( op == 0x30 ) { - print("F%d = F%d * F%d", rn, rx, ry); + util::stream_format(stream, "F%d = F%d * F%d", rn, rx, ry); return; } switch((op >> 1) & 0x3) { case 0: - case 1: print("R%d = ", rn); break; - case 2: print("MRF = "); break; - case 3: print("MRB = "); break; + case 1: util::stream_format(stream, "R%d = ", rn); break; + case 2: util::stream_format(stream, "MRF = "); break; + case 3: util::stream_format(stream, "MRB = "); break; } switch((op >> 6) & 0x3) { case 0: switch((op >> 4) & 0x3) { - case 0: print("SAT %s", (op & 0x2) ? "MRB" : "MRF"); break; + case 0: util::stream_format(stream, "SAT %s", (op & 0x2) ? "MRB" : "MRF"); break; case 1: if (op & 0x8) { - print("RND %s", (op & 0x2) ? "MRB" : "MRF"); + util::stream_format(stream, "RND %s", (op & 0x2) ? "MRB" : "MRF"); } else { - print("0"); + util::stream_format(stream, "0"); } break; } break; case 1: - print("R%d * R%d", rx, ry); break; + util::stream_format(stream, "R%d * R%d", rx, ry); break; case 2: - print("%s +(R%d * R%d)", (op & 0x2) ? "MRB" : "MRF", rx, ry); break; + util::stream_format(stream, "%s +(R%d * R%d)", (op & 0x2) ? "MRB" : "MRF", rx, ry); break; case 3: - print("%s -(R%d * R%d)", (op & 0x2) ? "MRB" : "MRF", rx, ry); break; + util::stream_format(stream, "%s -(R%d * R%d)", (op & 0x2) ? "MRB" : "MRF", rx, ry); break; } break; } @@ -256,50 +312,50 @@ static void compute(uint32_t opcode) { switch(op) { - case 0x00: print("R%d = LSHIFT R%d BY R%d", rn, rx, ry); break; - case 0x20: print("R%d = R%d OR LSHIFT R%d BY R%d", rn, rn, rx, ry); break; - case 0x04: print("R%d = ASHIFT R%d BY R%d", rn, rx, ry); break; - case 0x24: print("R%d = R%d OR ASHIFT R%d BY R%d", rn, rn, rx, ry); break; - case 0x08: print("R%d = ROT R%d BY R%d", rn, rx, ry); break; - case 0xc4: print("R%d = BCLR R%d BY R%d", rn, rx, ry); break; - case 0xc0: print("R%d = BSET R%d BY R%d", rn, rx, ry); break; - case 0xc8: print("R%d = BTGL R%d BY R%d", rn, rx, ry); break; - case 0xcc: print("BTST R%d BY R%d", rx, ry); break; - case 0x44: print("R%d = FDEP R%d BY R%d", rn, rx, ry); break; - case 0x64: print("R%d = R%d OR FDEP R%d BY R%d", rn, rn, rx, ry); break; - case 0x4c: print("R%d = FDEP R%d BY R%d (SE)", rn, rx, ry); break; - case 0x6c: print("R%d = R%d OR FDEP R%d BY R%d (SE)", rn, rn, rx, ry); break; - case 0x40: print("R%d = FEXT R%d BY R%d", rn, rx, ry); break; - case 0x48: print("R%d = FEXT R%d BY R%d (SE)", rn, rx, ry); break; - case 0x80: print("R%d = EXP R%d", rn, rx); break; - case 0x84: print("R%d = EXP R%d (EX)", rn, rx); break; - case 0x88: print("R%d = LEFTZ R%d", rn, rx); break; - case 0x8c: print("R%d = LEFTO R%d", rn, rx); break; - case 0x90: print("R%d = FPACK F%d", rn, rx); break; - case 0x94: print("F%d = FUNPACK R%d", rn, rx); break; - default: print("??? (COMPUTE, SHIFT)"); break; + case 0x00: util::stream_format(stream, "R%d = LSHIFT R%d BY R%d", rn, rx, ry); break; + case 0x20: util::stream_format(stream, "R%d = R%d OR LSHIFT R%d BY R%d", rn, rn, rx, ry); break; + case 0x04: util::stream_format(stream, "R%d = ASHIFT R%d BY R%d", rn, rx, ry); break; + case 0x24: util::stream_format(stream, "R%d = R%d OR ASHIFT R%d BY R%d", rn, rn, rx, ry); break; + case 0x08: util::stream_format(stream, "R%d = ROT R%d BY R%d", rn, rx, ry); break; + case 0xc4: util::stream_format(stream, "R%d = BCLR R%d BY R%d", rn, rx, ry); break; + case 0xc0: util::stream_format(stream, "R%d = BSET R%d BY R%d", rn, rx, ry); break; + case 0xc8: util::stream_format(stream, "R%d = BTGL R%d BY R%d", rn, rx, ry); break; + case 0xcc: util::stream_format(stream, "BTST R%d BY R%d", rx, ry); break; + case 0x44: util::stream_format(stream, "R%d = FDEP R%d BY R%d", rn, rx, ry); break; + case 0x64: util::stream_format(stream, "R%d = R%d OR FDEP R%d BY R%d", rn, rn, rx, ry); break; + case 0x4c: util::stream_format(stream, "R%d = FDEP R%d BY R%d (SE)", rn, rx, ry); break; + case 0x6c: util::stream_format(stream, "R%d = R%d OR FDEP R%d BY R%d (SE)", rn, rn, rx, ry); break; + case 0x40: util::stream_format(stream, "R%d = FEXT R%d BY R%d", rn, rx, ry); break; + case 0x48: util::stream_format(stream, "R%d = FEXT R%d BY R%d (SE)", rn, rx, ry); break; + case 0x80: util::stream_format(stream, "R%d = EXP R%d", rn, rx); break; + case 0x84: util::stream_format(stream, "R%d = EXP R%d (EX)", rn, rx); break; + case 0x88: util::stream_format(stream, "R%d = LEFTZ R%d", rn, rx); break; + case 0x8c: util::stream_format(stream, "R%d = LEFTO R%d", rn, rx); break; + case 0x90: util::stream_format(stream, "R%d = FPACK F%d", rn, rx); break; + case 0x94: util::stream_format(stream, "F%d = FUNPACK R%d", rn, rx); break; + default: util::stream_format(stream, "??? (COMPUTE, SHIFT)"); break; } break; } default: { - print("??? (COMPUTE)"); + util::stream_format(stream, "??? (COMPUTE)"); break; } } } } -static void get_if_condition(int cond) +void sharc_disassembler::get_if_condition(std::ostream &stream, int cond) { if (cond != 31) { - print("IF %s, ", condition_codes_if[cond]); + util::stream_format(stream, "IF %s, ", condition_codes_if[cond]); } } -static void pm_dm_ureg(int g, int d, int i, int m, int ureg, int update) +void sharc_disassembler::pm_dm_ureg(std::ostream &stream, int g, int d, int i, int m, int ureg, int update) { if (update) // post-modify { @@ -307,22 +363,22 @@ static void pm_dm_ureg(int g, int d, int i, int m, int ureg, int update) { if (g) { - print("PM(%s, %s) = %s", GET_DAG2_I(i), GET_DAG2_M(m), GET_UREG(ureg)); + util::stream_format(stream, "PM(%s, %s) = %s", GET_DAG2_I(i), GET_DAG2_M(m), GET_UREG(ureg)); } else { - print("DM(%s, %s) = %s", GET_DAG1_I(i), GET_DAG1_M(m), GET_UREG(ureg)); + util::stream_format(stream, "DM(%s, %s) = %s", GET_DAG1_I(i), GET_DAG1_M(m), GET_UREG(ureg)); } } else { if (g) { - print("%s = PM(%s, %s)", GET_UREG(ureg), GET_DAG2_I(i), GET_DAG2_M(m)); + util::stream_format(stream, "%s = PM(%s, %s)", GET_UREG(ureg), GET_DAG2_I(i), GET_DAG2_M(m)); } else { - print("%s = DM(%s, %s)", GET_UREG(ureg), GET_DAG1_I(i), GET_DAG1_M(m)); + util::stream_format(stream, "%s = DM(%s, %s)", GET_UREG(ureg), GET_DAG1_I(i), GET_DAG1_M(m)); } } @@ -333,28 +389,28 @@ static void pm_dm_ureg(int g, int d, int i, int m, int ureg, int update) { if (g) { - print("PM(%s, %s) = %s", GET_DAG2_M(m), GET_DAG2_I(i), GET_UREG(ureg)); + util::stream_format(stream, "PM(%s, %s) = %s", GET_DAG2_M(m), GET_DAG2_I(i), GET_UREG(ureg)); } else { - print("DM(%s, %s) = %s", GET_DAG1_M(m), GET_DAG1_I(i), GET_UREG(ureg)); + util::stream_format(stream, "DM(%s, %s) = %s", GET_DAG1_M(m), GET_DAG1_I(i), GET_UREG(ureg)); } } else { if (g) { - print("%s = PM(%s, %s)", GET_UREG(ureg), GET_DAG2_M(m), GET_DAG2_I(i)); + util::stream_format(stream, "%s = PM(%s, %s)", GET_UREG(ureg), GET_DAG2_M(m), GET_DAG2_I(i)); } else { - print("%s = DM(%s, %s)", GET_UREG(ureg), GET_DAG1_M(m), GET_DAG1_I(i)); + util::stream_format(stream, "%s = DM(%s, %s)", GET_UREG(ureg), GET_DAG1_M(m), GET_DAG1_I(i)); } } } } -static void pm_dm_imm_dreg(int g, int d, int i, int data, int dreg, int update) +void sharc_disassembler::pm_dm_imm_dreg(std::ostream &stream, int g, int d, int i, int data, int dreg, int update) { const char *sign = ""; if (data & 0x20) @@ -369,22 +425,22 @@ static void pm_dm_imm_dreg(int g, int d, int i, int data, int dreg, int update) { if (g) { - print("PM(%s, %s0x%02X) = %s", GET_DAG2_I(i), sign, data, GET_DREG(dreg)); + util::stream_format(stream, "PM(%s, %s0x%02X) = %s", GET_DAG2_I(i), sign, data, GET_DREG(dreg)); } else { - print("DM(%s, %s0x%02X) = %s", GET_DAG1_I(i), sign, data, GET_DREG(dreg)); + util::stream_format(stream, "DM(%s, %s0x%02X) = %s", GET_DAG1_I(i), sign, data, GET_DREG(dreg)); } } else { if (g) { - print("%s = PM(%s, %s0x%02X)", GET_DREG(dreg), GET_DAG2_I(i), sign, data); + util::stream_format(stream, "%s = PM(%s, %s0x%02X)", GET_DREG(dreg), GET_DAG2_I(i), sign, data); } else { - print("%s = DM(%s, %s0x%02X)", GET_DREG(dreg), GET_DAG1_I(i), sign, data); + util::stream_format(stream, "%s = DM(%s, %s0x%02X)", GET_DREG(dreg), GET_DAG1_I(i), sign, data); } } } @@ -394,54 +450,54 @@ static void pm_dm_imm_dreg(int g, int d, int i, int data, int dreg, int update) { if (g) { - print("PM(%s0x%02X, %s) = %s", sign, data, GET_DAG2_I(i), GET_DREG(dreg)); + util::stream_format(stream, "PM(%s0x%02X, %s) = %s", sign, data, GET_DAG2_I(i), GET_DREG(dreg)); } else { - print("DM(%s0x%02X, %s) = %s", sign, data, GET_DAG1_I(i), GET_DREG(dreg)); + util::stream_format(stream, "DM(%s0x%02X, %s) = %s", sign, data, GET_DAG1_I(i), GET_DREG(dreg)); } } else { if (g) { - print("%s = PM(%s0x%02X, %s)", GET_DREG(dreg), sign, data, GET_DAG2_I(i)); + util::stream_format(stream, "%s = PM(%s0x%02X, %s)", GET_DREG(dreg), sign, data, GET_DAG2_I(i)); } else { - print("%s = DM(%s0x%02X, %s)", GET_DREG(dreg), sign, data, GET_DAG1_I(i)); + util::stream_format(stream, "%s = DM(%s0x%02X, %s)", GET_DREG(dreg), sign, data, GET_DAG1_I(i)); } } } } -static void pm_dm_dreg(int g, int d, int i, int m, int dreg) +void sharc_disassembler::pm_dm_dreg(std::ostream &stream, int g, int d, int i, int m, int dreg) { if (d) { if (g) { - print("PM(%s, %s) = %s", GET_DAG2_I(i), GET_DAG2_M(m), GET_DREG(dreg)); + util::stream_format(stream, "PM(%s, %s) = %s", GET_DAG2_I(i), GET_DAG2_M(m), GET_DREG(dreg)); } else { - print("DM(%s, %s) = %s", GET_DAG1_I(i), GET_DAG1_M(m), GET_DREG(dreg)); + util::stream_format(stream, "DM(%s, %s) = %s", GET_DAG1_I(i), GET_DAG1_M(m), GET_DREG(dreg)); } } else { if (g) { - print("%s = PM(%s, %s)", GET_DREG(dreg), GET_DAG2_I(i), GET_DAG2_M(m)); + util::stream_format(stream, "%s = PM(%s, %s)", GET_DREG(dreg), GET_DAG2_I(i), GET_DAG2_M(m)); } else { - print("%s = DM(%s, %s)", GET_DREG(dreg), GET_DAG1_I(i), GET_DAG1_M(m)); + util::stream_format(stream, "%s = DM(%s, %s)", GET_DREG(dreg), GET_DAG1_I(i), GET_DAG1_M(m)); } } } -static void shiftop(int shift, int data, int rn, int rx) +void sharc_disassembler::shiftop(std::ostream &stream, int shift, int data, int rn, int rx) { int8_t data8 = data & 0xff; int bit6 = data & 0x3f; @@ -449,36 +505,32 @@ static void shiftop(int shift, int data, int rn, int rx) switch(shift) { - case 0x00: print("R%d = LSHIFT R%d BY %d", rn, rx, data8); break; - case 0x08: print("R%d = R%d OR LSHIFT R%d BY %d", rn, rn, rx, data8); break; - case 0x01: print("R%d = ASHIFT R%d BY %d", rn, rx, data8); break; - case 0x09: print("R%d = R%d OR ASHIFT R%d BY %d", rn, rn, rx, data8); break; - case 0x02: print("R%d = ROT R%d BY %d", rn, rx, data8); break; - case 0x31: print("R%d = BCLR R%d BY %d", rn, rx, data8); break; - case 0x30: print("R%d = BSET R%d BY %d", rn, rx, data8); break; - case 0x32: print("R%d = BTGL R%d BY %d", rn, rx, data8); break; - case 0x33: print("BTST R%d BY %d", rx, data8); break; - case 0x11: print("R%d = FDEP R%d BY %d:%d", rn, rx, bit6, len); break; - case 0x19: print("R%d = R%d OR FDEP R%d BY %d:%d", rn, rn, rx, bit6, len); break; - case 0x13: print("R%d = FDEP R%d BY %d:%d (SE)", rn, rx, bit6, len); break; - case 0x1b: print("R%d = R%d OR FDEP R%d BY %d:%d (SE)", rn, rn, rx, bit6, len); break; - case 0x10: print("R%d = FEXT R%d BY %d:%d", rn, rx, bit6, len); break; - case 0x12: print("R%d = FEXT R%d BY %d:%d (SE)", rn, rx, bit6, len); break; - case 0x20: print("R%d = EXP R%d", rn, rx); break; - case 0x21: print("R%d = EXP R%d (EX)", rn, rx); break; - case 0x22: print("R%d = LEFTZ R%d", rn, rx); break; - case 0x23: print("R%d = LEFTO R%d", rn, rx); break; - case 0x24: print("R%d = FPACK F%d", rn, rx); break; - case 0x25: print("F%d = FUNPACK R%d", rn, rx); break; - default: print("??? (SHIFTOP)"); break; + case 0x00: util::stream_format(stream, "R%d = LSHIFT R%d BY %d", rn, rx, data8); break; + case 0x08: util::stream_format(stream, "R%d = R%d OR LSHIFT R%d BY %d", rn, rn, rx, data8); break; + case 0x01: util::stream_format(stream, "R%d = ASHIFT R%d BY %d", rn, rx, data8); break; + case 0x09: util::stream_format(stream, "R%d = R%d OR ASHIFT R%d BY %d", rn, rn, rx, data8); break; + case 0x02: util::stream_format(stream, "R%d = ROT R%d BY %d", rn, rx, data8); break; + case 0x31: util::stream_format(stream, "R%d = BCLR R%d BY %d", rn, rx, data8); break; + case 0x30: util::stream_format(stream, "R%d = BSET R%d BY %d", rn, rx, data8); break; + case 0x32: util::stream_format(stream, "R%d = BTGL R%d BY %d", rn, rx, data8); break; + case 0x33: util::stream_format(stream, "BTST R%d BY %d", rx, data8); break; + case 0x11: util::stream_format(stream, "R%d = FDEP R%d BY %d:%d", rn, rx, bit6, len); break; + case 0x19: util::stream_format(stream, "R%d = R%d OR FDEP R%d BY %d:%d", rn, rn, rx, bit6, len); break; + case 0x13: util::stream_format(stream, "R%d = FDEP R%d BY %d:%d (SE)", rn, rx, bit6, len); break; + case 0x1b: util::stream_format(stream, "R%d = R%d OR FDEP R%d BY %d:%d (SE)", rn, rn, rx, bit6, len); break; + case 0x10: util::stream_format(stream, "R%d = FEXT R%d BY %d:%d", rn, rx, bit6, len); break; + case 0x12: util::stream_format(stream, "R%d = FEXT R%d BY %d:%d (SE)", rn, rx, bit6, len); break; + case 0x20: util::stream_format(stream, "R%d = EXP R%d", rn, rx); break; + case 0x21: util::stream_format(stream, "R%d = EXP R%d (EX)", rn, rx); break; + case 0x22: util::stream_format(stream, "R%d = LEFTZ R%d", rn, rx); break; + case 0x23: util::stream_format(stream, "R%d = LEFTO R%d", rn, rx); break; + case 0x24: util::stream_format(stream, "R%d = FPACK F%d", rn, rx); break; + case 0x25: util::stream_format(stream, "F%d = FUNPACK R%d", rn, rx); break; + default: util::stream_format(stream, "??? (SHIFTOP)"); break; } } - - - - -static uint32_t dasm_compute_dreg_dmpm(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_compute_dreg_dmpm(std::ostream &stream, uint32_t pc, uint64_t opcode) { int dmi = (opcode >> 41) & 0x7; int dmm = (opcode >> 38) & 0x7; @@ -492,42 +544,42 @@ static uint32_t dasm_compute_dreg_dmpm(uint32_t pc, uint64_t opcode) if (comp) { - compute(comp); - print(", "); + compute(stream, comp); + util::stream_format(stream, ", "); } if (dmd) { - print("DM(%s, %s) = R%d, ", GET_DAG1_I(dmi), GET_DAG1_M(dmm), dmdreg); + util::stream_format(stream, "DM(%s, %s) = R%d, ", GET_DAG1_I(dmi), GET_DAG1_M(dmm), dmdreg); } else { - print("R%d = DM(%s, %s), ", dmdreg, GET_DAG1_I(dmi), GET_DAG1_M(dmm)); + util::stream_format(stream, "R%d = DM(%s, %s), ", dmdreg, GET_DAG1_I(dmi), GET_DAG1_M(dmm)); } if (pmd) { - print("PM(%s, %s) = R%d", GET_DAG2_I(pmi), GET_DAG2_M(pmm), pmdreg); + util::stream_format(stream, "PM(%s, %s) = R%d", GET_DAG2_I(pmi), GET_DAG2_M(pmm), pmdreg); } else { - print("R%d = PM(%s, %s)", pmdreg, GET_DAG2_I(pmi), GET_DAG2_M(pmm)); + util::stream_format(stream, "R%d = PM(%s, %s)", pmdreg, GET_DAG2_I(pmi), GET_DAG2_M(pmm)); } return 0; } -static uint32_t dasm_compute(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_compute(std::ostream &stream, uint32_t pc, uint64_t opcode) { int cond = (opcode >> 33) & 0x1f; int comp = opcode & 0x7fffff; if (comp) { - get_if_condition(cond); - compute(comp); + get_if_condition(stream, cond); + compute(stream, comp); } return 0; } -static uint32_t dasm_compute_uregdmpm_regmod(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_compute_uregdmpm_regmod(std::ostream &stream, uint32_t pc, uint64_t opcode) { int cond = (opcode >> 33) & 0x1f; int g = (opcode >> 32) & 0x1; @@ -538,17 +590,17 @@ static uint32_t dasm_compute_uregdmpm_regmod(uint32_t pc, uint64_t opcode) int ureg = (opcode >> 23) & 0xff; int comp = opcode & 0x7fffff; - get_if_condition(cond); + get_if_condition(stream, cond); if (comp) { - compute(comp); - print(", "); + compute(stream, comp); + util::stream_format(stream, ", "); } - pm_dm_ureg(g,d,i,m, ureg, u); + pm_dm_ureg(stream, g,d,i,m, ureg, u); return 0; } -static uint32_t dasm_compute_dregdmpm_immmod(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_compute_dregdmpm_immmod(std::ostream &stream, uint32_t pc, uint64_t opcode) { int cond = (opcode >> 33) & 0x1f; int g = (opcode >> 40) & 0x1; @@ -559,34 +611,34 @@ static uint32_t dasm_compute_dregdmpm_immmod(uint32_t pc, uint64_t opcode) int data = (opcode >> 27) & 0x3f; int comp = opcode & 0x7fffff; - get_if_condition(cond); + get_if_condition(stream, cond); if (comp) { - compute(comp); - print(", "); + compute(stream, comp); + util::stream_format(stream, ", "); } - pm_dm_imm_dreg(g,d,i, data, dreg, u); + pm_dm_imm_dreg(stream, g,d,i, data, dreg, u); return 0; } -static uint32_t dasm_compute_ureg_ureg(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_compute_ureg_ureg(std::ostream &stream, uint32_t pc, uint64_t opcode) { int cond = (opcode >> 31) & 0x1f; int uregs = (opcode >> 36) & 0xff; int uregd = (opcode >> 23) & 0xff; int comp = opcode & 0x7fffff; - get_if_condition(cond); + get_if_condition(stream, cond); if (comp) { - compute(comp); - print(", "); + compute(stream, comp); + util::stream_format(stream, ", "); } - print("%s = %s", GET_UREG(uregd), GET_UREG(uregs)); + util::stream_format(stream, "%s = %s", GET_UREG(uregd), GET_UREG(uregs)); return 0; } -static uint32_t dasm_immshift_dregdmpm(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_immshift_dregdmpm(std::ostream &stream, uint32_t pc, uint64_t opcode) { int cond = (opcode >> 33) & 0x1f; int g = (opcode >> 32) & 0x1; @@ -599,14 +651,14 @@ static uint32_t dasm_immshift_dregdmpm(uint32_t pc, uint64_t opcode) int dreg = (opcode >> 23) & 0xf; int data = (((opcode >> 27) & 0xf) << 8) | ((opcode >> 8) & 0xff); - get_if_condition(cond); - shiftop(shift, data, rn, rx); - print(", "); - pm_dm_dreg(g,d,i,m, dreg); + get_if_condition(stream, cond); + shiftop(stream, shift, data, rn, rx); + util::stream_format(stream, ", "); + pm_dm_dreg(stream, g,d,i,m, dreg); return 0; } -static uint32_t dasm_immshift_dregdmpm_nodata(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_immshift_dregdmpm_nodata(std::ostream &stream, uint32_t pc, uint64_t opcode) { int cond = (opcode >> 33) & 0x1f; int rn = (opcode >> 4) & 0xf; @@ -614,12 +666,12 @@ static uint32_t dasm_immshift_dregdmpm_nodata(uint32_t pc, uint64_t opcode) int shift = (opcode >> 16) & 0x3f; int data = (((opcode >> 27) & 0xf) << 8) | ((opcode >> 8) & 0xff); - get_if_condition(cond); - shiftop(shift, data, rn, rx); + get_if_condition(stream, cond); + shiftop(stream, shift, data, rn, rx); return 0; } -static uint32_t dasm_compute_modify(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_compute_modify(std::ostream &stream, uint32_t pc, uint64_t opcode) { int cond = (opcode >> 33) & 0x1f; int g = (opcode >> 38) & 0x7; @@ -627,17 +679,17 @@ static uint32_t dasm_compute_modify(uint32_t pc, uint64_t opcode) int m = (opcode >> 27) & 0x7; int comp = opcode & 0x7fffff; - get_if_condition(cond); + get_if_condition(stream, cond); if (comp) { - compute(comp); - print(", "); + compute(stream, comp); + util::stream_format(stream, ", "); } - print("MODIFY(I%d, M%d)", (g ? 8+i : i), (g ? 8+m : m)); + util::stream_format(stream, "MODIFY(I%d, M%d)", (g ? 8+i : i), (g ? 8+m : m)); return 0; } -static uint32_t dasm_direct_jump(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_direct_jump(std::ostream &stream, uint32_t pc, uint64_t opcode) { int j = (opcode >> 26) & 0x1; int cond = (opcode >> 33) & 0x1f; @@ -645,37 +697,37 @@ static uint32_t dasm_direct_jump(uint32_t pc, uint64_t opcode) uint32_t addr = opcode & 0xffffff; uint32_t flags = 0; - get_if_condition(cond); + get_if_condition(stream, cond); if (opcode & 0x8000000000U) { - print("CALL"); - flags = DASMFLAG_STEP_OVER; + util::stream_format(stream, "CALL"); + flags = STEP_OVER; } else { - print("JUMP"); + util::stream_format(stream, "JUMP"); } if (opcode & 0x10000000000U) /* PC-relative branch */ { - print(" (0x%08X)", pc + SIGN_EXTEND24(addr)); + util::stream_format(stream, " (0x%08X)", pc + SIGN_EXTEND24(addr)); } else /* Indirect branch */ { - print(" (0x%08X)", addr); + util::stream_format(stream, " (0x%08X)", addr); } if (j) { - print(" (DB)"); + util::stream_format(stream, " (DB)"); } if (ci) { - print(" (CI)"); + util::stream_format(stream, " (CI)"); } return flags; } -static uint32_t dasm_indirect_jump_compute(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_indirect_jump_compute(std::ostream &stream, uint32_t pc, uint64_t opcode) { int b = (opcode >> 39) & 0x1; int j = (opcode >> 26) & 0x1; @@ -688,48 +740,48 @@ static uint32_t dasm_indirect_jump_compute(uint32_t pc, uint64_t opcode) int comp = opcode & 0x7fffff; uint32_t flags = 0; - get_if_condition(cond); + get_if_condition(stream, cond); if (b) { - print("CALL"); - flags = DASMFLAG_STEP_OVER; + util::stream_format(stream, "CALL"); + flags = STEP_OVER; } else { - print("JUMP"); + util::stream_format(stream, "JUMP"); } if (opcode & 0x10000000000U) /* PC-relative branch */ { - print(" (0x%08X)", pc + SIGN_EXTEND6(reladdr)); + util::stream_format(stream, " (0x%08X)", pc + SIGN_EXTEND6(reladdr)); } else /* Indirect branch */ { - print(" (%s, %s)", GET_DAG2_M(pmm), GET_DAG2_I(pmi)); + util::stream_format(stream, " (%s, %s)", GET_DAG2_M(pmm), GET_DAG2_I(pmi)); } if (j) { - print(" (DB)"); + util::stream_format(stream, " (DB)"); } if (ci) { - print(" (CI)"); + util::stream_format(stream, " (CI)"); } if (comp) { - print(", "); + util::stream_format(stream, ", "); if (e) { - print("ELSE "); + util::stream_format(stream, "ELSE "); } - compute(comp); + compute(stream, comp); } return flags; } -static uint32_t dasm_indirect_jump_compute_dregdm(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_indirect_jump_compute_dregdm(std::ostream &stream, uint32_t pc, uint64_t opcode) { int d = (opcode >> 44) & 0x1; int cond = (opcode >> 33) & 0x1f; @@ -741,36 +793,36 @@ static uint32_t dasm_indirect_jump_compute_dregdm(uint32_t pc, uint64_t opcode) int dreg = (opcode >> 23) & 0xf; int comp = opcode & 0x7fffff; - get_if_condition(cond); - print("JUMP"); + get_if_condition(stream, cond); + util::stream_format(stream, "JUMP"); if (opcode & 0x200000000000U) /* PC-relative branch */ { - print(" (0x%08X)", pc + SIGN_EXTEND6(reladdr)); + util::stream_format(stream, " (0x%08X)", pc + SIGN_EXTEND6(reladdr)); } else /* Indirect branch */ { - print(" (%s, %s)", GET_DAG2_M(pmm), GET_DAG2_I(pmi)); + util::stream_format(stream, " (%s, %s)", GET_DAG2_M(pmm), GET_DAG2_I(pmi)); } - print(", ELSE "); + util::stream_format(stream, ", ELSE "); if (comp) { - compute(comp); - print(", "); + compute(stream, comp); + util::stream_format(stream, ", "); } if (d) { - print("%s = DM(%s, %s)", GET_DREG(dreg), GET_DAG1_I(dmi), GET_DAG1_M(dmm)); + util::stream_format(stream, "%s = DM(%s, %s)", GET_DREG(dreg), GET_DAG1_I(dmi), GET_DAG1_M(dmm)); } else { - print("DM(%s, %s) = %s", GET_DAG1_I(dmi), GET_DAG1_M(dmm), GET_DREG(dreg)); + util::stream_format(stream, "DM(%s, %s) = %s", GET_DAG1_I(dmi), GET_DAG1_M(dmm), GET_DREG(dreg)); } return 0; } -static uint32_t dasm_rts_compute(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_rts_compute(std::ostream &stream, uint32_t pc, uint64_t opcode) { int j = (opcode >> 26) & 0x1; int e = (opcode >> 25) & 0x1; @@ -778,40 +830,40 @@ static uint32_t dasm_rts_compute(uint32_t pc, uint64_t opcode) int cond = (opcode >> 33) & 0x1f; int comp = opcode & 0x7fffff; - get_if_condition(cond); + get_if_condition(stream, cond); if (opcode & 0x10000000000U) { - print("RTI"); + util::stream_format(stream, "RTI"); } else { - print("RTS"); + util::stream_format(stream, "RTS"); } if (j) { - print(" (DB)"); + util::stream_format(stream, " (DB)"); } if (lr) { - print(" (LR)"); + util::stream_format(stream, " (LR)"); } if (comp) { - print(", "); + util::stream_format(stream, ", "); if (e) { - print("ELSE "); + util::stream_format(stream, "ELSE "); } - compute(comp); + compute(stream, comp); } - return DASMFLAG_STEP_OUT; + return STEP_OUT; } -static uint32_t dasm_do_until_counter(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_do_until_counter(std::ostream &stream, uint32_t pc, uint64_t opcode) { int data = (opcode >> 24) & 0xffff; int ureg = (opcode >> 32) & 0xff; @@ -819,27 +871,27 @@ static uint32_t dasm_do_until_counter(uint32_t pc, uint64_t opcode) if (opcode & 0x10000000000U) /* Loop counter from universal register */ { - print("LCNTR = %s, ", GET_UREG(ureg)); - print("DO (0x%08X)", pc + SIGN_EXTEND24(addr)); + util::stream_format(stream, "LCNTR = %s, ", GET_UREG(ureg)); + util::stream_format(stream, "DO (0x%08X)", pc + SIGN_EXTEND24(addr)); } else /* Loop counter from immediate */ { - print("LCNTR = 0x%04X, ", data); - print("DO (0x%08X) UNTIL LCE", pc + SIGN_EXTEND24(addr)); + util::stream_format(stream, "LCNTR = 0x%04X, ", data); + util::stream_format(stream, "DO (0x%08X) UNTIL LCE", pc + SIGN_EXTEND24(addr)); } return 0; } -static uint32_t dasm_do_until(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_do_until(std::ostream &stream, uint32_t pc, uint64_t opcode) { int term = (opcode >> 33) & 0x1f; uint32_t addr = opcode & 0xffffff; - print("DO (0x%08X) UNTIL %s", pc + SIGN_EXTEND24(addr), condition_codes_do[term]); + util::stream_format(stream, "DO (0x%08X) UNTIL %s", pc + SIGN_EXTEND24(addr), condition_codes_do[term]); return 0; } -static uint32_t dasm_immmove_uregdmpm(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_immmove_uregdmpm(std::ostream &stream, uint32_t pc, uint64_t opcode) { int d = (opcode >> 40) & 0x1; int g = (opcode >> 41) & 0x1; @@ -850,28 +902,28 @@ static uint32_t dasm_immmove_uregdmpm(uint32_t pc, uint64_t opcode) { if (d) { - print("PM(0x%08X) = %s", addr, GET_UREG(ureg)); + util::stream_format(stream, "PM(0x%08X) = %s", addr, GET_UREG(ureg)); } else { - print("%s = PM(0x%08X)", GET_UREG(ureg), addr); + util::stream_format(stream, "%s = PM(0x%08X)", GET_UREG(ureg), addr); } } else { if (d) { - print("DM(0x%08X) = %s", addr, GET_UREG(ureg)); + util::stream_format(stream, "DM(0x%08X) = %s", addr, GET_UREG(ureg)); } else { - print("%s = DM(0x%08X)", GET_UREG(ureg), addr); + util::stream_format(stream, "%s = DM(0x%08X)", GET_UREG(ureg), addr); } } return 0; } -static uint32_t dasm_immmove_uregdmpm_indirect(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_immmove_uregdmpm_indirect(std::ostream &stream, uint32_t pc, uint64_t opcode) { int d = (opcode >> 40) & 0x1; int g = (opcode >> 44) & 0x1; @@ -883,28 +935,28 @@ static uint32_t dasm_immmove_uregdmpm_indirect(uint32_t pc, uint64_t opcode) { if (d) { - print("PM(0x%08X, %s) = %s", addr, GET_DAG2_I(i), GET_UREG(ureg)); + util::stream_format(stream, "PM(0x%08X, %s) = %s", addr, GET_DAG2_I(i), GET_UREG(ureg)); } else { - print("%s = PM(0x%08X, %s)", GET_UREG(ureg), addr, GET_DAG2_I(i)); + util::stream_format(stream, "%s = PM(0x%08X, %s)", GET_UREG(ureg), addr, GET_DAG2_I(i)); } } else { if (d) { - print("DM(0x%08X, %s) = %s", addr, GET_DAG1_I(i), GET_UREG(ureg)); + util::stream_format(stream, "DM(0x%08X, %s) = %s", addr, GET_DAG1_I(i), GET_UREG(ureg)); } else { - print("%s = DM(0x%08X, %s)", GET_UREG(ureg), addr, GET_DAG1_I(i)); + util::stream_format(stream, "%s = DM(0x%08X, %s)", GET_UREG(ureg), addr, GET_DAG1_I(i)); } } return 0; } -static uint32_t dasm_immmove_immdata_dmpm(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_immmove_immdata_dmpm(std::ostream &stream, uint32_t pc, uint64_t opcode) { int g = (opcode >> 37) & 0x1; int i = (opcode >> 41) & 0x7; @@ -913,38 +965,38 @@ static uint32_t dasm_immmove_immdata_dmpm(uint32_t pc, uint64_t opcode) if (g) { - print("PM(%s, %s) = 0x%08X", GET_DAG2_I(i), GET_DAG2_M(m), data); + util::stream_format(stream, "PM(%s, %s) = 0x%08X", GET_DAG2_I(i), GET_DAG2_M(m), data); } else { - print("DM(%s, %s) = 0x%08X", GET_DAG1_I(i), GET_DAG1_M(m), data); + util::stream_format(stream, "DM(%s, %s) = 0x%08X", GET_DAG1_I(i), GET_DAG1_M(m), data); } return 0; } -static uint32_t dasm_immmove_immdata_ureg(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_immmove_immdata_ureg(std::ostream &stream, uint32_t pc, uint64_t opcode) { int ureg = (opcode >> 32) & 0xff; uint32_t data = opcode & 0xffffffff; - print("%s = 0x%08X", GET_UREG(ureg), data); + util::stream_format(stream, "%s = 0x%08X", GET_UREG(ureg), data); return 0; } -static uint32_t dasm_sysreg_bitop(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_sysreg_bitop(std::ostream &stream, uint32_t pc, uint64_t opcode) { int bop = (opcode >> 37) & 0x7; int sreg = (opcode >> 32) & 0xf; uint32_t data = opcode & 0xffffffff; - print("BIT "); - print("%s ", bopnames[bop]); - print("%s ", GET_SREG(sreg)); - print("0x%08X", data); + util::stream_format(stream, "BIT "); + util::stream_format(stream, "%s ", bopnames[bop]); + util::stream_format(stream, "%s ", GET_SREG(sreg)); + util::stream_format(stream, "0x%08X", data); return 0; } -static uint32_t dasm_ireg_modify(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_ireg_modify(std::ostream &stream, uint32_t pc, uint64_t opcode) { int g = (opcode >> 38) & 0x1; int i = (opcode >> 32) & 0x7; @@ -954,28 +1006,28 @@ static uint32_t dasm_ireg_modify(uint32_t pc, uint64_t opcode) { if (g) { - print("BITREV (%s, 0x%08X)", GET_DAG2_I(i), data); + util::stream_format(stream, "BITREV (%s, 0x%08X)", GET_DAG2_I(i), data); } else { - print("BITREV (%s, 0x%08X)", GET_DAG1_I(i), data); + util::stream_format(stream, "BITREV (%s, 0x%08X)", GET_DAG1_I(i), data); } } else /* without bit-reverse */ { if (g) { - print("MODIFY (%s, 0x%08X)", GET_DAG2_I(i), data); + util::stream_format(stream, "MODIFY (%s, 0x%08X)", GET_DAG2_I(i), data); } else { - print("MODIFY (%s, 0x%08X)", GET_DAG1_I(i), data); + util::stream_format(stream, "MODIFY (%s, 0x%08X)", GET_DAG1_I(i), data); } } return 0; } -static uint32_t dasm_misc(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_misc(std::ostream &stream, uint32_t pc, uint64_t opcode) { int bits = (opcode >> 33) & 0x7f; int lpu = (opcode >> 39) & 0x1; @@ -988,171 +1040,169 @@ static uint32_t dasm_misc(uint32_t pc, uint64_t opcode) if (lpu) { - print("PUSH LOOP"); + util::stream_format(stream, "PUSH LOOP"); if (bits & 0x3f) { - print(", "); + util::stream_format(stream, ", "); } } if (lpo) { - print("POP LOOP"); + util::stream_format(stream, "POP LOOP"); if (bits & 0x1f) { - print(", "); + util::stream_format(stream, ", "); } } if (spu) { - print("PUSH STS"); + util::stream_format(stream, "PUSH STS"); if (bits & 0xf) { - print(", "); + util::stream_format(stream, ", "); } } if (spo) { - print("POP STS"); + util::stream_format(stream, "POP STS"); if (bits & 0x7) { - print(", "); + util::stream_format(stream, ", "); } } if (ppu) { - print("PUSH PCSTK"); + util::stream_format(stream, "PUSH PCSTK"); if (bits & 0x3) { - print(", "); + util::stream_format(stream, ", "); } } if (ppo) { - print("POP PCSTK"); + util::stream_format(stream, "POP PCSTK"); if (bits & 0x1) { - print(", "); + util::stream_format(stream, ", "); } } if (fc) { - print("FLUSH CACHE"); + util::stream_format(stream, "FLUSH CACHE"); } return 0; } -static uint32_t dasm_idlenop(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_idlenop(std::ostream &stream, uint32_t pc, uint64_t opcode) { if (opcode & 0x8000000000U) { - print("IDLE"); + util::stream_format(stream, "IDLE"); } else { - print("NOP"); + util::stream_format(stream, "NOP"); } return 0; } -#ifdef UNUSED_FUNCTION -static uint32_t dasm_cjump_rframe(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_cjump_rframe(std::ostream &stream, uint32_t pc, uint64_t opcode) { /* TODO */ if (opcode & 0x10000000000U) /* RFRAME */ { - print("TODO: RFRAME"); + util::stream_format(stream, "TODO: RFRAME"); } else { - print("TODO: CJUMP"); + util::stream_format(stream, "TODO: CJUMP"); } return 0; } -#endif -static uint32_t dasm_invalid(uint32_t pc, uint64_t opcode) +uint32_t sharc_disassembler::dasm_invalid(std::ostream &stream, uint32_t pc, uint64_t opcode) { - print("?"); + util::stream_format(stream, "?"); return 0; } -static const SHARC_DASM_OP sharc_dasm_ops[] = +const sharc_disassembler::SHARC_DASM_OP sharc_disassembler::sharc_dasm_ops[] = { // |0 0 1| - { 0xe000, 0x2000, dasm_compute_dreg_dmpm }, + { 0xe000, 0x2000, &sharc_disassembler::dasm_compute_dreg_dmpm }, // |0 0 0|0 0 0 0 1| - { 0xff00, 0x0100, dasm_compute }, + { 0xff00, 0x0100, &sharc_disassembler::dasm_compute }, // |0 1 0| - { 0xe000, 0x4000, dasm_compute_uregdmpm_regmod }, + { 0xe000, 0x4000, &sharc_disassembler::dasm_compute_uregdmpm_regmod }, // |0 1 1|0| - { 0xf000, 0x6000, dasm_compute_dregdmpm_immmod }, + { 0xf000, 0x6000, &sharc_disassembler::dasm_compute_dregdmpm_immmod }, // |0 1 1|1| - { 0xf000, 0x7000, dasm_compute_ureg_ureg }, + { 0xf000, 0x7000, &sharc_disassembler::dasm_compute_ureg_ureg }, // |1 0 0|0| - { 0xf000, 0x8000, dasm_immshift_dregdmpm }, + { 0xf000, 0x8000, &sharc_disassembler::dasm_immshift_dregdmpm }, // |0 0 0|0 0 0 1 0| - { 0xff00, 0x0200, dasm_immshift_dregdmpm_nodata }, + { 0xff00, 0x0200, &sharc_disassembler::dasm_immshift_dregdmpm_nodata }, // |0 0 0|0 0 1 0 0| - { 0xff00, 0x0400, dasm_compute_modify }, + { 0xff00, 0x0400, &sharc_disassembler::dasm_compute_modify }, // |0 0 0|0 0 1 1 x| - { 0xfe00, 0x0600, dasm_direct_jump }, + { 0xfe00, 0x0600, &sharc_disassembler::dasm_direct_jump }, // |0 0 0|0 1 0 0 x| - { 0xfe00, 0x0800, dasm_indirect_jump_compute }, + { 0xfe00, 0x0800, &sharc_disassembler::dasm_indirect_jump_compute }, // |1 1 x| - { 0xc000, 0xc000, dasm_indirect_jump_compute_dregdm }, + { 0xc000, 0xc000, &sharc_disassembler::dasm_indirect_jump_compute_dregdm }, // |0 0 0|0 1 0 1 x| - { 0xfe00, 0x0a00, dasm_rts_compute }, + { 0xfe00, 0x0a00, &sharc_disassembler::dasm_rts_compute }, // |0 0 0|0 1 1 0 x| - { 0xfe00, 0x0c00, dasm_do_until_counter }, + { 0xfe00, 0x0c00, &sharc_disassembler::dasm_do_until_counter }, // |0 0 0|0 1 1 1 0| - { 0xff00, 0x0e00, dasm_do_until }, + { 0xff00, 0x0e00, &sharc_disassembler::dasm_do_until }, // |0 0 0|1 0 0|x|x| - { 0xfc00, 0x1000, dasm_immmove_uregdmpm }, + { 0xfc00, 0x1000, &sharc_disassembler::dasm_immmove_uregdmpm }, // |1 0 1|x|x x x|x| - { 0xe000, 0xa000, dasm_immmove_uregdmpm_indirect }, + { 0xe000, 0xa000, &sharc_disassembler::dasm_immmove_uregdmpm_indirect }, // |1 0 0|1| - { 0xf000, 0x9000, dasm_immmove_immdata_dmpm }, + { 0xf000, 0x9000, &sharc_disassembler::dasm_immmove_immdata_dmpm }, // |0 0 0|0 1 1 1 1| - { 0xff00, 0x0f00, dasm_immmove_immdata_ureg }, + { 0xff00, 0x0f00, &sharc_disassembler::dasm_immmove_immdata_ureg }, // |0 0 0|1 0 1 0 0| - { 0xff00, 0x1400, dasm_sysreg_bitop }, + { 0xff00, 0x1400, &sharc_disassembler::dasm_sysreg_bitop }, // |0 0 0|1 0 1 1 0| - { 0xff00, 0x1600, dasm_ireg_modify }, + { 0xff00, 0x1600, &sharc_disassembler::dasm_ireg_modify }, // |0 0 0|1 0 1 1 1| - { 0xff00, 0x1700, dasm_misc }, + { 0xff00, 0x1700, &sharc_disassembler::dasm_misc }, // |0 0 0|0 0 0 0 0| - { 0xff00, 0x0000, dasm_idlenop }, + { 0xff00, 0x0000, &sharc_disassembler::dasm_idlenop }, }; -static void build_dasm_table(void) +sharc_disassembler::sharc_disassembler() { int i, j; int num_ops = sizeof(sharc_dasm_ops) / sizeof(SHARC_DASM_OP); for (i=0; i < 256; i++) { - sharcdasm_table[i] = dasm_invalid; + sharcdasm_table[i] = &sharc_disassembler::dasm_invalid; } for (i=0; i < 256; i++) @@ -1163,7 +1213,7 @@ static void build_dasm_table(void) { if ((sharc_dasm_ops[j].op_mask & op) == sharc_dasm_ops[j].op_bits) { - if (sharcdasm_table[i] != dasm_invalid) + if (sharcdasm_table[i] != &sharc_disassembler::dasm_invalid) { fatalerror("build_dasm_table: table already filled! (i=%04X, j=%d)\n", i, j); } @@ -1176,45 +1226,15 @@ static void build_dasm_table(void) } } -static uint32_t sharc_dasm_one(std::ostream &stream, offs_t pc, uint64_t opcode) +offs_t sharc_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - #define DEFAULT_DASM_WIDTH (64) - - char dasm_buffer[2000]; - int i; + u64 opcode = opcodes.r64(pc); int op = (opcode >> 40) & 0xff; - uint32_t flags; - - if (!dasm_table_built) - { - build_dasm_table(); - dasm_table_built = 1; - } - memset(dasm_buffer, 0, sizeof(dasm_buffer)); - - /* set buffer for print */ - output = dasm_buffer; - - flags = (*sharcdasm_table[op])(pc, opcode); - - for (i=0; i < DEFAULT_DASM_WIDTH && dasm_buffer[i]; i++) - { - stream << dasm_buffer[i]; - } - return flags; + return 1 | (this->*sharcdasm_table[op])(stream, pc, opcode) | SUPPORTED; } - -CPU_DISASSEMBLE( sharc ) +u32 sharc_disassembler::opcode_alignment() const { - uint64_t op; - uint32_t flags; - - op = ((uint64_t)oprom[0] << 0) | ((uint64_t)oprom[1] << 8) | - ((uint64_t)oprom[2] << 16) | ((uint64_t)oprom[3] << 24) | - ((uint64_t)oprom[4] << 32) | ((uint64_t)oprom[5] << 40); - - flags = sharc_dasm_one(stream, pc, op); - return 1 | flags | DASMFLAG_SUPPORTED; + return 1; } diff --git a/src/devices/cpu/sharc/sharcdsm.h b/src/devices/cpu/sharc/sharcdsm.h index e4a52e94ea6..f752a133d6a 100644 --- a/src/devices/cpu/sharc/sharcdsm.h +++ b/src/devices/cpu/sharc/sharcdsm.h @@ -1,79 +1,68 @@ // license:BSD-3-Clause // copyright-holders:Ville Linde -static const char ureg_names[256][16] = -{ - "R0", "R1", "R2", "R3", "R4", "R5", "R6", "R7", - "R8", "R9", "R10", "R11", "R12", "R13", "R14", "R15", - "I0", "I1", "I2", "I3", "I4", "I5", "I6", "I7", - "I8", "I9", "I10", "I11", "I12", "I13", "I14", "I15", - "M0", "M1", "M2", "M3", "M4", "M5", "M6", "M7", - "M8", "M9", "M10", "M11", "M12", "M13", "M14", "M15", - "L0", "L1", "L2", "L3", "L4", "L5", "L6", "L7", - "L8", "L9", "L10", "L11", "L12", "L13", "L14", "L15", - "B0", "B1", "B2", "B3", "B4", "B5", "B6", "B7", - "B8", "B9", "B10", "B11", "B12", "B13", "B14", "B15", - "???", "???", "???", "???", "???", "???", "???", "???", - "???", "???", "???", "???", "???", "???", "???", "???", - "FADDR", "DADDR", "???", "PC", "PCSTK", "PCSTKP", "LADDR", "CURLCNTR", - "LCNTR", "???", "???", "???", "???", "???", "???", "???", - "USTAT1", "USTAT2", "???", "???", "???", "???", "???", "???", - "???", "IRPTL", "MODE2", "MODE1", "ASTAT", "IMASK", "STKY", "IMASKP", - "???", "???", "???", "???", "???", "???", "???", "???", - "???", "???", "???", "???", "???", "???", "???", "???", - "???", "???", "???", "???", "???", "???", "???", "???", - "???", "???", "???", "???", "???", "???", "???", "???", - "???", "???", "???", "???", "???", "???", "???", "???", - "???", "???", "???", "???", "???", "???", "???", "???", - "???", "???", "???", "???", "???", "???", "???", "???", - "???", "???", "???", "???", "???", "???", "???", "???", - "???", "???", "???", "???", "???", "???", "???", "???", - "???", "???", "???", "???", "???", "???", "???", "???", - "???", "???", "???", "???", "???", "???", "???", "???", - "???", "???", "???", "PX", "PX1", "PX2", "TPERIOD", "TCOUNT", - "???", "???", "???", "???", "???", "???", "???", "???", - "???", "???", "???", "???", "???", "???", "???", "???", - "???", "???", "???", "???", "???", "???", "???", "???", - "???", "???", "???", "???", "???", "???", "???", "???" -}; -static const char bopnames[8][8] = -{ - "SET", "CLEAR", "TOGGLE", "???", "TEST", "XOR", "???", "???" -}; +#ifndef MAME_CPU_SHARC_SHARCDSM_H +#define MAME_CPU_SHARC_SHARCDSM_H -static const char condition_codes_if[32][32] = -{ - "EQ", "LT", "LE", "AC", - "AV", "MV", "MS", "SV", - "SZ", "FLAG0_IN", "FLAG1_IN", "FLAG2_IN", - "FLAG3_IN", "TF", "BM", "NOT LCE", - "NE", "GE", "GT", "NOT AC", - "NOT AV", "NOT MV", "NOT MS", "NOT SV", - "NOT SZ", "NOT FLAG0_IN", "NOT FLAG1_IN", "NOT FLAG2_IN", - "NOT FLAG3_IN", "NOT TF", "NBM", "" -}; +#pragma once -static const char condition_codes_do[32][32] = +class sharc_disassembler : public util::disasm_interface { - "EQ", "LT", "LE", "AC", - "AV", "MV", "MS", "SV", - "SZ", "FLAG0_IN", "FLAG1_IN", "FLAG2_IN", - "FLAG3_IN", "TF", "BM", "LCE", - "NE", "GE", "GT", "NOT AC", - "NOT AV", "NOT MV", "NOT MS", "NOT SV", - "NOT SZ", "NOT FLAG0_IN", "NOT FLAG1_IN", "NOT FLAG2_IN", - "NOT FLAG3_IN", "NOT TF", "NBM", "FOREVER" -}; +public: + sharc_disassembler(); + virtual ~sharc_disassembler() = default; -static const char mr_regnames[16][8] = -{ - "MR0F", "MR1F", "MR2F", "MR0B", "MR1B", "MR2B", "???", "???", - "???", "???", "???", "???", "???", "???", "???", "???" -}; + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; -struct SHARC_DASM_OP -{ - uint32_t op_mask; - uint32_t op_bits; - uint32_t (* handler)(uint32_t, uint64_t); +private: + struct SHARC_DASM_OP + { + uint32_t op_mask; + uint32_t op_bits; + uint32_t (sharc_disassembler::*handler)(std::ostream &, uint32_t, uint64_t); + }; + + static const char ureg_names[256][16]; + static const char bopnames[8][8]; + static const char condition_codes_if[32][32]; + static const char condition_codes_do[32][32]; + static const char mr_regnames[16][8]; + static const SHARC_DASM_OP sharc_dasm_ops[]; + + uint32_t (sharc_disassembler::*sharcdasm_table[256])(std::ostream &, uint32_t, uint64_t); + + void compute(std::ostream &stream, uint32_t opcode); + void get_if_condition(std::ostream &stream, int cond); + void pm_dm_ureg(std::ostream &stream, int g, int d, int i, int m, int ureg, int update); + void pm_dm_imm_dreg(std::ostream &stream, int g, int d, int i, int data, int dreg, int update); + void pm_dm_dreg(std::ostream &stream, int g, int d, int i, int m, int dreg); + void shiftop(std::ostream &stream, int shift, int data, int rn, int rx); + + uint32_t dasm_compute_dreg_dmpm(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_compute(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_compute_uregdmpm_regmod(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_compute_dregdmpm_immmod(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_compute_ureg_ureg(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_immshift_dregdmpm(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_immshift_dregdmpm_nodata(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_compute_modify(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_direct_jump(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_indirect_jump_compute(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_indirect_jump_compute_dregdm(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_rts_compute(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_do_until_counter(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_do_until(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_immmove_uregdmpm(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_immmove_uregdmpm_indirect(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_immmove_immdata_dmpm(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_immmove_immdata_ureg(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_sysreg_bitop(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_ireg_modify(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_misc(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_idlenop(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_cjump_rframe(std::ostream &stream, uint32_t pc, uint64_t opcode); + uint32_t dasm_invalid(std::ostream &stream, uint32_t pc, uint64_t opcode); }; + +#endif diff --git a/src/devices/cpu/sharc/sharcops.hxx b/src/devices/cpu/sharc/sharcops.hxx index af1beed292b..8e7a03d974e 100644 --- a/src/devices/cpu/sharc/sharcops.hxx +++ b/src/devices/cpu/sharc/sharcops.hxx @@ -2721,9 +2721,5 @@ void adsp21062_device::sharcop_idle() void adsp21062_device::sharcop_unimplemented() { - extern CPU_DISASSEMBLE(sharc); - std::ostringstream dasm; - CPU_DISASSEMBLE_NAME(sharc)(nullptr, dasm, m_core->pc, nullptr, nullptr, 0); - osd_printf_debug("SHARC: %08X: %s\n", m_core->pc, dasm.str().c_str()); fatalerror("SHARC: Unimplemented opcode %04X%08X at %08X\n", (uint16_t)(m_core->opcode >> 32), (uint32_t)(m_core->opcode), m_core->pc); } diff --git a/src/devices/cpu/sm510/sm500.h b/src/devices/cpu/sm510/sm500.h index a7b9b336220..25349ecb1f2 100644 --- a/src/devices/cpu/sm510/sm500.h +++ b/src/devices/cpu/sm510/sm500.h @@ -87,7 +87,7 @@ protected: virtual void device_start() override; virtual void device_reset() override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void execute_one() override; virtual void get_opcode_param() override; virtual void clock_melody() override; @@ -155,7 +155,7 @@ public: protected: sm5a_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, u32 clock, int stack_levels, int o_pins, int prgwidth, address_map_constructor program, int datawidth, address_map_constructor data); - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void execute_one() override; virtual int get_trs_field() override { return 1; } }; diff --git a/src/devices/cpu/sm510/sm500core.cpp b/src/devices/cpu/sm510/sm500core.cpp index daf60275680..d32fd935e4a 100644 --- a/src/devices/cpu/sm510/sm500core.cpp +++ b/src/devices/cpu/sm510/sm500core.cpp @@ -13,6 +13,7 @@ #include "emu.h" #include "sm500.h" +#include "sm510d.h" #include "debugger.h" @@ -48,10 +49,9 @@ sm500_device::sm500_device(const machine_config &mconfig, device_type type, cons // disasm -offs_t sm500_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +util::disasm_interface *sm500_device::create_disassembler() { - extern CPU_DISASSEMBLE(sm500); - return CPU_DISASSEMBLE_NAME(sm500)(this, stream, pc, oprom, opram, options); + return new sm500_disassembler; } diff --git a/src/devices/cpu/sm510/sm510.h b/src/devices/cpu/sm510/sm510.h index cb963e87fa8..f9972a0c6e7 100644 --- a/src/devices/cpu/sm510/sm510.h +++ b/src/devices/cpu/sm510/sm510.h @@ -153,10 +153,6 @@ protected: // device_memory_interface overrides virtual space_config_vector memory_space_config() const override; - // device_disasm_interface overrides - virtual u32 disasm_min_opcode_bytes() const override { return 1; } - virtual u32 disasm_max_opcode_bytes() const override { return 2; } - address_space_config m_program_config; address_space_config m_data_config; address_space *m_program; @@ -321,7 +317,7 @@ public: sm510_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock); protected: - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void execute_one() override; virtual void get_opcode_param() override; @@ -342,7 +338,7 @@ protected: virtual void device_post_load() override { notify_clock_changed(); } virtual void device_reset() override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void execute_one() override; virtual void get_opcode_param() override; diff --git a/src/devices/cpu/sm510/sm510core.cpp b/src/devices/cpu/sm510/sm510core.cpp index fe422988459..3540a07168f 100644 --- a/src/devices/cpu/sm510/sm510core.cpp +++ b/src/devices/cpu/sm510/sm510core.cpp @@ -11,6 +11,7 @@ #include "emu.h" #include "sm510.h" +#include "sm510d.h" #include "debugger.h" @@ -41,10 +42,9 @@ sm510_device::sm510_device(const machine_config &mconfig, const char *tag, devic // disasm -offs_t sm510_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +util::disasm_interface *sm510_device::create_disassembler() { - extern CPU_DISASSEMBLE(sm510); - return CPU_DISASSEMBLE_NAME(sm510)(this, stream, pc, oprom, opram, options); + return new sm510_disassembler; } diff --git a/src/devices/cpu/sm510/sm510d.cpp b/src/devices/cpu/sm510/sm510d.cpp index 4ec634b4771..186efde5cbc 100644 --- a/src/devices/cpu/sm510/sm510d.cpp +++ b/src/devices/cpu/sm510/sm510d.cpp @@ -7,40 +7,12 @@ */ #include "emu.h" -#include "debugger.h" -#include "sm510.h" +#include "sm510d.h" // common lookup tables -enum e_mnemonics -{ - // SM510 common - mILL /* 0! */, mEXT, - mLB, mLBL, mSBM, mEXBLA, mINCB, mDECB, - mATPL, mRTN0, mRTN1, mTL, mTML, mTM, mT, - mEXC, mBDC, mEXCI, mEXCD, mLDA, mLAX, mPTW, mWR, mWS, - mKTA, mATBP, mATX, mATL, mATFC, mATR, - mADD, mADD11, mADX, mCOMA, mROT, mRC, mSC, - mTB, mTC, mTAM, mTMI, mTA0, mTABL, mTIS, mTAL, mTF1, mTF4, - mRM, mSM, - mPRE, mSME, mRME, mTMEL, - mSKIP, mCEND, mIDIV, mDR, mDTA, mCLKLO, mCLKHI, - - // SM500 common - mCOMCB, mRTN, mRTNS, mSSR, mTR, mTRS, mRBM, - mADDC, mPDTW, mTW, mDTW, - mATS, mEXKSA, mEXKFA, - mRMF, mSMF, mCOMCN, - mTA, mTM2, mTG, - - // SM590 aliases - mNOP, mCCTRL, mINBL, mDEBL, mXBLA, mADCS, mTR7, - // SM590 uniques - mTAX, mLBLX, mMTR, mSTR, mINBM, mDEBM, mRTA, mBLTA, mEXAX, mTBA, mADS, mADC, mLBMX, mTLS -}; - -static const char *const s_mnemonics[] = +const char *const sm510_common_disassembler::s_mnemonics[] = { "?", "", "LB", "LBL", "SBM", "EXBLA", "INCB", "DECB", @@ -67,7 +39,7 @@ static const char *const s_mnemonics[] = }; // number of bits per opcode parameter, 8 or larger means 2-byte opcode -static const u8 s_bits[] = +const u8 sm510_common_disassembler::s_bits[] = { 0, 8, 4, 8, 0, 0, 0, 0, @@ -93,42 +65,39 @@ static const u8 s_bits[] = 4, 4, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 2, 2+8 }; -#define _OVER DASMFLAG_STEP_OVER -#define _OUT DASMFLAG_STEP_OUT - -static const u32 s_flags[] = +const u32 sm510_common_disassembler::s_flags[] = { 0, 0, 0, 0, 0, 0, 0, 0, - 0, _OUT, _OUT, 0, _OVER, _OVER, 0, + 0, STEP_OUT, STEP_OUT, 0, STEP_OVER, STEP_OVER, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, _OVER, 0, 0, 0, 0, 0, + 0, STEP_OVER, 0, 0, 0, 0, 0, // - 0, _OUT, _OUT, 0, 0, _OVER, 0, + 0, STEP_OUT, STEP_OUT, 0, 0, STEP_OVER, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // - 0, 0, 0, 0, 0, 0, _OVER, + 0, 0, 0, 0, 0, 0, STEP_OVER, // - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, _OVER + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, STEP_OVER }; // common disasm -static offs_t sm510_common_disasm(const u8 *lut_mnemonic, const u8 *lut_extended, std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram) +offs_t sm510_common_disassembler::common_disasm(const u8 *lut_mnemonic, const u8 *lut_extended, std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms, const u8 pclen) { // get raw opcode - u8 op = oprom[0]; + u8 op = opcodes.r8(pc); u8 instr = lut_mnemonic[op]; int len = 1; @@ -137,7 +106,19 @@ static offs_t sm510_common_disasm(const u8 *lut_mnemonic, const u8 *lut_extended u16 param = mask; if (bits >= 8) { - param = oprom[1]; + if (pclen == 6) + { + int feed = ((pc >> 1 ^ pc) & 1) ? 0 : 0x20; + pc = feed | (pc >> 1 & 0x1f) | (pc & ~0x3f); + } + else if (pclen == 7) + { + int feed = ((pc >> 1 ^ pc) & 1) ? 0 : 0x40; + pc = feed | (pc >> 1 & 0x3f) | (pc & ~0x7f); + } + else + abort(); + param = params.r8(pc); len++; } @@ -169,13 +150,13 @@ static offs_t sm510_common_disasm(const u8 *lut_mnemonic, const u8 *lut_extended } } - return len | s_flags[instr] | DASMFLAG_SUPPORTED; + return len | s_flags[instr] |SUPPORTED; } // SM510 disasm -static const u8 sm510_mnemonic[0x100] = +const u8 sm510_disassembler::sm510_mnemonic[0x100] = { /* 0 1 2 3 4 5 6 7 8 9 A B C D E F */ mSKIP, mATBP, mSBM, mATPL, mRM, mRM, mRM, mRM, mADD, mADD11,mCOMA, mEXBLA,mSM, mSM, mSM, mSM, // 0 @@ -199,15 +180,15 @@ static const u8 sm510_mnemonic[0x100] = mTM, mTM, mTM, mTM, mTM, mTM, mTM, mTM, mTM, mTM, mTM, mTM, mTM, mTM, mTM, mTM // F }; -CPU_DISASSEMBLE(sm510) +offs_t sm510_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - return sm510_common_disasm(sm510_mnemonic, nullptr, stream, pc, oprom, opram); + return common_disasm(sm510_mnemonic, nullptr, stream, pc, opcodes, params, 6); } // SM511 disasm -static const u8 sm511_mnemonic[0x100] = +const u8 sm511_disassembler::sm511_mnemonic[0x100] = { /* 0 1 2 3 4 5 6 7 8 9 A B C D E F */ mROT, mDTA, mSBM, mATPL, mRM, mRM, mRM, mRM, mADD, mADD11,mCOMA, mEXBLA,mSM, mSM, mSM, mSM, // 0 @@ -231,25 +212,25 @@ static const u8 sm511_mnemonic[0x100] = mTM, mTM, mTM, mTM, mTM, mTM, mTM, mTM, mTM, mTM, mTM, mTM, mTM, mTM, mTM, mTM // F }; -static const u8 sm511_extended[0x10] = +const u8 sm511_disassembler::sm511_extended[0x10] = { mRME, mSME, mTMEL, mATFC, mBDC, mATBP, mCLKHI,mCLKLO,0, 0, 0, 0, 0, 0, 0, 0 // 60 3 }; -CPU_DISASSEMBLE(sm511) +offs_t sm511_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { // create extended opcode table u8 ext[0x100]; memset(ext, 0, 0x100); memcpy(ext + 0x30, sm511_extended, 0x10); - return sm510_common_disasm(sm511_mnemonic, ext, stream, pc, oprom, opram); + return common_disasm(sm511_mnemonic, ext, stream, pc, opcodes, params, 6); } // SM500 disasm -static const u8 sm500_mnemonic[0x100] = +const u8 sm500_disassembler::sm500_mnemonic[0x100] = { /* 0 1 2 3 4 5 6 7 8 9 A B C D E F */ mSKIP, mATR, mEXKSA,mATBP, mRM, mRM, mRM, mRM, mADD, mADDC, mCOMA, mEXBLA,mSM, mSM, mSM, mSM, // 0 @@ -273,25 +254,25 @@ static const u8 sm500_mnemonic[0x100] = mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS // F }; -static const u8 sm500_extended[0x10] = +const u8 sm500_disassembler::sm500_extended[0x10] = { mCEND, 0, 0, 0, mDTA, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 // 5E 0 }; -CPU_DISASSEMBLE(sm500) +offs_t sm500_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { // create extended opcode table u8 ext[0x100]; memset(ext, 0, 0x100); memcpy(ext + 0x00, sm500_extended, 0x10); - return sm510_common_disasm(sm500_mnemonic, ext, stream, pc, oprom, opram); + return common_disasm(sm500_mnemonic, ext, stream, pc, opcodes, params, 6); } // SM5A disasm -static const u8 sm5a_mnemonic[0x100] = +const u8 sm5a_disassembler::sm5a_mnemonic[0x100] = { /* 0 1 2 3 4 5 6 7 8 9 A B C D E F */ mSKIP, mATR, mSBM, mATBP, mRM, mRM, mRM, mRM, mADD, mADDC, mCOMA, mEXBLA,mSM, mSM, mSM, mSM, // 0 @@ -315,25 +296,25 @@ static const u8 sm5a_mnemonic[0x100] = mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS, mTRS // F }; -static const u8 sm5a_extended[0x10] = +const u8 sm5a_disassembler::sm5a_extended[0x10] = { mCEND, 0, 0, 0, mDTA, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 // 5E 0 }; -CPU_DISASSEMBLE(sm5a) +offs_t sm5a_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { // create extended opcode table u8 ext[0x100]; memset(ext, 0, 0x100); memcpy(ext + 0x00, sm5a_extended, 0x10); - return sm510_common_disasm(sm5a_mnemonic, ext, stream, pc, oprom, opram); + return common_disasm(sm5a_mnemonic, ext, stream, pc, opcodes, params, 6); } // SM590 disasm -static const u8 sm590_mnemonic[0x100] = +const u8 sm590_disassembler::sm590_mnemonic[0x100] = { /* 0 1 2 3 4 5 6 7 8 9 A B C D E F */ mNOP, mADX, mADX, mADX, mADX, mADX, mADX, mADX, mADX, mADX, mADX, mADX, mADX, mADX, mADX, mADX, // 0 @@ -358,7 +339,90 @@ static const u8 sm590_mnemonic[0x100] = }; -CPU_DISASSEMBLE(sm590) +offs_t sm590_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + return common_disasm(sm590_mnemonic, nullptr, stream, pc, opcodes, params, 7); +} + +u32 sm510_common_disassembler::opcode_alignment() const +{ + return 1; +} + +u32 sm510_common_disassembler::interface_flags() const +{ + return NONLINEAR_PC|PAGED2LEVEL; +} + +u32 sm510_common_disassembler::page_address_bits() const +{ + return 6; +} + +u32 sm510_common_disassembler::page2_address_bits() const +{ + return 4; +} + +offs_t sm510_common_disassembler::pc_linear_to_real(offs_t pc) const +{ + static const u8 l2r[64] = { + 0x00, 0x20, 0x30, 0x38, 0x3c, 0x3e, 0x1f, 0x2f, 0x37, 0x3b, 0x3d, 0x1e, 0x0f, 0x27, 0x33, 0x39, + 0x1c, 0x2e, 0x17, 0x2b, 0x35, 0x1a, 0x0d, 0x06, 0x03, 0x21, 0x10, 0x28, 0x34, 0x3a, 0x1d, 0x0e, + 0x07, 0x23, 0x31, 0x18, 0x2c, 0x36, 0x1b, 0x2d, 0x16, 0x0b, 0x25, 0x12, 0x09, 0x04, 0x22, 0x11, + 0x08, 0x24, 0x32, 0x19, 0x0c, 0x26, 0x13, 0x29, 0x14, 0x2a, 0x15, 0x0a, 0x05, 0x02, 0x01, 0x3f, + }; + return (pc & ~0x3f) | l2r[pc & 0x3f]; +} + +offs_t sm510_common_disassembler::pc_real_to_linear(offs_t pc) const +{ + static const u8 r2l[64] = { + 0x00, 0x3e, 0x3d, 0x18, 0x2d, 0x3c, 0x17, 0x20, 0x30, 0x2c, 0x3b, 0x29, 0x34, 0x16, 0x1f, 0x0c, + 0x1a, 0x2f, 0x2b, 0x36, 0x38, 0x3a, 0x28, 0x12, 0x23, 0x33, 0x15, 0x26, 0x10, 0x1e, 0x0b, 0x06, + 0x01, 0x19, 0x2e, 0x21, 0x31, 0x2a, 0x35, 0x0d, 0x1b, 0x37, 0x39, 0x13, 0x24, 0x27, 0x11, 0x07, + 0x02, 0x22, 0x32, 0x0e, 0x1c, 0x14, 0x25, 0x08, 0x03, 0x0f, 0x1d, 0x09, 0x04, 0x0a, 0x05, 0x3f, + }; + return (pc & ~0x3f) | r2l[pc & 0x3f]; +} + +u32 sm590_disassembler::page_address_bits() const +{ + return 7; +} + +u32 sm590_disassembler::page2_address_bits() const +{ + return 2; +} + +offs_t sm590_disassembler::pc_linear_to_real(offs_t pc) const +{ + static const u8 l2r[128] = { + 0x00, 0x40, 0x60, 0x70, 0x78, 0x7c, 0x7e, 0x3f, 0x5f, 0x6f, 0x77, 0x7b, 0x7d, 0x3e, 0x1f, 0x4f, + 0x67, 0x73, 0x79, 0x3c, 0x5e, 0x2f, 0x57, 0x6b, 0x75, 0x3a, 0x1d, 0x0e, 0x07, 0x43, 0x61, 0x30, + 0x58, 0x6c, 0x76, 0x3b, 0x5d, 0x2e, 0x17, 0x4b, 0x65, 0x32, 0x19, 0x0c, 0x46, 0x23, 0x51, 0x28, + 0x54, 0x6a, 0x35, 0x1a, 0x0d, 0x06, 0x03, 0x41, 0x20, 0x50, 0x68, 0x74, 0x7a, 0x3d, 0x1e, 0x0f, + 0x47, 0x63, 0x71, 0x38, 0x5c, 0x6e, 0x37, 0x5b, 0x6d, 0x36, 0x1b, 0x4d, 0x26, 0x13, 0x49, 0x24, + 0x52, 0x29, 0x14, 0x4a, 0x25, 0x12, 0x09, 0x04, 0x42, 0x21, 0x10, 0x48, 0x64, 0x72, 0x39, 0x1c, + 0x4e, 0x27, 0x53, 0x69, 0x34, 0x5a, 0x2d, 0x16, 0x0b, 0x45, 0x22, 0x11, 0x08, 0x44, 0x62, 0x31, + 0x18, 0x4c, 0x66, 0x33, 0x59, 0x2c, 0x56, 0x2b, 0x55, 0x2a, 0x15, 0x0a, 0x05, 0x02, 0x01, 0x7f, + }; + return (pc & ~0x7f) | l2r[pc & 0x7f]; +} + +offs_t sm590_disassembler::pc_real_to_linear(offs_t pc) const { - return sm510_common_disasm(sm590_mnemonic, nullptr, stream, pc, oprom, opram); + static const u8 r2l[128] = { + 0x00, 0x7e, 0x7d, 0x36, 0x57, 0x7c, 0x35, 0x1c, 0x6c, 0x56, 0x7b, 0x68, 0x2b, 0x34, 0x1b, 0x3f, + 0x5a, 0x6b, 0x55, 0x4d, 0x52, 0x7a, 0x67, 0x26, 0x70, 0x2a, 0x33, 0x4a, 0x5f, 0x1a, 0x3e, 0x0e, + 0x38, 0x59, 0x6a, 0x2d, 0x4f, 0x54, 0x4c, 0x61, 0x2f, 0x51, 0x79, 0x77, 0x75, 0x66, 0x25, 0x15, + 0x1f, 0x6f, 0x29, 0x73, 0x64, 0x32, 0x49, 0x46, 0x43, 0x5e, 0x19, 0x23, 0x13, 0x3d, 0x0d, 0x07, + 0x01, 0x37, 0x58, 0x1d, 0x6d, 0x69, 0x2c, 0x40, 0x5b, 0x4e, 0x53, 0x27, 0x71, 0x4b, 0x60, 0x0f, + 0x39, 0x2e, 0x50, 0x62, 0x30, 0x78, 0x76, 0x16, 0x20, 0x74, 0x65, 0x47, 0x44, 0x24, 0x14, 0x08, + 0x02, 0x1e, 0x6e, 0x41, 0x5c, 0x28, 0x72, 0x10, 0x3a, 0x63, 0x31, 0x17, 0x21, 0x48, 0x45, 0x09, + 0x03, 0x42, 0x5d, 0x11, 0x3b, 0x18, 0x22, 0x0a, 0x04, 0x12, 0x3c, 0x0b, 0x05, 0x0c, 0x06, 0x7f, + }; + return (pc & ~0x7f) | r2l[pc & 0x7f]; } + diff --git a/src/devices/cpu/sm510/sm510d.h b/src/devices/cpu/sm510/sm510d.h new file mode 100644 index 00000000000..899b8815334 --- /dev/null +++ b/src/devices/cpu/sm510/sm510d.h @@ -0,0 +1,131 @@ +// license:BSD-3-Clause +// copyright-holders:hap, Jonathan Gevaryahu +/* + + Sharp SM5xx MCU family disassembler + +*/ + +#ifndef MAME_CPU_SM510_SM510D_H +#define MAME_CPU_SM510_SM510D_H + +#pragma once + +class sm510_common_disassembler : public util::disasm_interface +{ +public: + sm510_common_disassembler() = default; + virtual ~sm510_common_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual u32 interface_flags() const override; + virtual u32 page_address_bits() const override; + virtual u32 page2_address_bits() const override; + virtual offs_t pc_linear_to_real(offs_t pc) const override; + virtual offs_t pc_real_to_linear(offs_t pc) const override; + +protected: + enum e_mnemonics + { + // SM510 common + mILL /* 0! */, mEXT, + mLB, mLBL, mSBM, mEXBLA, mINCB, mDECB, + mATPL, mRTN0, mRTN1, mTL, mTML, mTM, mT, + mEXC, mBDC, mEXCI, mEXCD, mLDA, mLAX, mPTW, mWR, mWS, + mKTA, mATBP, mATX, mATL, mATFC, mATR, + mADD, mADD11, mADX, mCOMA, mROT, mRC, mSC, + mTB, mTC, mTAM, mTMI, mTA0, mTABL, mTIS, mTAL, mTF1, mTF4, + mRM, mSM, + mPRE, mSME, mRME, mTMEL, + mSKIP, mCEND, mIDIV, mDR, mDTA, mCLKLO, mCLKHI, + + // SM500 common + mCOMCB, mRTN, mRTNS, mSSR, mTR, mTRS, mRBM, + mADDC, mPDTW, mTW, mDTW, + mATS, mEXKSA, mEXKFA, + mRMF, mSMF, mCOMCN, + mTA, mTM2, mTG, + + // SM590 aliases + mNOP, mCCTRL, mINBL, mDEBL, mXBLA, mADCS, mTR7, + // SM590 uniques + mTAX, mLBLX, mMTR, mSTR, mINBM, mDEBM, mRTA, mBLTA, mEXAX, mTBA, mADS, mADC, mLBMX, mTLS + }; + + static const char *const s_mnemonics[]; + static const u8 s_bits[]; + static const u32 s_flags[]; + + offs_t common_disasm(const u8 *lut_mnemonic, const u8 *lut_extended, std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms, const u8 pclen); +}; + +class sm510_disassembler : public sm510_common_disassembler +{ +public: + sm510_disassembler() = default; + virtual ~sm510_disassembler() = default; + + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const u8 sm510_mnemonic[0x100]; + +}; + +class sm511_disassembler : public sm510_common_disassembler +{ +public: + sm511_disassembler() = default; + virtual ~sm511_disassembler() = default; + + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const u8 sm511_mnemonic[0x100]; + static const u8 sm511_extended[0x10]; +}; + +class sm500_disassembler : public sm510_common_disassembler +{ +public: + sm500_disassembler() = default; + virtual ~sm500_disassembler() = default; + + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const u8 sm500_mnemonic[0x100]; + static const u8 sm500_extended[0x10]; +}; + +class sm5a_disassembler : public sm510_common_disassembler +{ +public: + sm5a_disassembler() = default; + virtual ~sm5a_disassembler() = default; + + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const u8 sm5a_mnemonic[0x100]; + static const u8 sm5a_extended[0x10]; +}; + +class sm590_disassembler : public sm510_common_disassembler +{ +public: + sm590_disassembler() = default; + virtual ~sm590_disassembler() = default; + + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + + virtual u32 page_address_bits() const override; + virtual u32 page2_address_bits() const override; + virtual offs_t pc_linear_to_real(offs_t pc) const override; + virtual offs_t pc_real_to_linear(offs_t pc) const override; + +private: + static const u8 sm590_mnemonic[0x100]; +}; + +#endif diff --git a/src/devices/cpu/sm510/sm511core.cpp b/src/devices/cpu/sm510/sm511core.cpp index 8ba41c19089..200740ee3e6 100644 --- a/src/devices/cpu/sm510/sm511core.cpp +++ b/src/devices/cpu/sm510/sm511core.cpp @@ -15,6 +15,7 @@ #include "emu.h" #include "sm510.h" +#include "sm510d.h" #include "debugger.h" @@ -43,10 +44,9 @@ ADDRESS_MAP_END // disasm -offs_t sm511_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +util::disasm_interface *sm511_device::create_disassembler() { - extern CPU_DISASSEMBLE(sm511); - return CPU_DISASSEMBLE_NAME(sm511)(this, stream, pc, oprom, opram, options); + return new sm511_disassembler; } diff --git a/src/devices/cpu/sm510/sm590.h b/src/devices/cpu/sm510/sm590.h index bdefb277207..c91b9287d63 100644 --- a/src/devices/cpu/sm510/sm590.h +++ b/src/devices/cpu/sm510/sm590.h @@ -101,7 +101,7 @@ protected: sm590_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, u32 clock, int stack_levels, int prgwidth, address_map_constructor program, int datawidth, address_map_constructor data); virtual void device_reset() override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; virtual bool wake_me_up() override; virtual void init_divider() override { } virtual void init_lcd_driver() override { } diff --git a/src/devices/cpu/sm510/sm590core.cpp b/src/devices/cpu/sm510/sm590core.cpp index 63544bf503f..c04e40d7461 100644 --- a/src/devices/cpu/sm510/sm590core.cpp +++ b/src/devices/cpu/sm510/sm590core.cpp @@ -13,6 +13,7 @@ #include "emu.h" #include "sm590.h" +#include "sm510d.h" #include "debugger.h" @@ -70,11 +71,9 @@ sm590_device::sm590_device(const machine_config &mconfig, device_type type, cons } -// disasm -offs_t sm590_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +util::disasm_interface *sm590_device::create_disassembler() { - extern CPU_DISASSEMBLE(sm590); - return CPU_DISASSEMBLE_NAME(sm590)(this, stream, pc, oprom, opram, options); + return new sm590_disassembler; } diff --git a/src/devices/cpu/sm510/sm5acore.cpp b/src/devices/cpu/sm510/sm5acore.cpp index 1fd23887227..427918fe1c1 100644 --- a/src/devices/cpu/sm510/sm5acore.cpp +++ b/src/devices/cpu/sm510/sm5acore.cpp @@ -11,6 +11,7 @@ #include "emu.h" #include "sm500.h" +#include "sm510d.h" #include "debugger.h" @@ -63,14 +64,12 @@ kb1013vk12_device::kb1013vk12_device(const machine_config &mconfig, const char * // disasm -offs_t sm5a_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +util::disasm_interface *sm5a_device::create_disassembler() { - extern CPU_DISASSEMBLE(sm5a); - return CPU_DISASSEMBLE_NAME(sm5a)(this, stream, pc, oprom, opram, options); + return new sm5a_disassembler; } - //------------------------------------------------- // execute //------------------------------------------------- diff --git a/src/devices/cpu/sm8500/sm8500.cpp b/src/devices/cpu/sm8500/sm8500.cpp index 654cc0d0db0..74d10aae658 100644 --- a/src/devices/cpu/sm8500/sm8500.cpp +++ b/src/devices/cpu/sm8500/sm8500.cpp @@ -21,6 +21,7 @@ they are internally. #include "emu.h" #include "sm8500.h" +#include "sm8500d.h" #include "debugger.h" @@ -348,10 +349,9 @@ void sm8500_cpu_device::process_interrupts() } -offs_t sm8500_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *sm8500_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( sm8500 ); - return CPU_DISASSEMBLE_NAME(sm8500)(this, stream, pc, oprom, opram, options); + return new sm8500_disassembler; } diff --git a/src/devices/cpu/sm8500/sm8500.h b/src/devices/cpu/sm8500/sm8500.h index 485d3a70ad8..ac9aea3fe82 100644 --- a/src/devices/cpu/sm8500/sm8500.h +++ b/src/devices/cpu/sm8500/sm8500.h @@ -74,9 +74,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 5; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; inline void get_sp(); uint8_t mem_readbyte(uint32_t offset) const; diff --git a/src/devices/cpu/sm8500/sm8500d.cpp b/src/devices/cpu/sm8500/sm8500d.cpp index 1b8b7dd2392..3d6139ef8ed 100644 --- a/src/devices/cpu/sm8500/sm8500d.cpp +++ b/src/devices/cpu/sm8500/sm8500d.cpp @@ -10,31 +10,9 @@ Sharp sm8500 CPU disassembly *******************************************************************/ #include "emu.h" -#include "debugger.h" -#include "sm8500.h" +#include "sm8500d.h" -enum e_mnemonics -{ - zADC=0, zADCW, zADD, zADDW, zAND, zANDW, zBAND, zBBC, zBBS, - zBCLR, zBCMP, zBMOV, zBOR, zBR, zBTST, zBSET, zBXOR, zCALL, zCALS, zCLR, - zCLRC, zCMP, zCMPW, zCOM, zCOMC, zDA, zDBNZ, zDEC, - zDECW, zDI, zDIV, zEI, zEXTS, zHALT, zINC, zINCW, - zIRET, zJMP, zMOV, zMOVM, zMOVW, zMULT, zNEG, zNOP, zOR, - zORW, zPOP, zPOPW, zPUSH, zPUSHW, zRET, zRL, zRLC, - zRR, zRRC, zSBC, zSBCW, zSETC, zSLL, zSRA, zSRL, zSTOP, - zSUB, zSUBW, zSWAP, zXOR, zXORW, zMOVPS0, zINVLD, zDM, -/* unknowns */ -z5A, z5B, - -/* more complicated instructions */ -z1A, z1B, z4F -}; - -/* instructions not found: -5A, 5B, -*/ - -static const char *const s_mnemonic[] = +const char *const sm8500_disassembler::s_mnemonic[] = { "adc", "adcw", "add", "addw", "and", "andw", "band", "bbc", "bbs", "bclr", "bcmp", "bmov", "bor", "br", "btst", "bset", "bxor", "call", "cals", "clr", @@ -51,45 +29,29 @@ static const char *const s_mnemonic[] = "comp1A", "comp1B", "comp4F", }; -#define _OVER DASMFLAG_STEP_OVER -#define _OUT DASMFLAG_STEP_OUT - -static const uint32_t s_flags[] = { +const uint32_t sm8500_disassembler::s_flags[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, _OVER, _OVER, 0, - 0, 0, 0, 0, 0, 0, _OVER, 0, - 0, 0, 0, 0, 0, _OVER, 0, 0, - _OUT, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, _OUT, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, STEP_OVER, STEP_OVER, 0, + 0, 0, 0, 0, 0, 0, STEP_OVER, 0, + 0, 0, 0, 0, 0, STEP_OVER, 0, 0, + STEP_OUT, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, STEP_OUT, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; -struct sm8500dasm -{ - uint8_t mnemonic; - uint8_t arguments; -}; - -static const char *const sm8500_cond[16] = { +const char *const sm8500_disassembler::sm8500_cond[16] = { "F", "LT", "LE", "ULE", "OV", "MI", "Z", "C", "T", "GE", "GT", "UGT", "NOV", "PL", "NZ", "NC" }; -static const uint8_t sm8500_b2w[8] = { +const uint8_t sm8500_disassembler::sm8500_b2w[8] = { 0, 8, 2, 10, 4, 12, 6, 14 }; -enum e_addrmodes { - AM_R=1, AM_rr, AM_r1, AM_S, AM_rmb, AM_mbr, AM_Ri, AM_rmw, AM_mwr, AM_smw, AM_mws, - AM_Sw, AM_iR, AM_rbr, AM_riw, AM_cjp, AM_rib, AM_pi, AM_cbr, AM_i, AM_ii, - AM_ss, AM_RR, AM_2, AM_SS, AM_bR, AM_Rbr, AM_Rb, AM_rR, AM_Rr, AM_Rii, AM_RiR, - AM_riB, AM_iS, AM_CALS, AM_bid, AM_1A, AM_1B, AM_4F -}; - -static const sm8500dasm mnemonic[256] = { +const sm8500_disassembler::sm8500dasm sm8500_disassembler::mnemonic[256] = { /* 00 - 0F */ {zCLR, AM_R}, {zNEG,AM_R}, {zCOM,AM_R}, {zRR,AM_R}, {zRL, AM_R}, {zRRC,AM_R}, {zRLC,AM_R}, {zSRL,AM_R}, @@ -173,16 +135,21 @@ static const sm8500dasm mnemonic[256] = { }; -CPU_DISASSEMBLE(sm8500) +u32 sm8500_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t sm8500_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { const sm8500dasm *instr; uint8_t op; int8_t offset; uint16_t ea; uint16_t ea2; - int pos = 0; + offs_t pos = pc; - op = oprom[pos++]; + op = opcodes.r8(pos++); instr = &mnemonic[op]; @@ -193,34 +160,34 @@ CPU_DISASSEMBLE(sm8500) } switch( instr->arguments ) { case AM_R: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); util::stream_format(stream, "R%02Xh", ea); break; case AM_iR: - util::stream_format(stream, "R%02Xh, $%02X", oprom[pos + 1], oprom[pos + 0]); + util::stream_format(stream, "R%02Xh, $%02X", opcodes.r8(pos+1), opcodes.r8(pos)); pos += 2; break; case AM_iS: - util::stream_format(stream, "RR%02Xh, $%02X", oprom[pos + 1], oprom[pos + 0]); + util::stream_format(stream, "RR%02Xh, $%02X", opcodes.r8(pos+1), opcodes.r8(pos)); pos += 2; break; case AM_Sw: - ea2 = oprom[pos++]; - ea = oprom[pos++] << 8; - ea += oprom[pos++]; + ea2 = opcodes.r8(pos++); + ea = opcodes.r8(pos++) << 8; + ea += opcodes.r8(pos++); util::stream_format(stream, "RR%02Xh, $%04X", ea2, ea); break; case AM_rib: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); util::stream_format(stream, "r%02Xh, $%02X", op & 0x07, ea); break; case AM_riw: - ea = oprom[pos++] << 8; - ea += oprom[pos++]; + ea = opcodes.r8(pos++) << 8; + ea += opcodes.r8(pos++); util::stream_format(stream, "rr%02Xh, $%04X", sm8500_b2w[op & 0x07], ea); break; case AM_rmb: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); util::stream_format(stream, "r%02Xh,", ( ea >> 3 ) & 0x07); switch( ea & 0xC0 ) { case 0x00: @@ -228,7 +195,7 @@ CPU_DISASSEMBLE(sm8500) case 0x40: util::stream_format(stream, "(r%02Xh)+", ea & 0x07); break; case 0x80: - ea2 = oprom[pos++]; + ea2 = opcodes.r8(pos++); if ( ea & 0x07 ) { util::stream_format(stream, "$%02X(r%02Xh)", ea2, ea & 0x07); } else { @@ -240,14 +207,14 @@ CPU_DISASSEMBLE(sm8500) } break; case AM_mbr: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); switch( ea & 0xC0 ) { case 0x00: util::stream_format(stream, "@r%02Xh", ea & 0x07); break; case 0x40: util::stream_format(stream, "(r%02Xh)+", ea & 0x07); break; case 0x80: - ea2 = oprom[pos++]; + ea2 = opcodes.r8(pos++); if ( ea & 0x07 ) { util::stream_format(stream, "$%02X(r%02Xh)", ea2, ea & 0x07); } else { @@ -260,7 +227,7 @@ CPU_DISASSEMBLE(sm8500) util::stream_format(stream, ",r%02Xh", ( ea >> 3 ) & 0x07); break; case AM_rmw: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); util::stream_format(stream, "r%02Xh,", ( ea >> 3 ) & 0x07); switch( ea & 0xC0 ) { case 0x00: @@ -268,8 +235,8 @@ CPU_DISASSEMBLE(sm8500) case 0x40: util::stream_format(stream, "(rr%02Xh)+", sm8500_b2w[ea & 0x07]); break; case 0x80: - ea2 = oprom[pos++] << 8; - ea2 += oprom[pos++]; + ea2 = opcodes.r8(pos++) << 8; + ea2 += opcodes.r8(pos++); if ( ea & 0x07 ) { util::stream_format(stream, "$%04X(rr%02Xh)", ea2, sm8500_b2w[ea & 0x07]); } else { @@ -281,15 +248,15 @@ CPU_DISASSEMBLE(sm8500) } break; case AM_mwr: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); switch( ea & 0xC0 ) { case 0x00: util::stream_format(stream, "@rr%02Xh", sm8500_b2w[ea & 0x07]); break; case 0x40: util::stream_format(stream, "(rr%02Xh)+", sm8500_b2w[ea & 0x07]); break; case 0x80: - ea2 = oprom[pos++] << 8; - ea2 += oprom[pos++]; + ea2 = opcodes.r8(pos++) << 8; + ea2 += opcodes.r8(pos++); if ( ea & 0x07 ) { util::stream_format(stream, "$%04X(rr%02Xh)", ea2, sm8500_b2w[ea & 0x07]); } else { @@ -302,7 +269,7 @@ CPU_DISASSEMBLE(sm8500) util::stream_format(stream, ",r%02Xh", ( ea >> 3 ) & 0x07); break; case AM_smw: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); util::stream_format(stream, "rr%02Xh,", sm8500_b2w[( ea >> 3 ) & 0x07]); switch( ea & 0xC0 ) { case 0x00: @@ -310,8 +277,8 @@ CPU_DISASSEMBLE(sm8500) case 0x40: util::stream_format(stream, "(rr%02Xh)+", sm8500_b2w[ea & 0x07]); break; case 0x80: - ea2 = oprom[pos++] << 8; - ea2 += oprom[pos++]; + ea2 = opcodes.r8(pos++) << 8; + ea2 += opcodes.r8(pos++); if ( ea & 0x07 ) { util::stream_format(stream, "$%04X(rr%02Xh)", ea2, sm8500_b2w[ea & 0x07]); } else { @@ -323,15 +290,15 @@ CPU_DISASSEMBLE(sm8500) } break; case AM_mws: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); switch( ea & 0xC0 ) { case 0x00: util::stream_format(stream, "@rr%02Xh", sm8500_b2w[ea & 0x07]); break; case 0x40: util::stream_format(stream, "(rr%02Xh)+", sm8500_b2w[ea & 0x07]); break; case 0x80: - ea2 = oprom[pos++] << 8; - ea2 += oprom[pos++]; + ea2 = opcodes.r8(pos++) << 8; + ea2 += opcodes.r8(pos++); if ( ea & 0x07 ) { util::stream_format(stream, "$%04X(rr%02Xh)", ea2, sm8500_b2w[ea & 0x07]); } else { @@ -344,20 +311,20 @@ CPU_DISASSEMBLE(sm8500) util::stream_format(stream, ",rr%02Xh", sm8500_b2w[( ea >> 3 ) & 0x07]); break; case AM_cbr: - offset = (int8_t) oprom[pos++]; + offset = (int8_t) opcodes.r8(pos++); util::stream_format(stream, "%s,$%04X", sm8500_cond[ op & 0x0F ], pc + pos + offset); break; case AM_rbr: - offset = (int8_t) oprom[pos++]; + offset = (int8_t) opcodes.r8(pos++); util::stream_format(stream, "r%02Xh,$%04X", op & 0x07, pc + pos + offset); break; case AM_cjp: - ea = oprom[pos++] << 8; - ea += oprom[pos++]; + ea = opcodes.r8(pos++) << 8; + ea += opcodes.r8(pos++); util::stream_format(stream, "%s,$%04X", sm8500_cond[ op & 0x0F], ea); break; case AM_rr: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); switch( ea & 0xc0 ) { case 0x00: util::stream_format(stream, "r%02Xh,r%02Xh", (ea >> 3 ) & 0x07, ea & 0x07); @@ -370,7 +337,7 @@ CPU_DISASSEMBLE(sm8500) } break; case AM_r1: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); switch( ea & 0xC0 ) { case 0x00: util::stream_format(stream, "@r%02Xh", (ea >> 3 ) & 0x07); @@ -383,29 +350,29 @@ CPU_DISASSEMBLE(sm8500) } break; case AM_S: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); util::stream_format(stream, "RR%02Xh", ea); break; case AM_pi: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); util::stream_format(stream, "r%02Xh, $%02X", 0x10 + (op & 0x07), ea); break; case AM_Ri: - ea = oprom[pos++]; - ea2 = oprom[pos++]; + ea = opcodes.r8(pos++); + ea2 = opcodes.r8(pos++); util::stream_format(stream, "R%02Xh,$%02X", ea, ea2); break; case AM_i: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); util::stream_format(stream, "$%02X", ea); break; case AM_ii: - ea = oprom[pos++] << 8; - ea += oprom[pos++]; + ea = opcodes.r8(pos++) << 8; + ea += opcodes.r8(pos++); util::stream_format(stream, "$%04X", ea); break; case AM_ss: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); switch( ea & 0xC0 ) { case 0x00: util::stream_format(stream, "rr%02Xh,rr%02Xh", sm8500_b2w[( ea >> 3 ) & 0x07], sm8500_b2w[ea & 0x07]); break; @@ -418,18 +385,18 @@ CPU_DISASSEMBLE(sm8500) } break; case AM_RR: - ea = oprom[pos++]; - ea2 = oprom[pos++]; + ea = opcodes.r8(pos++); + ea2 = opcodes.r8(pos++); util::stream_format(stream, "R%02Xh,R%02Xh", ea2, ea); break; case AM_2: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); switch( ea & 0xC0 ) { case 0x00: util::stream_format(stream, "rr%02Xh", sm8500_b2w[ea & 0x07]); break; case 0x40: - ea2 = oprom[pos++] << 8; - ea2 += oprom[pos++]; + ea2 = opcodes.r8(pos++) << 8; + ea2 += opcodes.r8(pos++); if ( ea & 0x38 ) { util::stream_format(stream, "@$%04X(r%02Xh)", ea2, ( ea >> 3 ) & 0x07); } else { @@ -443,13 +410,13 @@ CPU_DISASSEMBLE(sm8500) } break; case AM_SS: - ea = oprom[pos++]; - ea2 = oprom[pos++]; + ea = opcodes.r8(pos++); + ea2 = opcodes.r8(pos++); util::stream_format(stream, "RR%02Xh,RR%02Xh", ea2, ea); break; case AM_bR: - ea = oprom[pos++]; - ea2 = oprom[pos++]; + ea = opcodes.r8(pos++); + ea2 = opcodes.r8(pos++); switch( ea & 0xC0 ) { case 0x00: util::stream_format(stream, "BF,R%02Xh,#%d", ea2, ea & 0x07); break; @@ -462,41 +429,41 @@ CPU_DISASSEMBLE(sm8500) } break; case AM_Rbr: - ea = oprom[pos++]; - offset = (int8_t) oprom[pos++]; + ea = opcodes.r8(pos++); + offset = (int8_t) opcodes.r8(pos++); util::stream_format(stream, "R%02Xh,#%d,$%04X", ea, op & 0x07, pc + pos + offset); break; case AM_Rb: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); util::stream_format(stream, "R%02Xh,#%d", ea, op&0x07); break; case AM_rR: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); util::stream_format(stream, "r%02Xh,R%02Xh", op & 0x07, ea); break; case AM_Rr: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); util::stream_format(stream, "R%02Xh,r%02Xh", ea, op & 0x07); break; case AM_Rii: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); util::stream_format(stream, "R%02Xh,", ea); - ea = oprom[pos++]; + ea = opcodes.r8(pos++); util::stream_format(stream, "$%02X,", ea); - ea = oprom[pos++]; + ea = opcodes.r8(pos++); util::stream_format(stream, "$%02X", ea); break; case AM_RiR: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); util::stream_format(stream, "R%02Xh,", ea); - ea = oprom[pos++]; + ea = opcodes.r8(pos++); util::stream_format(stream, "$%02X,", ea); - ea = oprom[pos++]; + ea = opcodes.r8(pos++); util::stream_format(stream, "R%02Xh", ea); break; case AM_riB: - ea = oprom[pos++]; - ea2 = oprom[pos++]; + ea = opcodes.r8(pos++); + ea2 = opcodes.r8(pos++); switch( ea & 0xC0 ) { case 0x00: util::stream_format(stream, "#%2x(r%02Xh),#%d", ea2, ea >> 3, ea & 0x07); @@ -510,23 +477,23 @@ CPU_DISASSEMBLE(sm8500) } break; case AM_CALS: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); util::stream_format(stream, "$%04X", 0x1000 | ( ( op & 0x0f ) << 8 ) | ea); break; case AM_bid: - ea = oprom[pos++]; - ea2 = oprom[pos++]; + ea = opcodes.r8(pos++); + ea2 = opcodes.r8(pos++); if ( ea & 0x38 ) { util::stream_format(stream, "$%02X(r%02Xh)", ea2, ( ea >> 3 ) & 0x07); } else { util::stream_format(stream, "$%04X", 0xFF00 + ea2); } util::stream_format(stream, ",#%d,", ea & 0x07); - offset = (int8_t) oprom[pos++]; + offset = (int8_t) opcodes.r8(pos++); util::stream_format(stream, "$%04X", pc + pos + offset); break; case AM_1A: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); switch( ea & 0x07 ) { case 0x00: util::stream_format(stream, "%-4s ", s_mnemonic[ zCLR ]); break; case 0x01: util::stream_format(stream, "%-4s ", s_mnemonic[ zNEG ]); break; @@ -540,7 +507,7 @@ CPU_DISASSEMBLE(sm8500) util::stream_format(stream, "@r%02Xh", ( ea >> 3 ) & 0x07); break; case AM_1B: - ea = oprom[pos++]; + ea = opcodes.r8(pos++); switch( ea & 0x07 ) { case 0x00: util::stream_format(stream, "%-4s ", s_mnemonic[ zINC ]); break; case 0x01: util::stream_format(stream, "%-4s ", s_mnemonic[ zDEC ]); break; @@ -554,8 +521,8 @@ CPU_DISASSEMBLE(sm8500) util::stream_format(stream, "@r%02Xh", ( ea >> 3 ) & 0x07); break; case AM_4F: - ea = oprom[pos++]; - ea2 = oprom[pos++]; + ea = opcodes.r8(pos++); + ea2 = opcodes.r8(pos++); switch( ea & 0xc0 ) { case 0x00: util::stream_format(stream, "%-4s ", s_mnemonic[ zBCMP ]); break; case 0x40: util::stream_format(stream, "%-4s ", s_mnemonic[ zBAND ]); break; @@ -577,5 +544,5 @@ CPU_DISASSEMBLE(sm8500) util::stream_format(stream, "%s", s_mnemonic[ instr->mnemonic ]); } - return pos | s_flags[instr->mnemonic] | DASMFLAG_SUPPORTED; + return (pos - pc) | s_flags[instr->mnemonic] | SUPPORTED; } diff --git a/src/devices/cpu/sm8500/sm8500d.h b/src/devices/cpu/sm8500/sm8500d.h new file mode 100644 index 00000000000..8d425b86c19 --- /dev/null +++ b/src/devices/cpu/sm8500/sm8500d.h @@ -0,0 +1,68 @@ +// license:BSD-3-Clause +// copyright-holders:Wilbert Pol +/******************************************************************* + +sm8500d.c +Sharp sm8500 CPU disassembly + + + +*******************************************************************/ + +#ifndef MAME_CPU_SM8500_SM8500D_H +#define MAME_CPU_SM8500_SM8500D_H + +#pragma once + +class sm8500_disassembler : public util::disasm_interface +{ +public: + sm8500_disassembler() = default; + virtual ~sm8500_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum e_mnemonics + { + zADC=0, zADCW, zADD, zADDW, zAND, zANDW, zBAND, zBBC, zBBS, + zBCLR, zBCMP, zBMOV, zBOR, zBR, zBTST, zBSET, zBXOR, zCALL, zCALS, zCLR, + zCLRC, zCMP, zCMPW, zCOM, zCOMC, zDA, zDBNZ, zDEC, + zDECW, zDI, zDIV, zEI, zEXTS, zHALT, zINC, zINCW, + zIRET, zJMP, zMOV, zMOVM, zMOVW, zMULT, zNEG, zNOP, zOR, + zORW, zPOP, zPOPW, zPUSH, zPUSHW, zRET, zRL, zRLC, + zRR, zRRC, zSBC, zSBCW, zSETC, zSLL, zSRA, zSRL, zSTOP, + zSUB, zSUBW, zSWAP, zXOR, zXORW, zMOVPS0, zINVLD, zDM, + /* unknowns */ + z5A, z5B, + + /* more complicated instructions */ + z1A, z1B, z4F + }; + + /* instructions not found: + 5A, 5B, + */ + + enum e_addrmodes { + AM_R=1, AM_rr, AM_r1, AM_S, AM_rmb, AM_mbr, AM_Ri, AM_rmw, AM_mwr, AM_smw, AM_mws, + AM_Sw, AM_iR, AM_rbr, AM_riw, AM_cjp, AM_rib, AM_pi, AM_cbr, AM_i, AM_ii, + AM_ss, AM_RR, AM_2, AM_SS, AM_bR, AM_Rbr, AM_Rb, AM_rR, AM_Rr, AM_Rii, AM_RiR, + AM_riB, AM_iS, AM_CALS, AM_bid, AM_1A, AM_1B, AM_4F + }; + + struct sm8500dasm + { + uint8_t mnemonic; + uint8_t arguments; + }; + + static const char *const s_mnemonic[]; + static const uint32_t s_flags[]; + static const char *const sm8500_cond[16]; + static const uint8_t sm8500_b2w[8]; + static const sm8500dasm mnemonic[256]; +}; + +#endif diff --git a/src/devices/cpu/sparc/mb86901.cpp b/src/devices/cpu/sparc/mb86901.cpp index 1f6430835f4..cc2e00750ea 100644 --- a/src/devices/cpu/sparc/mb86901.cpp +++ b/src/devices/cpu/sparc/mb86901.cpp @@ -43,7 +43,6 @@ const int mb86901_device::NWINDOWS = 7; mb86901_device::mb86901_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) : cpu_device(mconfig, MB86901, tag, owner, clock) , m_program_config("program", ENDIANNESS_BIG, 32, 32) - , m_dasm(this, 7) { } @@ -520,36 +519,15 @@ void mb86901_device::state_string_export(const device_state_entry &entry, std::s //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t mb86901_device::disasm_min_opcode_bytes() const -{ - return 4; -} - - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t mb86901_device::disasm_max_opcode_bytes() const -{ - return 4; -} - - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t mb86901_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *mb86901_device::create_disassembler() { - uint32_t op = *reinterpret_cast(oprom); - return m_dasm.dasm(stream, pc, big_endianize_int32(op)); + auto dasm = new sparc_disassembler(this, 7); + m_asi_desc_adder(dasm); + return dasm; } diff --git a/src/devices/cpu/sparc/sparc.h b/src/devices/cpu/sparc/sparc.h index 5355a2ed005..8d91183ee1a 100644 --- a/src/devices/cpu/sparc/sparc.h +++ b/src/devices/cpu/sparc/sparc.h @@ -20,9 +20,9 @@ // TODO: when there are more SPARC CPUs, move setter to a base class #define MCFG_SPARC_ADD_ASI_DESC(desc) \ - mb86901_device::add_asi_desc(*device, desc); + mb86901_device::add_asi_desc(*device, [](sparc_disassembler *dasm) { dasm->add_asi_desc(desc); }); -class mb86901_device : public cpu_device, protected sparc_debug_state +class mb86901_device : public cpu_device, protected sparc_disassembler::config { public: mb86901_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); @@ -43,9 +43,7 @@ public: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // device_state_interface overrides virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; @@ -53,7 +51,7 @@ public: uint8_t get_asi() { return m_asi; } uint32_t pc() { return m_pc; } - template static void add_asi_desc(device_t &device, const T &desc) { return downcast(device).add_asi_desc(desc); } + static void add_asi_desc(device_t &device, std::function f) { downcast(device).m_asi_desc_adder = f; } #if LOG_FCODES void enable_log_fcodes(bool enable) { m_log_fcodes = enable; } @@ -62,8 +60,6 @@ public: #endif protected: - template void add_asi_desc(const T &desc) { m_dasm.add_asi_desc(desc); } - void update_gpr_pointers(); void execute_add(uint32_t op); @@ -213,7 +209,6 @@ protected: // debugger helpers uint32_t m_dbgregs[24]; - sparc_disassembler m_dasm; // address spaces address_space *m_program; @@ -230,6 +225,8 @@ protected: // processor configuration static const int NWINDOWS; + + std::function m_asi_desc_adder; }; // device type definition diff --git a/src/devices/cpu/sparc/sparcdasm.cpp b/src/devices/cpu/sparc/sparcdasm.cpp index 296c987a467..584b5ab427a 100644 --- a/src/devices/cpu/sparc/sparcdasm.cpp +++ b/src/devices/cpu/sparc/sparcdasm.cpp @@ -17,10 +17,10 @@ namespace { int32_t get_disp19(uint32_t op) { return DISP19; } int32_t get_disp22(uint32_t op) { return DISP19; } - const char *bicc_comment(const sparc_debug_state *state, bool use_cc, offs_t pc, uint32_t op) + const char *bicc_comment(const sparc_disassembler::config *conf, bool use_cc, offs_t pc, uint32_t op) { - if (!state || (state->get_translated_pc() != pc)) return nullptr; - auto const cc((use_cc && (BRCC & 0x2)) ? state->get_xcc() : state->get_icc()); + if (!conf || (conf->get_translated_pc() != pc)) return nullptr; + auto const cc((use_cc && (BRCC & 0x2)) ? conf->get_xcc() : conf->get_icc()); switch (COND) { case 0x0: return "will fall through"; @@ -42,10 +42,10 @@ namespace { } return nullptr; } - const char *bfcc_comment(const sparc_debug_state *state, bool use_cc, offs_t pc, uint32_t op) + const char *bfcc_comment(const sparc_disassembler::config *conf, bool use_cc, offs_t pc, uint32_t op) { - if (!state || (state->get_translated_pc() != pc)) return nullptr; - auto const fcc(state->get_fcc(use_cc ? BRCC : 0)); + if (!conf || (conf->get_translated_pc() != pc)) return nullptr; + auto const fcc(conf->get_fcc(use_cc ? BRCC : 0)); switch (COND) { case 0x0: return "will fall through"; @@ -67,10 +67,10 @@ namespace { } return nullptr; } - const char *bpr_comment(const sparc_debug_state *state, bool use_cc, offs_t pc, uint32_t op) + const char *bpr_comment(const sparc_disassembler::config *conf, bool use_cc, offs_t pc, uint32_t op) { - if (!state || (state->get_translated_pc() != pc)) return nullptr; - const int64_t reg(state->get_reg_r(RS1)); + if (!conf || (conf->get_translated_pc() != pc)) return nullptr; + const int64_t reg(conf->get_reg_r(RS1)); switch (COND) { case 1: return (reg == 0) ? "will branch" : "will fall through"; @@ -610,12 +610,12 @@ inline void sparc_disassembler::pad_op_field(std::ostream &stream, std::streampo stream << ' '; } -sparc_disassembler::sparc_disassembler(const sparc_debug_state *state, unsigned version) - : sparc_disassembler(state, version, vis_none) +sparc_disassembler::sparc_disassembler(const config *conf, unsigned version) + : sparc_disassembler(conf, version, vis_none) { } -sparc_disassembler::sparc_disassembler(const sparc_debug_state *state, unsigned version, vis_level vis) +sparc_disassembler::sparc_disassembler(const config *conf, unsigned version, vis_level vis) : m_version(version) , m_vis_level(vis) , m_op_field_width(9) @@ -722,6 +722,15 @@ sparc_disassembler::sparc_disassembler(const sparc_debug_state *state, unsigned } } +u32 sparc_disassembler::opcode_alignment() const +{ + return 4; +} + +offs_t sparc_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + return dasm(stream, pc, opcodes.r32(pc)); +} offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) const { @@ -742,10 +751,10 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co default: return dasm_branch(stream, pc, op); } - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; case 1: util::stream_format(stream, "%-*s%%pc%c0x%08x ! 0x%08x", m_op_field_width, "call", (DISP30 < 0) ? '-' : '+', std::abs(DISP30), pc + DISP30); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; case 2: switch (OP3) { @@ -754,7 +763,7 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co { if (SIMM13 == 1) util::stream_format(stream, "%-*s%s", m_op_field_width, "inc", REG_NAMES[RD]); else util::stream_format(stream, "%-*s%d,%s", m_op_field_width, "inc", SIMM13, REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x02: @@ -763,13 +772,13 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co if (USEIMM) util::stream_format(stream, "%-*s%d,%s", m_op_field_width, "mov", SIMM13, REG_NAMES[RD]); else if (RS2 == 0) util::stream_format(stream, "%-*s%s", m_op_field_width, "clr", REG_NAMES[RD]); else util::stream_format(stream, "%-*s%s,%s", m_op_field_width, "mov", REG_NAMES[RS2], REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } else if (RS1 == RD) { if (USEIMM) util::stream_format(stream, "%-*s0x%08x,%s", m_op_field_width, "bset", SIMM13, REG_NAMES[RD]); else util::stream_format(stream, "%-*s%s,%s", m_op_field_width, "bset", REG_NAMES[RS2], REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x03: @@ -777,7 +786,7 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co { if (USEIMM) util::stream_format(stream, "%-*s0x%08x,%s", m_op_field_width, "btog", SIMM13, REG_NAMES[RD]); else util::stream_format(stream, "%-*s%s,%s", m_op_field_width, "btog", REG_NAMES[RS2], REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x04: @@ -787,7 +796,7 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co { if (SIMM13 == 1) util::stream_format(stream, "%-*s%s", m_op_field_width, "dec", REG_NAMES[RD]); else util::stream_format(stream, "%-*s%d,%s", m_op_field_width, "dec", SIMM13, REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } } else @@ -796,7 +805,7 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co { if (RS2 == RD) util::stream_format(stream, "%-*s%s", m_op_field_width, "neg", REG_NAMES[RD]); else util::stream_format(stream, "%-*s%s,%s", m_op_field_width, "neg", REG_NAMES[RS2], REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } } break; @@ -805,7 +814,7 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co { if (USEIMM) util::stream_format(stream, "%-*s0x%08x,%s", m_op_field_width, "bclr", SIMM13, REG_NAMES[RD]); else util::stream_format(stream, "%-*s%s,%s", m_op_field_width, "bclr", REG_NAMES[RS2], REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x07: @@ -813,7 +822,7 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co { if (RS1 == RD) util::stream_format(stream, "%-*s%s", m_op_field_width, "not", REG_NAMES[RD]); else util::stream_format(stream, "%-*s%s,%s", m_op_field_width, "not", REG_NAMES[RS1], REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x10: @@ -821,14 +830,14 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co { if (SIMM13 == 1) util::stream_format(stream, "%-*s%s", m_op_field_width, "inccc", REG_NAMES[RD]); else util::stream_format(stream, "%-*s%d,%s", m_op_field_width, "inccc", SIMM13, REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x12: if (!USEIMM && (RS1 == 0) && (RD == 0)) { util::stream_format(stream, "%-*s%s", m_op_field_width, "tst", REG_NAMES[RS2]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x14: @@ -836,7 +845,7 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co { if (SIMM13 == 1) util::stream_format(stream, "%-*s%s", m_op_field_width, "deccc", REG_NAMES[RD]); else util::stream_format(stream, "%-*s%d,%s", m_op_field_width, "deccc", SIMM13, REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x25: @@ -851,7 +860,7 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co if (m_version <= 8) { util::stream_format(stream, "%-*s%%psr,%s", m_op_field_width, "rd", REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x2a: @@ -860,13 +869,13 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co if (V9_PRIV_REG_NAMES[RS1]) { util::stream_format(stream, "%-*s%s,%s", m_op_field_width, "rdpr", V9_PRIV_REG_NAMES[RS1], REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } } else { util::stream_format(stream, "%-*s%%wim,%s", m_op_field_width, "rd", REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x2b: @@ -875,13 +884,13 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co if (!USEIMM) { util::stream_format(stream, "flushw"); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } } else { util::stream_format(stream, "%-*s%%tbr,%s", m_op_field_width, "rd", REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x2c: @@ -891,7 +900,7 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co { if (USEIMM) util::stream_format(stream, "%-*s%d,%s", m_op_field_width, "popc", SIMM13, REG_NAMES[RD]); else util::stream_format(stream, "%-*s%s,%s", m_op_field_width, "popc", REG_NAMES[RS2], REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x2f: @@ -905,10 +914,10 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co { case 0: util::stream_format(stream, "saved"); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; case 1: util::stream_format(stream, "restored"); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } } else @@ -923,7 +932,7 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co if (USEIMM) util::stream_format(stream, "%-*s%s,0x%08x,%%psr", m_op_field_width, "wr", REG_NAMES[RS1], SIMM13); else util::stream_format(stream, "%-*s%s,%s,%%psr", m_op_field_width, "wr", REG_NAMES[RS1], REG_NAMES[RS2]); } - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x32: @@ -935,7 +944,7 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co if (!USEIMM) util::stream_format(stream, "%-*s%s,%s,%s", m_op_field_width, "wrpr", REG_NAMES[RS1], REG_NAMES[RS2], V9_PRIV_REG_NAMES[RD]); else if (RS1 == 0) util::stream_format(stream, "%-*s0x%08x,%s", m_op_field_width, "wrpr", SIMM13, V9_PRIV_REG_NAMES[RD]); else util::stream_format(stream, "%-*s%s,0x%08x,%s", m_op_field_width, "wrpr", REG_NAMES[RS1], SIMM13, V9_PRIV_REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } } else @@ -950,7 +959,7 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co if (USEIMM) util::stream_format(stream, "%-*s%s,0x%08x,%%wim", m_op_field_width, "wr", REG_NAMES[RS1], SIMM13); else util::stream_format(stream, "%-*s%s,%s,%%wim", m_op_field_width, "wr", REG_NAMES[RS1], REG_NAMES[RS2]); } - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x33: @@ -966,7 +975,7 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co if (USEIMM) util::stream_format(stream, "%-*s%s,0x%08x,%%tbr", m_op_field_width, "wr", REG_NAMES[RS1], SIMM13); else util::stream_format(stream, "%-*s%s,%s,%%tbr", m_op_field_width, "wr", REG_NAMES[RS1], REG_NAMES[RS2]); } - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x34: @@ -989,21 +998,21 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co { util::stream_format(stream, "%-*s", m_op_field_width, "flush"); dasm_address(stream, op); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x3c: if (!USEIMM && (RS1 == RS2) && (RS2 == RD) && (RD == 0)) { util::stream_format(stream, "save"); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x3d: if (!USEIMM && (RS1 == RS2) && (RS2 == RD) && (RD == 0)) { util::stream_format(stream, "restore"); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x3e: @@ -1011,8 +1020,8 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co { switch (RD) { - case 0: util::stream_format(stream, "done"); return 4 | DASMFLAG_SUPPORTED; - case 1: util::stream_format(stream, "retry"); return 4 | DASMFLAG_SUPPORTED; + case 0: util::stream_format(stream, "done"); return 4 | SUPPORTED; + case 1: util::stream_format(stream, "retry"); return 4 | SUPPORTED; } } break; @@ -1039,7 +1048,7 @@ offs_t sparc_disassembler::dasm(std::ostream &stream, offs_t pc, uint32_t op) co else util::stream_format(stream, "%-*s%s,%d,%s", m_op_field_width, it->second.mnemonic, REG_NAMES[RS1], SIMM13, REG_NAMES[RD]); } - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } } break; @@ -1072,7 +1081,7 @@ offs_t sparc_disassembler::dasm_invalid(std::ostream &stream, offs_t pc, uint32_ { util::stream_format(stream, "op=%x op3=%02x i=%01x rd=%d", OP, OP3, USEIMM, RD); } - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } @@ -1089,10 +1098,10 @@ offs_t sparc_disassembler::dasm_branch(std::ostream &stream, offs_t pc, uint32_t if (OP2 == 3) util::stream_format(stream, "%s,", REG_NAMES[RS1]); const int32_t disp(desc.get_disp(op)); util::stream_format(stream, "%%pc%c0x%0*x ! 0x%08x", (disp < 0) ? '-' : '+', desc.disp_width, std::abs(disp), pc + disp); - //const char * const comment(desc.get_comment ? desc.get_comment(m_state, desc.use_cc, pc, op) : nullptr); + //const char * const comment(desc.get_comment ? desc.get_comment(m_config, desc.use_cc, pc, op) : nullptr); //if (comment) util::stream_format(stream, " - %s", comment); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } @@ -1117,7 +1126,7 @@ offs_t sparc_disassembler::dasm_shift(std::ostream &stream, offs_t pc, uint32_t { util::stream_format(stream, "%-*s%s,%s,%s", m_op_field_width, mnemonic, REG_NAMES[RS1], REG_NAMES[RS2], REG_NAMES[RD]); } - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } @@ -1126,14 +1135,14 @@ offs_t sparc_disassembler::dasm_read_state_reg(std::ostream &stream, offs_t pc, if (RS1 == 0) { util::stream_format(stream, "%-*s%%y,%s", m_op_field_width, "rd", REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } else if ((m_version == 8) || ((m_version >= 9) && !USEIMM)) { if (!USEIMM && (RS1 == 15) && (RD == 0)) { util::stream_format(stream, "stbar"); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } else { @@ -1144,7 +1153,7 @@ offs_t sparc_disassembler::dasm_read_state_reg(std::ostream &stream, offs_t pc, util::stream_format(stream, "%-*s%s,%s", m_op_field_width, "rd", it->second.read_name, REG_NAMES[RD]); else util::stream_format(stream, "%-*s%%asr%d,%s ! %s", m_op_field_width, "rd", RS1, REG_NAMES[RD], (RS1 < 16) ? "reserved" : "implementation-dependent"); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } } } @@ -1166,7 +1175,7 @@ offs_t sparc_disassembler::dasm_read_state_reg(std::ostream &stream, offs_t pc, if (mask & 1) util::stream_format(stream, "#MemIssue%s", (mask >> 1) ? "|" : ""); mask >>= 1; if (mask & 1) util::stream_format(stream, "#Sync"); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } return dasm_invalid(stream, pc, op); } @@ -1186,14 +1195,14 @@ offs_t sparc_disassembler::dasm_write_state_reg(std::ostream &stream, offs_t pc, if (USEIMM) util::stream_format(stream, "%-*s%s,%08x,%%y", m_op_field_width, "wr", REG_NAMES[RS1], SIMM13); else util::stream_format(stream, "%-*s%s,%s,%%y", m_op_field_width, "wr", REG_NAMES[RS1], REG_NAMES[RS2]); } - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } else if (m_version >= 8) { if ((m_version >= 9) && USEIMM && (RS1 == 0) && (RD == 15)) { util::stream_format(stream, "%-*s%d", m_op_field_width, "sir", SIMM13); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } else { @@ -1227,7 +1236,7 @@ offs_t sparc_disassembler::dasm_write_state_reg(std::ostream &stream, offs_t pc, else util::stream_format(stream, "%-*s%s,%s,%%asr%d ! %s", m_op_field_width, "wr", REG_NAMES[RS1], REG_NAMES[RS2], RD, comment); } } - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } } } @@ -1247,7 +1256,7 @@ offs_t sparc_disassembler::dasm_move_cond(std::ostream &stream, offs_t pc, uint3 else util::stream_format(stream, "%s,%s,%s", MOVCC_CC_NAMES[MOVCC], REG_NAMES[RS2], REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } offs_t sparc_disassembler::dasm_move_reg_cond(std::ostream &stream, offs_t pc, uint32_t op) const @@ -1259,7 +1268,7 @@ offs_t sparc_disassembler::dasm_move_reg_cond(std::ostream &stream, offs_t pc, u else util::stream_format(stream, "%-*s%s,%s,%s", m_op_field_width, MOVE_INT_COND_MNEMONICS[RCOND], REG_NAMES[RS1], REG_NAMES[RS2], REG_NAMES[RD]); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } @@ -1272,7 +1281,7 @@ offs_t sparc_disassembler::dasm_fpop1(std::ostream &stream, offs_t pc, uint32_t util::stream_format(stream, "%-*s%%f%d,%%f%d,%%f%d", m_op_field_width, it->second.mnemonic, freg(RS1, it->second.rs1_shift), freg(RS2, it->second.rs2_shift), freg(RD, it->second.rd_shift)); else util::stream_format(stream, "%-*s%%f%d,%%f%d", m_op_field_width, it->second.mnemonic, freg(RS2, it->second.rs2_shift), freg(RD, it->second.rd_shift)); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } @@ -1296,7 +1305,7 @@ offs_t sparc_disassembler::dasm_fpop2(std::ostream &stream, offs_t pc, uint32_t util::stream_format(stream, "%s%s", mnemonic, MOVCC_COND_NAMES[MOVCOND | ((OPFCC << 2) & 16)]); pad_op_field(stream, start_position); util::stream_format(stream, "%s,%%f%d,%%f%d", MOVCC_CC_NAMES[OPFCC], freg(RS2, shift), freg(RD, shift)); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } } @@ -1308,18 +1317,18 @@ offs_t sparc_disassembler::dasm_fpop2(std::ostream &stream, offs_t pc, uint32_t if (it->second.int_rs1) { util::stream_format(stream, "%-*s%s,%%f%d,%%f%d", m_op_field_width, it->second.mnemonic, REG_NAMES[RS1], freg(RS2, it->second.shift), freg(RD, it->second.shift)); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } else if (RD < 4) { util::stream_format(stream, "%-*s%%fcc%d,%%f%d,%%f%d", m_op_field_width, it->second.mnemonic, RD, freg(RS1, it->second.shift), freg(RS2, it->second.shift)); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } } else if (!it->second.int_rs1) { util::stream_format(stream, "%-*s%%f%d,%%f%d", m_op_field_width, it->second.mnemonic, freg(RS1, it->second.shift), freg(RS2, it->second.shift)); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } } @@ -1348,7 +1357,7 @@ offs_t sparc_disassembler::dasm_impdep1(std::ostream &stream, offs_t pc, uint32_ dasm_vis_arg(stream, args, it->second.rs2, RS2); } dasm_vis_arg(stream, args, it->second.rd, RD); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } switch (OPF) @@ -1357,7 +1366,7 @@ offs_t sparc_disassembler::dasm_impdep1(std::ostream &stream, offs_t pc, uint32_ if (m_vis_level >= vis_2) { util::stream_format(stream, "%-*s0x%x", m_op_field_width, "siam", IAMODE); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x151: @@ -1366,7 +1375,7 @@ offs_t sparc_disassembler::dasm_impdep1(std::ostream &stream, offs_t pc, uint32_ { const bool shift(OPF == 0x152); util::stream_format(stream, "%-*s%%fcc%d,%%f%d,%%f%d", m_op_field_width, (shift) ? "flcmpd" : "flcmps", RD & 3, freg(RS1, shift), freg(RS2, shift)); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; } @@ -1390,7 +1399,7 @@ offs_t sparc_disassembler::dasm_jmpl(std::ostream &stream, offs_t pc, uint32_t o if ((RD != 0) && (RD != 15)) util::stream_format(stream, ",%s", REG_NAMES[RD]); } - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } @@ -1398,7 +1407,7 @@ offs_t sparc_disassembler::dasm_return(std::ostream &stream, offs_t pc, uint32_t { util::stream_format(stream, "%-*s", m_op_field_width, (m_version >= 9) ? "return" : "rett"); dasm_address(stream, op); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } @@ -1431,7 +1440,7 @@ offs_t sparc_disassembler::dasm_tcc(std::ostream &stream, offs_t pc, uint32_t op else if (RS2 == 0) util::stream_format(stream, "%s", REG_NAMES[RS1]); else util::stream_format(stream, "%s,%s", REG_NAMES[RS1], REG_NAMES[RS2]); } - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } @@ -1447,7 +1456,7 @@ offs_t sparc_disassembler::dasm_ldst(std::ostream &stream, offs_t pc, uint32_t o util::stream_format(stream, "%-*s[", m_op_field_width, (RD == 1) ? "ldx" : "ld"); dasm_address(stream, op); util::stream_format(stream, "],%%fsr"); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } else if ((RD == 3) && (m_vis_level >= vis_3b)) { @@ -1462,7 +1471,7 @@ offs_t sparc_disassembler::dasm_ldst(std::ostream &stream, offs_t pc, uint32_t o util::stream_format(stream, "%-*s%%fsr,[", m_op_field_width, (RD == 1) ? "stx" : "st"); dasm_address(stream, op); stream << ']'; - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } break; case 0x3c: // Compare and swap word in alternate space @@ -1488,7 +1497,7 @@ offs_t sparc_disassembler::dasm_ldst(std::ostream &stream, offs_t pc, uint32_t o util::stream_format(stream, ",%s,%s", REG_NAMES[RS2], REG_NAMES[RD]); if (print_asi) dasm_asi_comment(stream, op); } - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; case 0x2d: // Prefetch data case 0x3d: // Prefetch data from alternate space { @@ -1501,7 +1510,7 @@ offs_t sparc_disassembler::dasm_ldst(std::ostream &stream, offs_t pc, uint32_t o else util::stream_format(stream, ",0x%02x", RD); if (OP3 == 0x3d) dasm_asi_comment(stream, op); } - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } } else @@ -1513,19 +1522,19 @@ offs_t sparc_disassembler::dasm_ldst(std::ostream &stream, offs_t pc, uint32_t o util::stream_format(stream, "%-*s[", m_op_field_width, "ld"); dasm_address(stream, op); util::stream_format(stream, "],%%%csr", (OP3 == 0x31) ? 'c' : 'f'); - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; case 0x25: // Store Floating-point State Register case 0x35: // Store Coprocessor State Register util::stream_format(stream, "%-*s%%%csr,[", m_op_field_width, "st", (OP3 == 0x35) ? 'c' : 'f'); dasm_address(stream, op); stream << ']'; - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; case 0x26: // Store Floating-point deferred-trap Queue case 0x36: // Store Coprocessor deferred-trap Queue util::stream_format(stream, "%-*s%%%cq,[", m_op_field_width, "std", (OP3 == 0x36) ? 'c' : 'f'); dasm_address(stream, op); stream << ']'; - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } } @@ -1566,7 +1575,7 @@ offs_t sparc_disassembler::dasm_ldst(std::ostream &stream, offs_t pc, uint32_t o } if (it->second.alternate) dasm_asi_comment(stream, op); } - return 4 | DASMFLAG_SUPPORTED; + return 4 | SUPPORTED; } diff --git a/src/devices/cpu/sparc/sparcdasm.h b/src/devices/cpu/sparc/sparcdasm.h index f5643a0e87b..f6f0e7bc27d 100644 --- a/src/devices/cpu/sparc/sparcdasm.h +++ b/src/devices/cpu/sparc/sparcdasm.h @@ -11,24 +11,21 @@ #include - -class sparc_debug_state +class sparc_disassembler : public util::disasm_interface { public: - virtual uint64_t get_reg_r(unsigned index) const = 0; - virtual uint64_t get_translated_pc() const = 0; - virtual uint8_t get_icc() const = 0; - virtual uint8_t get_xcc() const = 0; - virtual uint8_t get_fcc(unsigned index) const = 0; // ?><= - -protected: - ~sparc_debug_state() { } -}; + struct config + { + public: + virtual ~config() = default; + virtual uint64_t get_reg_r(unsigned index) const = 0; + virtual uint64_t get_translated_pc() const = 0; + virtual uint8_t get_icc() const = 0; + virtual uint8_t get_xcc() const = 0; + virtual uint8_t get_fcc(unsigned index) const = 0; // ?><= + }; -class sparc_disassembler -{ -public: enum vis_level { vis_none, vis_1, vis_2, vis_2p, vis_3, vis_3b }; struct asi_desc @@ -58,8 +55,8 @@ public: }; typedef std::map prftch_desc_map; - sparc_disassembler(const sparc_debug_state *state, unsigned version); - sparc_disassembler(const sparc_debug_state *state, unsigned version, vis_level vis); + sparc_disassembler(const config *conf, unsigned version); + sparc_disassembler(const config *conf, unsigned version, vis_level vis); template void add_state_reg_desc(const T &desc) { @@ -106,13 +103,16 @@ public: } } + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + offs_t dasm(std::ostream &stream, offs_t pc, uint32_t op) const; private: struct branch_desc { int32_t (*get_disp)(uint32_t op); - const char * (*get_comment)(const sparc_debug_state *state, bool use_cc, offs_t pc, uint32_t op); + const char * (*get_comment)(const config *conf, bool use_cc, offs_t pc, uint32_t op); int disp_width; bool use_pred, use_cc; const char *reg_cc[4]; @@ -238,7 +238,7 @@ private: static const vis_op_desc_map::value_type VIS3_OP_DESC[]; static const vis_op_desc_map::value_type VIS3B_OP_DESC[]; - //const sparc_debug_state *m_state; + //const config *m_config; unsigned m_version; vis_level m_vis_level; int m_op_field_width; diff --git a/src/devices/cpu/spc700/spc700.cpp b/src/devices/cpu/spc700/spc700.cpp index cb44ce03c19..07390f03969 100644 --- a/src/devices/cpu/spc700/spc700.cpp +++ b/src/devices/cpu/spc700/spc700.cpp @@ -1353,9 +1353,9 @@ void spc700_device::execute_set_input( int inptnum, int state ) #include "spc700ds.h" -offs_t spc700_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *spc700_device::create_disassembler() { - return CPU_DISASSEMBLE_NAME(spc700)(this, stream, pc, oprom, opram, options); + return new spc700_disassembler; } //int dump_flag = 0; diff --git a/src/devices/cpu/spc700/spc700.h b/src/devices/cpu/spc700/spc700.h index 161ebea347c..6af60c16d8e 100644 --- a/src/devices/cpu/spc700/spc700.h +++ b/src/devices/cpu/spc700/spc700.h @@ -33,9 +33,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 3; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/spc700/spc700ds.cpp b/src/devices/cpu/spc700/spc700ds.cpp index de7accc7cb8..9f220b02e26 100644 --- a/src/devices/cpu/spc700/spc700ds.cpp +++ b/src/devices/cpu/spc700/spc700ds.cpp @@ -15,39 +15,7 @@ All rights reserved. #include "emu.h" #include "spc700ds.h" - - -struct spc700_opcode_struct -{ - unsigned char name; - unsigned char args[2]; -}; - -enum -{ - IMP , A , X , Y , YA , SP , PSW , C , REL , UPAG, IMM , XI , - XII , YI , DP , DPX , DPY , DPI , DXI , DIY , ABS , ABX , ABY , AXI , N0 , - N1 , N2 , N3 , N4 , N5 , N6 , N7 , N8 , N9 , N10 , N11 , N12 , - N13 , N14 , N15 , DP0 , DP1 , DP2 , DP3 , DP4 , DP5 , DP6 , DP7 , MEMN, - MEMI -}; - - -enum -{ - ADC , ADDW , AND , AND1 , ASL , BBC , BBS , BCC , - BCS , BEQ , BMI , BNE , BPL , BRA , BRK , BVC , - BVS , CALL , CBNE , CLR1 , CLRC , CLRP , CLRV , CMP , - CMPW , DAA , DAS , DBNZ , DEC , DECW , DI , DIV , - EI , EOR , EOR1 , INC , INCW , JMP , LSR , MOV , - MOV1 , MOVW , MUL , NOP , NOT1 , NOTQ , NOTC , OR , - OR1 , PCALL , POP , PUSH , RET , RETI , ROL , ROR , - SBC , SET1 , SETC , SETP , SLEEP , STOP , SUBW , TCALL , - TCLR1 , TSET1 , XCN -}; - - -static const char *const g_opnames[] = +const char *const spc700_disassembler::g_opnames[] = { "ADC ", "ADDW ", "AND ", "AND1 ", "ASL ", "BBC ", "BBS ", "BCC ", "BCS ", "BEQ ", "BMI ", "BNE ", "BPL ", "BRA ", "BRK ", "BVC ", @@ -60,7 +28,7 @@ static const char *const g_opnames[] = "TCLR1", "TSET1", "XCN " }; -static const spc700_opcode_struct g_opcodes[256] = +const spc700_disassembler::spc700_opcode_struct spc700_disassembler::g_opcodes[256] = { /* 00 */ {NOP , {IMP , IMP }}, /* 01 */ {TCALL , {N0 , IMP }}, @@ -320,45 +288,44 @@ static const spc700_opcode_struct g_opcodes[256] = /* FF */ {STOP , {IMP , IMP }}, }; -static unsigned int g_pc; -static const uint8_t *rombase; +inline unsigned int spc700_disassembler::read_8_immediate(offs_t &pc, const data_buffer &opcodes) +{ + return opcodes.r8(pc++); +} -static inline unsigned int read_8_immediate(void) +inline unsigned int spc700_disassembler::read_16_immediate(offs_t &pc, const data_buffer &opcodes) { - g_pc++; - return *rombase++; + u16 r = opcodes.r16(pc); + pc += 2; + return r; } -static inline unsigned int read_16_immediate(void) +u32 spc700_disassembler::opcode_alignment() const { - unsigned int result; - g_pc += 2; - result = *rombase++; - return result | (*rombase++ << 8); + return 1; } -CPU_DISASSEMBLE(spc700) +offs_t spc700_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { const spc700_opcode_struct* opcode; uint32_t flags = 0; int var; int i; + offs_t base_pc = pc; - g_pc = pc; - rombase = oprom; - opcode = g_opcodes + read_8_immediate(); + opcode = g_opcodes + read_8_immediate(pc, opcodes); stream << g_opnames[opcode->name] << " "; if (opcode->name == CALL) - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; else if (opcode->name == RET || opcode->name == RETI) - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; if (opcode->args[0] == DP && (opcode->args[1] == DP || opcode->args[1] == IMM)) { - int src = read_8_immediate(); - int dst = read_8_immediate(); + int src = read_8_immediate(pc, opcodes); + int dst = read_8_immediate(pc, opcodes); util::stream_format(stream, "$%02x,%s$%02x", dst, (opcode->args[1] == IMM ? "#" : ""), src); } else for(i=0;i<2;i++) @@ -378,22 +345,22 @@ CPU_DISASSEMBLE(spc700) case SP: util::stream_format(stream, "SP"); break; case PSW: util::stream_format(stream, "PSW"); break; case C: util::stream_format(stream, "C"); break; - case REL: util::stream_format(stream, "%04x", ((g_pc + (char)read_8_immediate())&0xffff)); break; - case UPAG: util::stream_format(stream, "$%02x", read_8_immediate()); break; - case IMM: util::stream_format(stream, "#$%02x", read_8_immediate()); break; + case REL: util::stream_format(stream, "%04x", ((pc + (char)read_8_immediate(pc, opcodes))&0xffff)); break; + case UPAG: util::stream_format(stream, "$%02x", read_8_immediate(pc, opcodes)); break; + case IMM: util::stream_format(stream, "#$%02x", read_8_immediate(pc, opcodes)); break; case XI: util::stream_format(stream, "(X)"); break; case XII: util::stream_format(stream, "(X)+"); break; case YI: util::stream_format(stream, "(Y)"); break; - case DP: util::stream_format(stream, "$%02x", read_8_immediate()); break; - case DPX: util::stream_format(stream, "$%02x+X", read_8_immediate()); break; - case DPY: util::stream_format(stream, "$%02x+Y", read_8_immediate()); break; - case DPI: util::stream_format(stream, "($%02x)", read_8_immediate()); break; - case DXI: util::stream_format(stream, "($%02x+X)", read_8_immediate()); break; - case DIY: util::stream_format(stream, "($%02x)+Y", read_8_immediate()); break; - case ABS: util::stream_format(stream, "$%04x", read_16_immediate()); break; - case ABX: util::stream_format(stream, "$%04x+X", read_16_immediate()); break; - case ABY: util::stream_format(stream, "$%04x+Y", read_16_immediate()); break; - case AXI: util::stream_format(stream, "($%04x+X)", read_16_immediate()); break; + case DP: util::stream_format(stream, "$%02x", read_8_immediate(pc, opcodes)); break; + case DPX: util::stream_format(stream, "$%02x+X", read_8_immediate(pc, opcodes)); break; + case DPY: util::stream_format(stream, "$%02x+Y", read_8_immediate(pc, opcodes)); break; + case DPI: util::stream_format(stream, "($%02x)", read_8_immediate(pc, opcodes)); break; + case DXI: util::stream_format(stream, "($%02x+X)", read_8_immediate(pc, opcodes)); break; + case DIY: util::stream_format(stream, "($%02x)+Y", read_8_immediate(pc, opcodes)); break; + case ABS: util::stream_format(stream, "$%04x", read_16_immediate(pc, opcodes)); break; + case ABX: util::stream_format(stream, "$%04x+X", read_16_immediate(pc, opcodes)); break; + case ABY: util::stream_format(stream, "$%04x+Y", read_16_immediate(pc, opcodes)); break; + case AXI: util::stream_format(stream, "($%04x+X)", read_16_immediate(pc, opcodes)); break; case N0: util::stream_format(stream, "0"); break; case N1: util::stream_format(stream, "1"); break; case N2: util::stream_format(stream, "2"); break; @@ -410,23 +377,23 @@ CPU_DISASSEMBLE(spc700) case N13: util::stream_format(stream, "13"); break; case N14: util::stream_format(stream, "14"); break; case N15: util::stream_format(stream, "15"); break; - case DP0: util::stream_format(stream, "$%02x.0", read_8_immediate()); break; - case DP1: util::stream_format(stream, "$%02x.1", read_8_immediate()); break; - case DP2: util::stream_format(stream, "$%02x.2", read_8_immediate()); break; - case DP3: util::stream_format(stream, "$%02x.3", read_8_immediate()); break; - case DP4: util::stream_format(stream, "$%02x.4", read_8_immediate()); break; - case DP5: util::stream_format(stream, "$%02x.5", read_8_immediate()); break; - case DP6: util::stream_format(stream, "$%02x.6", read_8_immediate()); break; - case DP7: util::stream_format(stream, "$%02x.7", read_8_immediate()); break; + case DP0: util::stream_format(stream, "$%02x.0", read_8_immediate(pc, opcodes)); break; + case DP1: util::stream_format(stream, "$%02x.1", read_8_immediate(pc, opcodes)); break; + case DP2: util::stream_format(stream, "$%02x.2", read_8_immediate(pc, opcodes)); break; + case DP3: util::stream_format(stream, "$%02x.3", read_8_immediate(pc, opcodes)); break; + case DP4: util::stream_format(stream, "$%02x.4", read_8_immediate(pc, opcodes)); break; + case DP5: util::stream_format(stream, "$%02x.5", read_8_immediate(pc, opcodes)); break; + case DP6: util::stream_format(stream, "$%02x.6", read_8_immediate(pc, opcodes)); break; + case DP7: util::stream_format(stream, "$%02x.7", read_8_immediate(pc, opcodes)); break; case MEMN: - var = read_16_immediate(); + var = read_16_immediate(pc, opcodes); util::stream_format(stream, "%04x.%d", var&0x1fff, var>>13); break; case MEMI: - var = read_16_immediate(); + var = read_16_immediate(pc, opcodes); util::stream_format(stream, "/%04x.%d", var&0x1fff, var>>13); break; } } - return (g_pc - pc) | flags | DASMFLAG_SUPPORTED; + return (pc - base_pc) | flags | SUPPORTED; } diff --git a/src/devices/cpu/spc700/spc700ds.h b/src/devices/cpu/spc700/spc700ds.h index e2135526363..fdd7bbeba7b 100644 --- a/src/devices/cpu/spc700/spc700ds.h +++ b/src/devices/cpu/spc700/spc700ds.h @@ -17,8 +17,49 @@ All rights reserved. */ +class spc700_disassembler : public util::disasm_interface +{ +public: + spc700_disassembler() = default; + virtual ~spc700_disassembler() = default; -CPU_DISASSEMBLE( spc700 ); + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + struct spc700_opcode_struct + { + unsigned char name; + unsigned char args[2]; + }; + + enum + { + IMP , A , X , Y , YA , SP , PSW , C , REL , UPAG, IMM , XI , + XII , YI , DP , DPX , DPY , DPI , DXI , DIY , ABS , ABX , ABY , AXI , N0 , + N1 , N2 , N3 , N4 , N5 , N6 , N7 , N8 , N9 , N10 , N11 , N12 , + N13 , N14 , N15 , DP0 , DP1 , DP2 , DP3 , DP4 , DP5 , DP6 , DP7 , MEMN, + MEMI + }; + + enum + { + ADC , ADDW , AND , AND1 , ASL , BBC , BBS , BCC , + BCS , BEQ , BMI , BNE , BPL , BRA , BRK , BVC , + BVS , CALL , CBNE , CLR1 , CLRC , CLRP , CLRV , CMP , + CMPW , DAA , DAS , DBNZ , DEC , DECW , DI , DIV , + EI , EOR , EOR1 , INC , INCW , JMP , LSR , MOV , + MOV1 , MOVW , MUL , NOP , NOT1 , NOTQ , NOTC , OR , + OR1 , PCALL , POP , PUSH , RET , RETI , ROL , ROR , + SBC , SET1 , SETC , SETP , SLEEP , STOP , SUBW , TCALL , + TCLR1 , TSET1 , XCN + }; + + static const char *const g_opnames[]; + static const spc700_opcode_struct g_opcodes[256]; + static inline unsigned int read_8_immediate(offs_t &pc, const data_buffer &opcodes); + static inline unsigned int read_16_immediate(offs_t &pc, const data_buffer &opcodes); +}; #endif /* __SPC700DS_H__ */ diff --git a/src/devices/cpu/ssem/ssem.cpp b/src/devices/cpu/ssem/ssem.cpp index 69c6ce66571..6cfffaef83d 100644 --- a/src/devices/cpu/ssem/ssem.cpp +++ b/src/devices/cpu/ssem/ssem.cpp @@ -9,8 +9,7 @@ #include "emu.h" #include "debugger.h" #include "ssem.h" - -CPU_DISASSEMBLE( ssem ); +#include "ssemdasm.h" #define SSEM_DISASM_ON_UNIMPL 0 @@ -160,36 +159,13 @@ void ssem_device::state_string_export(const device_state_entry &entry, std::stri //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t ssem_device::disasm_min_opcode_bytes() const -{ - return 4; -} - - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t ssem_device::disasm_max_opcode_bytes() const -{ - return 4; -} - - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t ssem_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *ssem_device::create_disassembler() { - extern CPU_DISASSEMBLE( ssem ); - return CPU_DISASSEMBLE_NAME(ssem)(this, stream, pc, oprom, opram, options); + return new ssem_disassembler; } diff --git a/src/devices/cpu/ssem/ssem.h b/src/devices/cpu/ssem/ssem.h index b9485678a18..c6e396307f1 100644 --- a/src/devices/cpu/ssem/ssem.h +++ b/src/devices/cpu/ssem/ssem.h @@ -41,9 +41,7 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // device_state_interface overrides virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; @@ -82,6 +80,4 @@ enum SSEM_HALT }; -CPU_DISASSEMBLE( ssem ); - #endif // MAME_CPU_SSEM_SSEM_H diff --git a/src/devices/cpu/ssem/ssemdasm.cpp b/src/devices/cpu/ssem/ssemdasm.cpp index 8ad79f96d8c..43adb44510b 100644 --- a/src/devices/cpu/ssem/ssemdasm.cpp +++ b/src/devices/cpu/ssem/ssemdasm.cpp @@ -7,8 +7,9 @@ */ #include "emu.h" +#include "ssemdasm.h" -static inline uint32_t reverse(uint32_t v) +inline uint32_t ssem_disassembler::reverse(uint32_t v) { // Taken from http://www-graphics.stanford.edu/~seander/bithacks.html#ReverseParallel // swap odd and even bits @@ -25,8 +26,14 @@ static inline uint32_t reverse(uint32_t v) return v; } -static offs_t ssem_dasm_one(std::ostream &stream, offs_t pc, uint32_t op) +u32 ssem_disassembler::opcode_alignment() const { + return 4; +} + +offs_t ssem_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + uint32_t op = opcodes.r32(pc); uint8_t instr = (reverse(op) >> 13) & 7; uint8_t addr = reverse(op) & 0x1f; @@ -59,16 +66,5 @@ static offs_t ssem_dasm_one(std::ostream &stream, offs_t pc, uint32_t op) break; } - return 4 | DASMFLAG_SUPPORTED; -} - -/*****************************************************************************/ - -CPU_DISASSEMBLE( ssem ) -{ - uint32_t op = (*(uint8_t *)(opram + 0) << 24) | - (*(uint8_t *)(opram + 1) << 16) | - (*(uint8_t *)(opram + 2) << 8) | - (*(uint8_t *)(opram + 3) << 0); - return ssem_dasm_one(stream, pc, op); + return 4 | SUPPORTED; } diff --git a/src/devices/cpu/ssem/ssemdasm.h b/src/devices/cpu/ssem/ssemdasm.h new file mode 100644 index 00000000000..a83e38c6f8f --- /dev/null +++ b/src/devices/cpu/ssem/ssemdasm.h @@ -0,0 +1,28 @@ +// license:BSD-3-Clause +// copyright-holders:Ryan Holtz +/* + Manchester Small-Scale Experimental Machine (SSEM) disassembler + + Written by Ryan Holtz +*/ + +#ifndef MAME_CPU_SSEM_SSEMDASM_H +#define MAME_CPU_SSEM_SSEMDASM_H + +#pragma once + +class ssem_disassembler : public util::disasm_interface +{ +public: + ssem_disassembler() = default; + virtual ~ssem_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static inline uint32_t reverse(uint32_t v); + +}; + +#endif diff --git a/src/devices/cpu/ssp1601/ssp1601.cpp b/src/devices/cpu/ssp1601/ssp1601.cpp index 0ee9139cc1c..5ab63550275 100644 --- a/src/devices/cpu/ssp1601/ssp1601.cpp +++ b/src/devices/cpu/ssp1601/ssp1601.cpp @@ -18,6 +18,7 @@ #include "emu.h" #include "ssp1601.h" +#include "ssp1601d.h" #include "debugger.h" @@ -209,10 +210,9 @@ device_memory_interface::space_config_vector ssp1601_device::memory_space_config } -offs_t ssp1601_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *ssp1601_device::create_disassembler() { - extern CPU_DISASSEMBLE( ssp1601 ); - return CPU_DISASSEMBLE_NAME(ssp1601)(this, stream, pc, oprom, opram, options); + return new ssp1601_disassembler; } diff --git a/src/devices/cpu/ssp1601/ssp1601.h b/src/devices/cpu/ssp1601/ssp1601.h index 55a1184b5bb..fd1fb82d84b 100644 --- a/src/devices/cpu/ssp1601/ssp1601.h +++ b/src/devices/cpu/ssp1601/ssp1601.h @@ -43,9 +43,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/ssp1601/ssp1601d.cpp b/src/devices/cpu/ssp1601/ssp1601d.cpp index 465dd657d90..5b9f3c6ac27 100644 --- a/src/devices/cpu/ssp1601/ssp1601d.cpp +++ b/src/devices/cpu/ssp1601/ssp1601d.cpp @@ -9,10 +9,10 @@ */ #include "emu.h" -#include "debugger.h" +#include "ssp1601d.h" -static const char *const reg[16] = +const char *const ssp1601_disassembler::reg[16] = { "-", "X", "Y", "A", "ST", "STACK", "PC", "P", @@ -20,22 +20,22 @@ static const char *const reg[16] = "EXT4", "EXT5", "EXT6", "AL" }; -static const char *const rij[8] = +const char *const ssp1601_disassembler::rij[8] = { "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7" }; -static const char *const modifier[4] = +const char *const ssp1601_disassembler::modifier[4] = { "", "+!", "-", "+" }; -static const char *const modifier_sf[4] = +const char *const ssp1601_disassembler::modifier_sf[4] = { "|00", "|01", "|10", "|11" }; -static const char *const cond[16] = +const char *const ssp1601_disassembler::cond[16] = { "always", "RESERVED", "gpi0", "gpi1", "l", "z", "ov", "n", @@ -43,18 +43,18 @@ static const char *const cond[16] = "RESERVED", "RESERVED", "RESERVED", "RESERVED", }; -static const char *const acc_op[8] = +const char *const ssp1601_disassembler::acc_op[8] = { "ror", "rol", "shr", "shl", "inc", "dec", "neg", "abs" }; // pag. 81 uses different addresses! -static const char *const flag_op[16] = +const char *const ssp1601_disassembler::flag_op[16] = { "?", "?", "resl", "setl", "resie", "setie", "?", "?", "resop", "setop", "?", "?", "?", "?", "res", "set" }; -static const char *const arith_ops[8] = +const char *const ssp1601_disassembler::arith_ops[8] = { "", "add", "", "cmp", "add", "and", "or", "eor" }; @@ -68,27 +68,24 @@ static const char *const arith_ops[8] = #define MODIFIER_LOW MODIFIER((op >> 2) & 3, op&3) #define MODIFIER_HIGH MODIFIER((op >> 6) & 3, (op >> 4)&3) -#define READ_OP_DASM(p) ((base_oprom[p] << 8) | base_oprom[(p) + 1]) - -static char *get_cond(int op) +std::string ssp1601_disassembler::get_cond(int op) { - static char scond[16]; - if (op&0xf0) sprintf(scond, "%s=%i", cond[(op >> 4) & 0xf], BIT_B); - else sprintf(scond, "%s", cond[(op >> 4) & 0xf]); - return scond; + if (op&0xf0) return util::string_format("%s=%i", cond[(op >> 4) & 0xf], BIT_B); + else return util::string_format("%s", cond[(op >> 4) & 0xf]); } +u32 ssp1601_disassembler::opcode_alignment() const +{ + return 1; +} -static unsigned dasm_ssp1601(std::ostream &stream, unsigned pc, const uint8_t *oprom) +offs_t ssp1601_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - const uint8_t *base_oprom; uint16_t op; int size = 1; int flags = 0; - base_oprom = oprom; - - op = READ_OP_DASM(0); + op = opcodes.r16(pc); switch (op >> 9) { @@ -102,7 +99,7 @@ static unsigned dasm_ssp1601(std::ostream &stream, unsigned pc, const uint8_t *o { // ret util::stream_format(stream, "ret"); - flags |= DASMFLAG_STEP_OUT; + flags |= STEP_OUT; } else { @@ -128,7 +125,7 @@ static unsigned dasm_ssp1601(std::ostream &stream, unsigned pc, const uint8_t *o // ldi d, imm case 0x04: - util::stream_format(stream, "ld %s, %X", reg[(op >> 4) & 0xf], READ_OP_DASM(2)); + util::stream_format(stream, "ld %s, %X", reg[(op >> 4) & 0xf], opcodes.r16(pc+1)); size = 2; break; @@ -139,7 +136,7 @@ static unsigned dasm_ssp1601(std::ostream &stream, unsigned pc, const uint8_t *o // ldi (ri), imm case 0x06: - util::stream_format(stream, "ld (%s%s), %X", RIJ, MODIFIER_LOW, READ_OP_DASM(2)); + util::stream_format(stream, "ld (%s%s), %X", RIJ, MODIFIER_LOW, opcodes.r16(pc+1)); size = 2; break; @@ -203,7 +200,7 @@ static unsigned dasm_ssp1601(std::ostream &stream, unsigned pc, const uint8_t *o case 0x54: case 0x64: case 0x74: - util::stream_format(stream, "%si A, %X", arith_ops[op >> 13], READ_OP_DASM(2)); + util::stream_format(stream, "%si A, %X", arith_ops[op >> 13], opcodes.r16(pc+1)); size = 2; break; @@ -244,8 +241,8 @@ static unsigned dasm_ssp1601(std::ostream &stream, unsigned pc, const uint8_t *o // call cond, addr case 0x24: - util::stream_format(stream, "call %s, %X", get_cond(op), READ_OP_DASM(2)); - flags |= DASMFLAG_STEP_OVER; + util::stream_format(stream, "call %s, %X", get_cond(op), opcodes.r16(pc+1)); + flags |= STEP_OVER; size = 2; break; @@ -256,7 +253,7 @@ static unsigned dasm_ssp1601(std::ostream &stream, unsigned pc, const uint8_t *o // bra cond, addr case 0x26: - util::stream_format(stream, "bra %s, %X", get_cond(op), READ_OP_DASM(2)); + util::stream_format(stream, "bra %s, %X", get_cond(op), opcodes.r16(pc+1)); size = 2; break; @@ -285,14 +282,5 @@ static unsigned dasm_ssp1601(std::ostream &stream, unsigned pc, const uint8_t *o break; } - return size | flags | DASMFLAG_SUPPORTED; -} - -// vim:ts=4 - -CPU_DISASSEMBLE( ssp1601 ) -{ - //ssp1601_state_t *ssp1601_state = get_safe_token(device); - - return dasm_ssp1601(stream, pc, oprom); + return size | flags | SUPPORTED; } diff --git a/src/devices/cpu/ssp1601/ssp1601d.h b/src/devices/cpu/ssp1601/ssp1601d.h new file mode 100644 index 00000000000..9c868a5d308 --- /dev/null +++ b/src/devices/cpu/ssp1601/ssp1601d.h @@ -0,0 +1,37 @@ +// license:BSD-3-Clause +// copyright-holders:Pierpaolo Prazzoli,Grazvydas Ignotas +/* + + SSP1601 disassembler + written by Pierpaolo Prazzoli + updated for SSP1601 by Grazvydas Ignotas + +*/ + +#ifndef MAME_CPU_SSP1601_SSP1601DASM_H +#define MAME_CPU_SSP1601_SSP1601DASM_H + +#pragma once + +class ssp1601_disassembler : public util::disasm_interface +{ +public: + ssp1601_disassembler() = default; + virtual ~ssp1601_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *const reg[16]; + static const char *const rij[8]; + static const char *const modifier[4]; + static const char *const modifier_sf[4]; + static const char *const cond[16]; + static const char *const acc_op[8]; + static const char *const flag_op[16]; + static const char *const arith_ops[8]; + static std::string get_cond(int op); +}; + +#endif diff --git a/src/devices/cpu/superfx/sfx_dasm.cpp b/src/devices/cpu/superfx/sfx_dasm.cpp index a4e2855480f..58139452ea2 100644 --- a/src/devices/cpu/superfx/sfx_dasm.cpp +++ b/src/devices/cpu/superfx/sfx_dasm.cpp @@ -1,10 +1,24 @@ // license:BSD-3-Clause // copyright-holders:Ryan Holtz #include "emu.h" -#include "superfx.h" +#include "sfx_dasm.h" -offs_t superfx_dasm_one(std::ostream &stream, offs_t pc, uint8_t op, uint8_t param0, uint8_t param1, uint16_t alt) +superfx_disassembler::superfx_disassembler(config *conf) : m_config(conf) { +} + +u32 superfx_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t superfx_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + uint8_t op = opcodes.r8(pc); + uint8_t param0 = opcodes.r8(pc+1); + uint8_t param1 = opcodes.r8(pc+2); + uint16_t alt = m_config->get_alt(); + uint8_t bytes_consumed = 1; switch(op) @@ -409,5 +423,5 @@ offs_t superfx_dasm_one(std::ostream &stream, offs_t pc, uint8_t op, uint8_t par break; } - return bytes_consumed | DASMFLAG_SUPPORTED; + return bytes_consumed | SUPPORTED; } diff --git a/src/devices/cpu/superfx/sfx_dasm.h b/src/devices/cpu/superfx/sfx_dasm.h new file mode 100644 index 00000000000..4bd324c9e9d --- /dev/null +++ b/src/devices/cpu/superfx/sfx_dasm.h @@ -0,0 +1,36 @@ +// license:BSD-3-Clause +// copyright-holders:Ryan Holtz + +#ifndef MAME_CPU_SUPERFX_SFX_DASM_H +#define MAME_CPU_SUPERFX_SFX_DASM_H + +#pragma once + +class superfx_disassembler : public util::disasm_interface +{ +public: + enum { + SUPERFX_SFR_ALT = 0x0300, // ALT Mode, both bits + SUPERFX_SFR_ALT0 = 0x0000, // ALT Mode, no bits + SUPERFX_SFR_ALT1 = 0x0100, // ALT Mode, bit 0 + SUPERFX_SFR_ALT2 = 0x0200, // ALT Mode, bit 1 + SUPERFX_SFR_ALT3 = 0x0300 // ALT Mode, both bits (convenience dupe) + }; + + struct config { + virtual ~config() = default; + + virtual u16 get_alt() const = 0; + }; + + superfx_disassembler(config *conf); + virtual ~superfx_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + config *m_config; +}; + +#endif diff --git a/src/devices/cpu/superfx/superfx.cpp b/src/devices/cpu/superfx/superfx.cpp index 2879a6faeaf..1e203a0a1f3 100644 --- a/src/devices/cpu/superfx/superfx.cpp +++ b/src/devices/cpu/superfx/superfx.cpp @@ -1445,12 +1445,12 @@ void superfx_device::execute_run() } } -offs_t superfx_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +u16 superfx_device::get_alt() const { - uint8_t op = *(uint8_t *)(opram + 0); - uint8_t param0 = *(uint8_t *)(opram + 1); - uint8_t param1 = *(uint8_t *)(opram + 2); - uint16_t alt = m_sfr & SUPERFX_SFR_ALT; + return m_sfr & SUPERFX_SFR_ALT; +} - return superfx_dasm_one(stream, pc, op, param0, param1, alt); +util::disasm_interface *superfx_device::create_disassembler() +{ + return new superfx_disassembler(this); } diff --git a/src/devices/cpu/superfx/superfx.h b/src/devices/cpu/superfx/superfx.h index 172c51eb65b..0bd060bb5fa 100644 --- a/src/devices/cpu/superfx/superfx.h +++ b/src/devices/cpu/superfx/superfx.h @@ -5,6 +5,7 @@ #pragma once +#include "sfx_dasm.h" enum { @@ -92,7 +93,7 @@ enum devcb = &superfx_device::set_out_irq_func(*device, DEVCB_##_devcb); -class superfx_device : public cpu_device +class superfx_device : public cpu_device, public superfx_disassembler::config { public: // construction/destruction @@ -107,6 +108,8 @@ public: int access_ram(); int access_rom(); + virtual u16 get_alt() const override; + protected: // device-level overrides virtual void device_start() override; @@ -126,9 +129,7 @@ protected: virtual void state_export(const device_state_entry &entry) override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 3; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; @@ -216,6 +217,4 @@ private: DECLARE_DEVICE_TYPE(SUPERFX, superfx_device) -offs_t superfx_dasm_one(std::ostream &stream, offs_t pc, uint8_t op, uint8_t param0, uint8_t param1, uint16_t alt); - #endif // MAME_CPU_SUPERFX_SUPERFX_H diff --git a/src/devices/cpu/t11/t11.cpp b/src/devices/cpu/t11/t11.cpp index dba6241b553..156486a2f75 100644 --- a/src/devices/cpu/t11/t11.cpp +++ b/src/devices/cpu/t11/t11.cpp @@ -13,6 +13,7 @@ #include "emu.h" #include "t11.h" +#include "t11dasm.h" #include "debugger.h" @@ -422,9 +423,7 @@ void t11_device::execute_run() } while (m_icount > 0); } - -offs_t t11_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *t11_device::create_disassembler() { - extern CPU_DISASSEMBLE( t11 ); - return CPU_DISASSEMBLE_NAME(t11)(this, stream, pc, oprom, opram, options); + return new t11_disassembler; } diff --git a/src/devices/cpu/t11/t11.h b/src/devices/cpu/t11/t11.h index 47db0a9b144..1b547c4cc92 100644 --- a/src/devices/cpu/t11/t11.h +++ b/src/devices/cpu/t11/t11.h @@ -66,9 +66,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 6; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; address_space_config m_program_config; diff --git a/src/devices/cpu/t11/t11dasm.cpp b/src/devices/cpu/t11/t11dasm.cpp index b1936566f9c..c99789163ac 100644 --- a/src/devices/cpu/t11/t11dasm.cpp +++ b/src/devices/cpu/t11/t11dasm.cpp @@ -10,17 +10,18 @@ */ #include "emu.h" -#include "debugger.h" -#include "t11.h" +#include "t11dasm.h" -static const char *const regs[8] = { "R0", "R1", "R2", "R3", "R4", "R5", "SP", "PC" }; +const char *const t11_disassembler::regs[8] = { "R0", "R1", "R2", "R3", "R4", "R5", "SP", "PC" }; -static const uint8_t *rombase; -static offs_t pcbase; - -#define PARAM_WORD(v) ((v) = rombase[pc - pcbase] | (rombase[pc + 1 - pcbase] << 8), pc += 2) +u16 t11_disassembler::r16p(offs_t &pc, const data_buffer &opcodes) +{ + u16 r = opcodes.r16(pc); + pc += 2; + return r; +} -static unsigned MakeEA (char *ea, int lo, unsigned pc, int width) +std::string t11_disassembler::MakeEA (int lo, offs_t &pc, int width, const data_buffer &opcodes) { int reg, pm; @@ -31,71 +32,67 @@ static unsigned MakeEA (char *ea, int lo, unsigned pc, int width) switch ((lo >> 3) & 7) { case 0: - sprintf (ea, "%s", regs[reg]); + return util::string_format ("%s", regs[reg]); break; case 1: - sprintf (ea, "(%s)", regs[reg]); + return util::string_format ("(%s)", regs[reg]); break; case 2: if (reg == 7) { - PARAM_WORD (pm); - sprintf (ea, "#$%0*X", width, pm & ((width == 2) ? 0xff : 0xffff)); + pm = r16p(pc, opcodes); + return util::string_format ("#$%0*X", width, pm & ((width == 2) ? 0xff : 0xffff)); } else { - sprintf (ea, "(%s)+", regs[reg]); + return util::string_format ("(%s)+", regs[reg]); } break; case 3: if (reg == 7) { - PARAM_WORD (pm); - sprintf (ea, "$%04X", pm &= 0xffff); + pm = r16p(pc, opcodes); + return util::string_format ( "$%04X", pm &= 0xffff); } else { - sprintf (ea, "@(%s)+", regs[reg]); + return util::string_format ("@(%s)+", regs[reg]); } break; case 4: - sprintf (ea, "-(%s)", regs[reg]); + return util::string_format ("-(%s)", regs[reg]); break; case 5: - sprintf (ea, "@-(%s)", regs[reg]); + return util::string_format ("@-(%s)", regs[reg]); break; case 6: - PARAM_WORD (pm); - sprintf(ea, "%s$%X(%s)", + pm = r16p(pc, opcodes); + return util::string_format ("%s$%X(%s)", (pm&0x8000)?"-":"", (pm&0x8000)?-(signed short)pm:pm, regs[reg]); break; case 7: - PARAM_WORD (pm); - sprintf(ea, "@%s$%X(%s)", + pm = r16p(pc, opcodes); + return util::string_format ("@%s$%X(%s)", (pm&0x8000)?"-":"", (pm&0x8000)?-(signed short)pm:pm, regs[reg]); break; } - - return pc; + return ""; } -CPU_DISASSEMBLE(t11) +offs_t t11_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - char ea1[32], ea2[32]; - unsigned PC = pc; + offs_t PC = pc; uint16_t op, lo, hi, addr; int16_t offset; uint32_t flags = 0; + std::string ea1, ea2; - rombase = oprom; - pcbase = pc; - - PARAM_WORD(op); + op = r16p(pc, opcodes); lo = op & 077; hi = (op >> 6) & 077; @@ -106,7 +103,7 @@ CPU_DISASSEMBLE(t11) { case 0x00: util::stream_format(stream, "HALT"); break; case 0x01: util::stream_format(stream, "WAIT"); break; - case 0x02: util::stream_format(stream, "RTI"); flags = DASMFLAG_STEP_OUT; break; + case 0x02: util::stream_format(stream, "RTI"); flags = STEP_OUT; break; case 0x03: util::stream_format(stream, "BPT"); break; case 0x04: util::stream_format(stream, "IOT"); break; case 0x05: util::stream_format(stream, "RESET"); break; @@ -115,7 +112,7 @@ CPU_DISASSEMBLE(t11) } break; case 0x0040: - pc = MakeEA (ea1, lo, pc, 4); + ea1 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "JMP %s", ea1); break; case 0x0080: @@ -126,7 +123,7 @@ CPU_DISASSEMBLE(t11) util::stream_format(stream, "RTS"); else util::stream_format(stream, "RTS %s", regs[lo & 7]); - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; case 040: case 050: @@ -157,7 +154,7 @@ CPU_DISASSEMBLE(t11) } break; case 0x00c0: - pc = MakeEA (ea1, lo, pc, 4); + ea1 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "SWAB %s", ea1); break; case 0x0100: case 0x0140: case 0x0180: case 0x01c0: @@ -190,66 +187,66 @@ CPU_DISASSEMBLE(t11) break; case 0x0800: case 0x0840: case 0x0880: case 0x08c0: case 0x0900: case 0x0940: case 0x0980: case 0x09c0: - pc = MakeEA (ea1, lo, pc, 4); + ea1 = MakeEA (lo, pc, 4, opcodes); if ( (hi & 7) == 7 ) util::stream_format(stream, "JSR %s", ea1); else util::stream_format(stream, "JSR %s,%s", regs[hi & 7], ea1); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case 0x0a00: - pc = MakeEA (ea1, lo, pc, 4); + ea1 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "CLR %s", ea1); break; case 0x0a40: - pc = MakeEA (ea1, lo, pc, 4); + ea1 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "COM %s", ea1); break; case 0x0a80: - pc = MakeEA (ea1, lo, pc, 4); + ea1 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "INC %s", ea1); break; case 0x0ac0: - pc = MakeEA (ea1, lo, pc, 4); + ea1 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "DEC %s", ea1); break; case 0x0b00: - pc = MakeEA (ea1, lo, pc, 4); + ea1 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "NEG %s", ea1); break; case 0x0b40: - pc = MakeEA (ea1, lo, pc, 4); + ea1 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "ADC %s", ea1); break; case 0x0b80: - pc = MakeEA (ea1, lo, pc, 4); + ea1 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "SBC %s", ea1); break; case 0x0bc0: - pc = MakeEA (ea1, lo, pc, 4); + ea1 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "TST %s", ea1); break; case 0x0c00: - pc = MakeEA (ea1, lo, pc, 4); + ea1 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "ROR %s", ea1); break; case 0x0c40: - pc = MakeEA (ea1, lo, pc, 4); + ea1 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "ROL %s", ea1); break; case 0x0c80: - pc = MakeEA (ea1, lo, pc, 4); + ea1 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "ASR %s", ea1); break; case 0x0cc0: - pc = MakeEA (ea1, lo, pc, 4); + ea1 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "ASL %s", ea1); break; /* case 0x0d00: util::stream_format(stream, "MARK #$%X", lo); break;*/ case 0x0dc0: - pc = MakeEA (ea1, lo, pc, 4); + ea1 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "SXT %s", ea1); break; case 0x1000: case 0x1040: case 0x1080: case 0x10c0: case 0x1100: case 0x1140: case 0x1180: case 0x11c0: @@ -260,8 +257,8 @@ CPU_DISASSEMBLE(t11) case 0x1a00: case 0x1a40: case 0x1a80: case 0x1ac0: case 0x1b00: case 0x1b40: case 0x1b80: case 0x1bc0: case 0x1c00: case 0x1c40: case 0x1c80: case 0x1cc0: case 0x1d00: case 0x1d40: case 0x1d80: case 0x1dc0: case 0x1e00: case 0x1e40: case 0x1e80: case 0x1ec0: case 0x1f00: case 0x1f40: case 0x1f80: case 0x1fc0: - pc = MakeEA (ea1, hi, pc, 4); - pc = MakeEA (ea2, lo, pc, 4); + ea1 = MakeEA (hi, pc, 4, opcodes); + ea2 = MakeEA (lo, pc, 4, opcodes); if (lo == 046) /* MOV src,-(SP) */ util::stream_format(stream, "PUSH %s", ea1); else @@ -278,8 +275,8 @@ CPU_DISASSEMBLE(t11) case 0x2a00: case 0x2a40: case 0x2a80: case 0x2ac0: case 0x2b00: case 0x2b40: case 0x2b80: case 0x2bc0: case 0x2c00: case 0x2c40: case 0x2c80: case 0x2cc0: case 0x2d00: case 0x2d40: case 0x2d80: case 0x2dc0: case 0x2e00: case 0x2e40: case 0x2e80: case 0x2ec0: case 0x2f00: case 0x2f40: case 0x2f80: case 0x2fc0: - pc = MakeEA (ea1, hi, pc, 4); - pc = MakeEA (ea2, lo, pc, 4); + ea1 = MakeEA (hi, pc, 4, opcodes); + ea2 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "CMP %s,%s", ea1, ea2); break; case 0x3000: case 0x3040: case 0x3080: case 0x30c0: case 0x3100: case 0x3140: case 0x3180: case 0x31c0: @@ -290,8 +287,8 @@ CPU_DISASSEMBLE(t11) case 0x3a00: case 0x3a40: case 0x3a80: case 0x3ac0: case 0x3b00: case 0x3b40: case 0x3b80: case 0x3bc0: case 0x3c00: case 0x3c40: case 0x3c80: case 0x3cc0: case 0x3d00: case 0x3d40: case 0x3d80: case 0x3dc0: case 0x3e00: case 0x3e40: case 0x3e80: case 0x3ec0: case 0x3f00: case 0x3f40: case 0x3f80: case 0x3fc0: - pc = MakeEA (ea1, hi, pc, 4); - pc = MakeEA (ea2, lo, pc, 4); + ea1 = MakeEA (hi, pc, 4, opcodes); + ea2 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "BIT %s,%s", ea1, ea2); break; case 0x4000: case 0x4040: case 0x4080: case 0x40c0: case 0x4100: case 0x4140: case 0x4180: case 0x41c0: @@ -302,8 +299,8 @@ CPU_DISASSEMBLE(t11) case 0x4a00: case 0x4a40: case 0x4a80: case 0x4ac0: case 0x4b00: case 0x4b40: case 0x4b80: case 0x4bc0: case 0x4c00: case 0x4c40: case 0x4c80: case 0x4cc0: case 0x4d00: case 0x4d40: case 0x4d80: case 0x4dc0: case 0x4e00: case 0x4e40: case 0x4e80: case 0x4ec0: case 0x4f00: case 0x4f40: case 0x4f80: case 0x4fc0: - pc = MakeEA (ea1, hi, pc, 4); - pc = MakeEA (ea2, lo, pc, 4); + ea1 = MakeEA (hi, pc, 4, opcodes); + ea2 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "BIC %s,%s", ea1, ea2); break; case 0x5000: case 0x5040: case 0x5080: case 0x50c0: case 0x5100: case 0x5140: case 0x5180: case 0x51c0: @@ -314,8 +311,8 @@ CPU_DISASSEMBLE(t11) case 0x5a00: case 0x5a40: case 0x5a80: case 0x5ac0: case 0x5b00: case 0x5b40: case 0x5b80: case 0x5bc0: case 0x5c00: case 0x5c40: case 0x5c80: case 0x5cc0: case 0x5d00: case 0x5d40: case 0x5d80: case 0x5dc0: case 0x5e00: case 0x5e40: case 0x5e80: case 0x5ec0: case 0x5f00: case 0x5f40: case 0x5f80: case 0x5fc0: - pc = MakeEA (ea1, hi, pc, 4); - pc = MakeEA (ea2, lo, pc, 4); + ea1 = MakeEA (hi, pc, 4, opcodes); + ea2 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "BIS %s,%s", ea1, ea2); break; case 0x6000: case 0x6040: case 0x6080: case 0x60c0: case 0x6100: case 0x6140: case 0x6180: case 0x61c0: @@ -326,13 +323,13 @@ CPU_DISASSEMBLE(t11) case 0x6a00: case 0x6a40: case 0x6a80: case 0x6ac0: case 0x6b00: case 0x6b40: case 0x6b80: case 0x6bc0: case 0x6c00: case 0x6c40: case 0x6c80: case 0x6cc0: case 0x6d00: case 0x6d40: case 0x6d80: case 0x6dc0: case 0x6e00: case 0x6e40: case 0x6e80: case 0x6ec0: case 0x6f00: case 0x6f40: case 0x6f80: case 0x6fc0: - pc = MakeEA (ea1, hi, pc, 4); - pc = MakeEA (ea2, lo, pc, 4); + ea1 = MakeEA (hi, pc, 4, opcodes); + ea2 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "ADD %s,%s", ea1, ea2); break; case 0x7800: case 0x7840: case 0x7880: case 0x78c0: case 0x7900: case 0x7940: case 0x7980: case 0x79c0: - pc = MakeEA (ea1, lo, pc, 4); + ea1 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "XOR %s,%s", regs[hi & 7], ea1); break; @@ -381,59 +378,59 @@ CPU_DISASSEMBLE(t11) break; case 0x8a00: - pc = MakeEA (ea1, lo, pc, 2); + ea1 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "CLRB %s", ea1); break; case 0x8a40: - pc = MakeEA (ea1, lo, pc, 2); + ea1 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "COMB %s", ea1); break; case 0x8a80: - pc = MakeEA (ea1, lo, pc, 2); + ea1 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "INCB %s", ea1); break; case 0x8ac0: - pc = MakeEA (ea1, lo, pc, 2); + ea1 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "DECB %s", ea1); break; case 0x8b00: - pc = MakeEA (ea1, lo, pc, 2); + ea1 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "NEGB %s", ea1); break; case 0x8b40: - pc = MakeEA (ea1, lo, pc, 2); + ea1 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "ADCB %s", ea1); break; case 0x8b80: - pc = MakeEA (ea1, lo, pc, 2); + ea1 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "SBCB %s", ea1); break; case 0x8bc0: - pc = MakeEA (ea1, lo, pc, 2); + ea1 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "TSTB %s", ea1); break; case 0x8c00: - pc = MakeEA (ea1, lo, pc, 2); + ea1 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "RORB %s", ea1); break; case 0x8c40: - pc = MakeEA (ea1, lo, pc, 2); + ea1 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "ROLB %s", ea1); break; case 0x8c80: - pc = MakeEA (ea1, lo, pc, 2); + ea1 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "ASRB %s", ea1); break; case 0x8cc0: - pc = MakeEA (ea1, lo, pc, 2); + ea1 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "ASLB %s", ea1); break; case 0x8d00: - pc = MakeEA (ea1, lo, pc, 2); + ea1 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "MTPS %s", ea1); break; case 0x8dc0: - pc = MakeEA (ea1, lo, pc, 2); + ea1 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "MFPS %s", ea1); break; case 0x9000: case 0x9040: case 0x9080: case 0x90c0: case 0x9100: case 0x9140: case 0x9180: case 0x91c0: @@ -444,8 +441,8 @@ CPU_DISASSEMBLE(t11) case 0x9a00: case 0x9a40: case 0x9a80: case 0x9ac0: case 0x9b00: case 0x9b40: case 0x9b80: case 0x9bc0: case 0x9c00: case 0x9c40: case 0x9c80: case 0x9cc0: case 0x9d00: case 0x9d40: case 0x9d80: case 0x9dc0: case 0x9e00: case 0x9e40: case 0x9e80: case 0x9ec0: case 0x9f00: case 0x9f40: case 0x9f80: case 0x9fc0: - pc = MakeEA (ea1, hi, pc, 2); - pc = MakeEA (ea2, lo, pc, 2); + ea1 = MakeEA (hi, pc, 2, opcodes); + ea2 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "MOVB %s,%s", ea1, ea2); break; case 0xa000: case 0xa040: case 0xa080: case 0xa0c0: case 0xa100: case 0xa140: case 0xa180: case 0xa1c0: @@ -456,8 +453,8 @@ CPU_DISASSEMBLE(t11) case 0xaa00: case 0xaa40: case 0xaa80: case 0xaac0: case 0xab00: case 0xab40: case 0xab80: case 0xabc0: case 0xac00: case 0xac40: case 0xac80: case 0xacc0: case 0xad00: case 0xad40: case 0xad80: case 0xadc0: case 0xae00: case 0xae40: case 0xae80: case 0xaec0: case 0xaf00: case 0xaf40: case 0xaf80: case 0xafc0: - pc = MakeEA (ea1, hi, pc, 2); - pc = MakeEA (ea2, lo, pc, 2); + ea1 = MakeEA (hi, pc, 2, opcodes); + ea2 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "CMPB %s,%s", ea1, ea2); break; case 0xb000: case 0xb040: case 0xb080: case 0xb0c0: case 0xb100: case 0xb140: case 0xb180: case 0xb1c0: @@ -468,8 +465,8 @@ CPU_DISASSEMBLE(t11) case 0xba00: case 0xba40: case 0xba80: case 0xbac0: case 0xbb00: case 0xbb40: case 0xbb80: case 0xbbc0: case 0xbc00: case 0xbc40: case 0xbc80: case 0xbcc0: case 0xbd00: case 0xbd40: case 0xbd80: case 0xbdc0: case 0xbe00: case 0xbe40: case 0xbe80: case 0xbec0: case 0xbf00: case 0xbf40: case 0xbf80: case 0xbfc0: - pc = MakeEA (ea1, hi, pc, 2); - pc = MakeEA (ea2, lo, pc, 2); + ea1 = MakeEA (hi, pc, 2, opcodes); + ea2 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "BITB %s,%s", ea1, ea2); break; case 0xc000: case 0xc040: case 0xc080: case 0xc0c0: case 0xc100: case 0xc140: case 0xc180: case 0xc1c0: @@ -480,8 +477,8 @@ CPU_DISASSEMBLE(t11) case 0xca00: case 0xca40: case 0xca80: case 0xcac0: case 0xcb00: case 0xcb40: case 0xcb80: case 0xcbc0: case 0xcc00: case 0xcc40: case 0xcc80: case 0xccc0: case 0xcd00: case 0xcd40: case 0xcd80: case 0xcdc0: case 0xce00: case 0xce40: case 0xce80: case 0xcec0: case 0xcf00: case 0xcf40: case 0xcf80: case 0xcfc0: - pc = MakeEA (ea1, hi, pc, 2); - pc = MakeEA (ea2, lo, pc, 2); + ea1 = MakeEA (hi, pc, 2, opcodes); + ea2 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "BICB %s,%s", ea1, ea2); break; case 0xd000: case 0xd040: case 0xd080: case 0xd0c0: case 0xd100: case 0xd140: case 0xd180: case 0xd1c0: @@ -492,8 +489,8 @@ CPU_DISASSEMBLE(t11) case 0xda00: case 0xda40: case 0xda80: case 0xdac0: case 0xdb00: case 0xdb40: case 0xdb80: case 0xdbc0: case 0xdc00: case 0xdc40: case 0xdc80: case 0xdcc0: case 0xdd00: case 0xdd40: case 0xdd80: case 0xddc0: case 0xde00: case 0xde40: case 0xde80: case 0xdec0: case 0xdf00: case 0xdf40: case 0xdf80: case 0xdfc0: - pc = MakeEA (ea1, hi, pc, 2); - pc = MakeEA (ea2, lo, pc, 2); + ea1 = MakeEA (hi, pc, 2, opcodes); + ea2 = MakeEA (lo, pc, 2, opcodes); util::stream_format(stream, "BISB %s,%s", ea1, ea2); break; case 0xe000: case 0xe040: case 0xe080: case 0xe0c0: case 0xe100: case 0xe140: case 0xe180: case 0xe1c0: @@ -504,8 +501,8 @@ CPU_DISASSEMBLE(t11) case 0xea00: case 0xea40: case 0xea80: case 0xeac0: case 0xeb00: case 0xeb40: case 0xeb80: case 0xebc0: case 0xec00: case 0xec40: case 0xec80: case 0xecc0: case 0xed00: case 0xed40: case 0xed80: case 0xedc0: case 0xee00: case 0xee40: case 0xee80: case 0xeec0: case 0xef00: case 0xef40: case 0xef80: case 0xefc0: - pc = MakeEA (ea1, hi, pc, 4); - pc = MakeEA (ea2, lo, pc, 4); + ea1 = MakeEA (hi, pc, 4, opcodes); + ea2 = MakeEA (lo, pc, 4, opcodes); util::stream_format(stream, "SUB %s,%s", ea1, ea2); break; @@ -514,5 +511,10 @@ CPU_DISASSEMBLE(t11) break; } - return (pc - PC) | flags | DASMFLAG_SUPPORTED; + return (pc - PC) | flags | SUPPORTED; +} + +u32 t11_disassembler::opcode_alignment() const +{ + return 2; } diff --git a/src/devices/cpu/t11/t11dasm.h b/src/devices/cpu/t11/t11dasm.h new file mode 100644 index 00000000000..4d51dd75777 --- /dev/null +++ b/src/devices/cpu/t11/t11dasm.h @@ -0,0 +1,33 @@ +// license:BSD-3-Clause +// copyright-holders:Aaron Giles +/* + * A T11 disassembler + * + * Note: this is probably not the most efficient disassembler in the world :-) + * + * This code written by Aaron Giles (agiles@sirius.com) for the MAME project + * + */ + +#ifndef MAME_CPU_T11_T11DASM_H +#define MAME_CPU_T11_T11DASM_H + +#pragma once + +class t11_disassembler : public util::disasm_interface +{ +public: + t11_disassembler() = default; + virtual ~t11_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *const regs[8]; + u16 r16p(offs_t &pc, const data_buffer &opcodes); + std::string MakeEA (int lo, offs_t &pc, int width, const data_buffer &opcodes); + +}; + +#endif diff --git a/src/devices/cpu/tlcs870/tlcs870.cpp b/src/devices/cpu/tlcs870/tlcs870.cpp index c24b41da744..4488ccee744 100644 --- a/src/devices/cpu/tlcs870/tlcs870.cpp +++ b/src/devices/cpu/tlcs870/tlcs870.cpp @@ -16,86 +16,9 @@ #include "emu.h" #include "tlcs870.h" +#include "tlcs870d.h" #include "debugger.h" - -// di, ei, j, and test are just 'alias' opcodes -static const char *const op_names[] = { - "??", - "call", "callp", "callv", "clr", "cpl", - "daa", "das", "dec", /*"di",*/ "div", - /*"ei",*/ - "inc", - /*"j",*/ "jp", "jr", "jrs", - "ld", "ldw", - "mcmp", "mul", - "nop", - "pop", "push", - "ret", "reti", "retn", "rolc", "rold", "rorc", "rord", - "set", "shlc", "shrc", "swap", "swi", - /*"test",*/ "xch", - // ALU operations - "addc", - "add", - "subb", - "sub", - "and", - "xor", - "or", - "cmp", -}; - - - - -static const char *const reg8[] = { - "A", - "W", - "C", - "B", - "E", - "D", - "L", - "H" -}; - -static const char *const type_x[] = { - "(x)", - "(PC+A)", - "(DE)", - "(HL)", - "(HL+d)", - "(HL+C)", - "(HL+)", - "(-HL)", -}; - -static const char *const conditions[] = { - "EQ/Z", - "NE/NZ", - "LT/CS", - "GE/CC", - "LE", - "GT", - "T", - "F", -}; - -static const char *const reg16[] = { - "WA", - "BC", - "DE", - "HL" -}; - -#ifdef UNUSED_DEFINTION -static const char *const reg16p[] = { - "DE", - "HL" -}; -#endif - - #define IS16BIT 0x80 #define BITPOS 0x40 #define BITPOS_INDIRECT 0x20 @@ -2336,71 +2259,6 @@ bool tlcs870_device::stream_arg(std::ostream &stream, uint32_t pc, const char *p return false; } -void tlcs870_device::disasm_disassemble_param(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options, int type, uint16_t val) -{ - int basetype = type & MODE_MASK; - - if (basetype==ADDR_IN_IMM_X) util::stream_format(stream, " ($%02x)", val); // direct - if (basetype==ADDR_IN_PC_PLUS_REG_A) util::stream_format(stream, " %s", type_x[1]); - if (basetype==ADDR_IN_DE) util::stream_format(stream, " %s", type_x[2]); - if (basetype==ADDR_IN_HL) util::stream_format(stream, " %s", type_x[3]); - if (basetype==ADDR_IN_HL_PLUS_IMM_D) util::stream_format(stream, " (HL+$%04x)", val); // todo, sign extend - if (basetype==ADDR_IN_HL_PLUS_REG_C) util::stream_format(stream, " %s", type_x[5]); - if (basetype==ADDR_IN_HLINC) util::stream_format(stream, " %s", type_x[6]); - if (basetype==ADDR_IN_DECHL) util::stream_format(stream, " %s", type_x[7]); - - if (basetype==REG_8BIT) - { - if (type&IS16BIT) util::stream_format(stream, " %s", reg16[val&3]); - else util::stream_format(stream, " %s", reg8[val & 7]); - } - - if (basetype==CONDITIONAL) util::stream_format(stream, " %s", conditions[val]); - if (basetype==(STACKPOINTER & MODE_MASK)) util::stream_format(stream, " SP"); - if (basetype==REGISTERBANK) util::stream_format(stream, " RBS"); - if (basetype==PROGRAMSTATUSWORD) util::stream_format(stream, " PSW"); - if (basetype==MEMVECTOR_16BIT) util::stream_format(stream, " ($%04x)", val); - if (basetype==ABSOLUTE_VAL_8) - { - if (type&IS16BIT) util::stream_format(stream, "$%04x", val); - else util::stream_format(stream, "$%02x", val); - } - - if (basetype == (CARRYFLAG & MODE_MASK)) - { - util::stream_format(stream, " CF"); - } - else if (type&BITPOS) - { - if (type & BITPOS_INDIRECT) util::stream_format(stream, ".BIT_%s", reg8[m_bitpos&7]); - else util::stream_format(stream, ".BIT_%d", m_bitpos); - } -} - -offs_t tlcs870_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) -{ - m_addr = pc; - - decode(); - - util::stream_format (stream, "%-5s", op_names[ m_op ] ); - - if (m_param1_type) - { - disasm_disassemble_param(stream, pc, oprom, opram, options, m_param1_type, m_param1); - } - - if (m_param2_type) - { - if (m_param1_type) util::stream_format(stream, ","); - - disasm_disassemble_param(stream, pc, oprom, opram, options, m_param2_type, m_param2); - - } - - return (m_addr - pc) | DASMFLAG_SUPPORTED; -} - void tlcs870_device::execute_set_input(int inputnum, int state) { #if 0 @@ -3305,3 +3163,8 @@ void tlcs870_device::state_string_export(const device_state_entry &entry, std::s } } + +util::disasm_interface *tlcs870_device::create_disassembler() +{ + return new tlcs870_disassembler; +} diff --git a/src/devices/cpu/tlcs870/tlcs870.h b/src/devices/cpu/tlcs870/tlcs870.h index ea57533e122..ae05b38193f 100644 --- a/src/devices/cpu/tlcs870/tlcs870.h +++ b/src/devices/cpu/tlcs870/tlcs870.h @@ -106,11 +106,7 @@ protected: virtual void state_export(const device_state_entry &entry) override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 6; } - virtual void disasm_disassemble_param(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options, int type, uint16_t val); - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; - + virtual util::disasm_interface *create_disassembler() override; uint32_t m_debugger_temp; diff --git a/src/devices/cpu/tlcs870/tlcs870d.cpp b/src/devices/cpu/tlcs870/tlcs870d.cpp new file mode 100644 index 00000000000..3c3448863c2 --- /dev/null +++ b/src/devices/cpu/tlcs870/tlcs870d.cpp @@ -0,0 +1,2263 @@ +// license:BSD-3-Clause +// copyright-holders:David Haywood +/************************************************************************************************************* + + Toshiba TLCS-870 Series MCUs + + The TLCS-870/X expands on this instruction set using the same base encoding. + + The TLCS-870/C appears to have a completely different encoding. + + loosely baesd on the tlcs90 core by Luca Elia + +*************************************************************************************************************/ + +#include "emu.h" +#include "tlcs870d.h" + +#define IS16BIT 0x80 +#define BITPOS 0x40 +#define BITPOS_INDIRECT 0x20 + +#define ABSOLUTE_VAL_8 0x01 +#define REG_8BIT 0x02 +#define CONDITIONAL 0x03 +#define STACKPOINTER (0x04 | IS16BIT) // this is a 16-bit reg +#define CARRYFLAG (0x5 | BITPOS) // also flag as BITPOS since it's a bit operation? +#define MEMVECTOR_16BIT 0x6 +#define REGISTERBANK 0x7 +#define PROGRAMSTATUSWORD 0x8 + +#define ABSOLUTE_VAL_16 (ABSOLUTE_VAL_8|IS16BIT) +#define REG_16BIT (REG_8BIT|IS16BIT) + +#define ADDR_IN_BASE 0x10 +#define ADDR_IN_IMM_X (ADDR_IN_BASE+0x0) +#define ADDR_IN_PC_PLUS_REG_A (ADDR_IN_BASE+0x1) +#define ADDR_IN_DE (ADDR_IN_BASE+0x2) +#define ADDR_IN_HL (ADDR_IN_BASE+0x3) +#define ADDR_IN_HL_PLUS_IMM_D (ADDR_IN_BASE+0x4) +#define ADDR_IN_HL_PLUS_REG_C (ADDR_IN_BASE+0x5) +#define ADDR_IN_HLINC (ADDR_IN_BASE+0x6) +#define ADDR_IN_DECHL (ADDR_IN_BASE+0x7) + +#define MODE_MASK 0x1f + +#define FLAG_J (0x80) +#define FLAG_Z (0x40) +#define FLAG_C (0x20) +#define FLAG_H (0x10) + +u32 tlcs870_disassembler::opcode_alignment() const +{ + return 1; +} + + +uint8_t tlcs870_disassembler::READ8() +{ + uint8_t b0 = m_opcodes->r8( m_addr++ ); + m_addr &= 0xffff; + return b0; +} + +uint16_t tlcs870_disassembler::READ16() +{ + uint8_t b0 = READ8(); + return b0 | (READ8() << 8); +} + +// di, ei, j, and test are just 'alias' opcodes +const char *const tlcs870_disassembler::op_names[] = { + "??", + "call", "callp", "callv", "clr", "cpl", + "daa", "das", "dec", /*"di",*/ "div", + /*"ei",*/ + "inc", + /*"j",*/ "jp", "jr", "jrs", + "ld", "ldw", + "mcmp", "mul", + "nop", + "pop", "push", + "ret", "reti", "retn", "rolc", "rold", "rorc", "rord", + "set", "shlc", "shrc", "swap", "swi", + /*"test",*/ "xch", + // ALU operations + "addc", + "add", + "subb", + "sub", + "and", + "xor", + "or", + "cmp", +}; + + + + +const char *const tlcs870_disassembler::reg8[] = { + "A", + "W", + "C", + "B", + "E", + "D", + "L", + "H" +}; + +const char *const tlcs870_disassembler::type_x[] = { + "(x)", + "(PC+A)", + "(DE)", + "(HL)", + "(HL+d)", + "(HL+C)", + "(HL+)", + "(-HL)", +}; + +const char *const tlcs870_disassembler::conditions[] = { + "EQ/Z", + "NE/NZ", + "LT/CS", + "GE/CC", + "LE", + "GT", + "T", + "F", +}; + +const char *const tlcs870_disassembler::reg16[] = { + "WA", + "BC", + "DE", + "HL" +}; + +const char *const tlcs870_disassembler::reg16p[] = { + "DE", + "HL" +}; + +void tlcs870_disassembler::decode() +{ + m_op = 0; + m_param1_type = 0; + m_param1 = 0; + m_param2_type = 0; + m_param2 = 0; + m_bitpos = 0; + m_cycles = 1; + m_flagsaffected = 0; // needed to signal which flags to change and which to leave alone in some cases (LD operations at least) + + uint8_t b0; + uint8_t b1; + + int tmppc = m_addr; + + b0 = READ8(); + + + switch (b0) + { + case 0x00: + m_op = NOP; + // NOP; + break; + + case 0x01: + // SWAP A + m_op = SWAP; + + m_param1_type = REG_8BIT; + m_param1 = 0; // A + break; + + case 0x02: + // MUL W,A + m_op = MUL; + + m_param1_type = REG_8BIT; + m_param1 = 1; // W + + m_param2_type = REG_8BIT; + m_param2 = 0; // A + break; + + case 0x03: + // DIV WA,C + m_op = DIV; + + m_param1_type = REG_16BIT; + m_param1 = 0; // WA + + m_param2_type = REG_8BIT; + m_param2 = 2; // C + break; + + case 0x04: + // RETI + m_op = RETI; + break; + + case 0x05: + // RET + m_op = RET; + break; + + case 0x06: + // POP PSW + m_op = POP; + m_param1_type = PROGRAMSTATUSWORD; + break; + + case 0x07: + // PUSH PSW: + m_op = PUSH; + m_param1_type = PROGRAMSTATUSWORD; + break; + + case 0x08: + case 0x09: + // unused? + break; + + case 0x0a: + // DAA A + m_op = DAA; + + m_param1_type = REG_8BIT; + m_param1 = 0; // A + break; + + case 0x0b: + // DAS A + m_op = DAS; + + m_param1_type = REG_8BIT; + m_param1 = 0; // A + break; + + case 0x0c: + // CLR CF + m_op = CLR; + + m_param1_type = CARRYFLAG; // 16-bit register + //m_param1 = 0; + break; + + case 0x0d: + // SET CF + m_op = SET; + + m_param1_type = CARRYFLAG; // 16-bit register + //m_param1 = 0; + break; + + case 0x0e: + // CPL CF + m_op = CPL; + + m_param1_type = CARRYFLAG; // 16-bit register + //m_param1 = 0; + break; + + case 0x0f: + // LD RBS,n + m_op = LD; // Flags / Cycles 1--- / 2 + m_flagsaffected |= FLAG_J; + + m_param1_type = REGISTERBANK; // 4-bit register + //m_param1 = 0; + + m_param2_type = ABSOLUTE_VAL_8; + m_param2 = READ8(); + + break; + + case 0x10: + case 0x11: + case 0x12: + case 0x13: + // INC rr + m_op = INC; + + m_param1_type = REG_16BIT; // 16-bit register + m_param1 = b0&3; + + break; + + case 0x14: + case 0x15: + case 0x16: + case 0x17: + // LD rr,mn + m_op = LD; // Flags / Cycles 1--- / 3 + m_flagsaffected |= FLAG_J; + + m_param1_type = REG_16BIT; // 16-bit register + m_param1 = b0&3; + + m_param2_type = ABSOLUTE_VAL_16; // absolute value + m_param2 = READ16(); // 16-bit + + break; + + case 0x18: + case 0x19: + case 0x1a: + case 0x1b: + // DEC rr + m_op = DEC; + + m_param1_type = REG_16BIT; // 16-bit register + m_param1 = b0&3; + + break; + + case 0x1c: + // SHLC A + m_op = SHLC; + + m_param1_type = REG_8BIT; + m_param1 = 0; // A + break; + + case 0x1d: + // SHRC A + m_op = SHRC; + + m_param1_type = REG_8BIT; + m_param1 = 0; // A + break; + + case 0x1e: + // ROLC A + m_op = ROLC; + + m_param1_type = REG_8BIT; + m_param1 = 0; // A + break; + + case 0x1f: + // RORC A + m_op = RORC; + + m_param1_type = REG_8BIT; + m_param1 = 0; // A + break; + + case 0x20: + // INC (x) + m_op = INC; + m_param1_type = ADDR_IN_IMM_X; + m_param1 = READ8(); + break; + + case 0x21: + // INC (HL) + m_op = INC; + m_param1_type = ADDR_IN_HL; + //m_param1 = 0; + break; + + case 0x22: + // LD A,(x) + m_op = LD; // Flags / Cycles 1Z-- / 3 + m_flagsaffected |= FLAG_J | FLAG_Z; + + m_param1_type = REG_8BIT; + m_param1 = 0; // A + + m_param2_type = ADDR_IN_IMM_X; + m_param2 = READ8(); + break; + + case 0x23: + // LD A,(HL) + m_op = LD; // Flags / Cycles 1Z-- / 2 + m_flagsaffected |= FLAG_J | FLAG_Z; + + m_param1_type = REG_8BIT; + m_param1 = 0; // A + + m_param2_type = ADDR_IN_HL; + //m_param2 = 0; + break; + + case 0x24: + // LDW (x),mn + m_op = LDW; + m_param1_type = ADDR_IN_IMM_X; // 8-bit memory address + m_param1 = READ8(); + + m_param2_type = ABSOLUTE_VAL_16; // absolute value + m_param2 = READ16(); + break; + + case 0x25: + // LDW (HL),mn + m_op = LDW; + m_param1_type = ADDR_IN_HL; + //m_param1 = 0; + + m_param2_type = ABSOLUTE_VAL_16; + m_param2 = READ16(); + break; + + + case 0x26: + // LD (x),(y) // Flags / Cycles 1Z-- / 5 + m_op = LD; + m_flagsaffected |= FLAG_J | FLAG_Z; + + m_param2_type = ADDR_IN_IMM_X; + m_param2 = READ8(); + + m_param1_type = ADDR_IN_IMM_X; + m_param1 = READ8(); + break; + + case 0x27: + // unused + break; + + case 0x28: + // DEC (x) + m_op = DEC; + m_param1_type = ADDR_IN_IMM_X; + m_param1 = READ8(); + break; + + case 0x29: + // DEC (HL) + m_op = DEC; + m_param1_type = ADDR_IN_HL; + //m_param1 = 0; + break; + + case 0x2a: + // LD (x),A // Flags / Cycles 1Z-- / 3 + m_op = LD; + m_flagsaffected |= FLAG_J | FLAG_Z; + + m_param1_type = ADDR_IN_IMM_X; + m_param1 = READ8(); + + m_param2_type = REG_8BIT; + m_param2 = 0; // A + + break; + + case 0x2b: + // LD (HL),A // Flags / Cycles 1--- / 2 + m_op = LD; + m_flagsaffected |= FLAG_J; + + m_param1_type = ADDR_IN_HL; + //m_param1 = 0; + + m_param2_type = REG_8BIT; + m_param2 = 0; // A + break; + + case 0x2c: + // LD (x),n + m_op = LD; // Flags / Cycles 1--- / 4 + m_flagsaffected |= FLAG_J; + + m_param1_type = ADDR_IN_IMM_X; // 8-bit memory address + m_param1 = READ8(); + + m_param2_type = ABSOLUTE_VAL_8; // absolute value + m_param2 = READ8(); + + break; + + case 0x2d: + // LD (HL),n + m_op = LD; // Flags / Cycles 1--- / 3 + m_flagsaffected |= FLAG_J; + + m_param1_type = ADDR_IN_HL; // memory address in 16-bit register + //m_param1 = 3; // (HL) + + m_param2_type = ABSOLUTE_VAL_8; // absolute value + m_param2 = READ8(); + + break; + + case 0x2e: + // CLR (x) + m_op = CLR; + m_param1_type = ADDR_IN_IMM_X; // 8-bit memory address + m_param1 = READ8(); + + break; + + case 0x2f: + // CLR (HL) + m_op = CLR; + m_param1_type = ADDR_IN_HL; // memory address in 16-bit register + //m_param1 = 3; // (HL) + + break; + + case 0x30: + case 0x31: + case 0x32: + case 0x33: + case 0x34: + case 0x35: + case 0x36: + case 0x37: + // LD r,n + + m_op = LD; // Flags / Cycles 1--- / 2 + m_flagsaffected |= FLAG_J; + + m_param1_type = REG_8BIT; // 8-bit register register + m_param1 = b0&7; + + m_param2_type = ABSOLUTE_VAL_8; // absolute value + m_param2 = READ8(); + + + break; + + case 0x38: + case 0x39: + case 0x3a: + case 0x3b: + case 0x3c: + case 0x3d: + case 0x3e: + case 0x3f: + break; + + case 0x40: + case 0x41: + case 0x42: + case 0x43: + case 0x44: + case 0x45: + case 0x46: + case 0x47: + // SET (x).b + b1 = READ8(); +#if 0 + // this is just an alias + if ((b0 == 0x40) && (b1 == 0x3a)) + { + // EI 'Assembler expansion machine instruction' + break; + } +#endif + m_op = SET; + + m_param1_type = ADDR_IN_IMM_X | BITPOS; + m_param1 = b1; + m_bitpos = b0 & 7; + + break; + + case 0x48: + case 0x49: + case 0x4a: + case 0x4b: + case 0x4c: + case 0x4d: + case 0x4e: + case 0x4f: + // CLR (x).b + b1 = READ8(); +#if 0 + // this is just an alias + if ((b0 == 0x48) && (b1 == 0x3a)) + { + // DI 'Assembler expansion machine instruction' + break; + } +#endif + m_op = CLR; + + m_param1_type = ADDR_IN_IMM_X | BITPOS; + m_param1 = b1; + m_bitpos = b0 & 7; + + break; + + case 0x50: + case 0x51: + case 0x52: + case 0x53: + case 0x54: + case 0x55: + case 0x56: + case 0x57: + // LD A,r 0101 0rrr + m_op = LD; // Flags / Cycles 1Z-- / 1 + m_flagsaffected |= FLAG_J | FLAG_Z; + + m_param1_type = REG_8BIT; + m_param1 = 0; // A + + m_param2_type = REG_8BIT; + m_param2 = b0 & 0x7; + + break; + + case 0x58: + case 0x59: + case 0x5a: + case 0x5b: + case 0x5c: + case 0x5d: + case 0x5e: + case 0x5f: + // LD r,A 0101 1rrr + m_op = LD; // Flags / Cycles 1Z-- / 1 + m_flagsaffected |= FLAG_J | FLAG_Z; + + m_param2_type = REG_8BIT; + m_param2 = 0; // A + + m_param1_type = REG_8BIT; + m_param1 = b0 & 0x7; + break; + + case 0x60: + case 0x61: + case 0x62: + case 0x63: + case 0x64: + case 0x65: + case 0x66: + case 0x67: + // INC r + m_op = INC; + m_param1_type = REG_8BIT; + m_param1 = b0 & 0x7; + break; + + case 0x68: + case 0x69: + case 0x6a: + case 0x6b: + case 0x6c: + case 0x6d: + case 0x6e: + case 0x6f: + // DEC r + m_op = DEC; + m_param1_type = REG_8BIT; + m_param1 = b0 & 0x7; + break; + + case 0x70: + case 0x71: + case 0x72: + case 0x73: + case 0x74: + case 0x75: + case 0x76: + case 0x77: + // (ALU OP) A,n + m_op = (b0 & 0x7)+ALU_ADDC; + + m_param1_type = REG_8BIT; + m_param1 = 0; // A + + m_param2_type = ABSOLUTE_VAL_8; + m_param2 = READ8(); + + break; + + case 0x78: + case 0x79: + case 0x7a: + case 0x7b: + case 0x7c: + case 0x7d: + case 0x7e: + case 0x7f: + // (ALU OP) A,(x) + m_op = (b0 & 0x7)+ALU_ADDC; + + m_param1_type = REG_8BIT; + m_param1 = 0; // A + + m_param2_type = ADDR_IN_IMM_X; + m_param2 = READ8(); + + break; + + case 0x80: + case 0x81: + case 0x82: + case 0x83: + case 0x84: + case 0x85: + case 0x86: + case 0x87: + case 0x88: + case 0x89: + case 0x8a: + case 0x8b: + case 0x8c: + case 0x8d: + case 0x8e: + case 0x8f: + case 0x90: + case 0x91: + case 0x92: + case 0x93: + case 0x94: + case 0x95: + case 0x96: + case 0x97: + case 0x98: + case 0x99: + case 0x9a: + case 0x9b: + case 0x9c: + case 0x9d: + case 0x9e: + case 0x9f: + { + // JRS T,a + m_op = JRS; + + m_param1_type = CONDITIONAL; + m_param1 = 6; + + m_param2_type = ABSOLUTE_VAL_16; + + int val = b0 & 0x1f; + if (val & 0x10) val -= 0x20; + + m_param2 = tmppc + 2 + val; + + break; + } + case 0xa0: + case 0xa1: + case 0xa2: + case 0xa3: + case 0xa4: + case 0xa5: + case 0xa6: + case 0xa7: + case 0xa8: + case 0xa9: + case 0xaa: + case 0xab: + case 0xac: + case 0xad: + case 0xae: + case 0xaf: + case 0xb0: + case 0xb1: + case 0xb2: + case 0xb3: + case 0xb4: + case 0xb5: + case 0xb6: + case 0xb7: + case 0xb8: + case 0xb9: + case 0xba: + case 0xbb: + case 0xbc: + case 0xbd: + case 0xbe: + case 0xbf: + { + // JRS F,a + m_op = JRS; + + m_param1_type = CONDITIONAL; + m_param1 = 7; + + m_param2_type = ABSOLUTE_VAL_16; + + int val = b0 & 0x1f; + if (val & 0x10) val -= 0x20; + + m_param2 = tmppc + 2 + val; + + break; + } + + case 0xc0: + case 0xc1: + case 0xc2: + case 0xc3: + case 0xc4: + case 0xc5: + case 0xc6: + case 0xc7: + case 0xc8: + case 0xc9: + case 0xca: + case 0xcb: + case 0xcc: + case 0xcd: + case 0xce: + case 0xcf: + // CALLV n + m_op = CALLV; + + m_param1_type = MEMVECTOR_16BIT; + + m_param1 = 0xffc0 + ((b0 & 0xf) * 2); + + break; + + case 0xd0: + case 0xd1: + case 0xd2: + case 0xd3: + case 0xd4: + case 0xd5: + case 0xd6: + case 0xd7: + { + // JR cc,a + + m_op = JR; + + m_param1_type = CONDITIONAL; + m_param1 = b0 & 0x7; + + m_param2_type = ABSOLUTE_VAL_16; + + int val = READ8(); + if (val & 0x80) val -= 0x100; + + m_param2 = tmppc+ 2 + val; + + break; + } + case 0xd8: + case 0xd9: + case 0xda: + case 0xdb: + case 0xdc: + case 0xdd: + case 0xde: + case 0xdf: + // LD CF, (x).b aka TEST (x).b + m_op = LD; // Flags / Cycles %-*- / 4 + m_flagsaffected |= FLAG_J | FLAG_C; + + m_param1_type = CARRYFLAG; + //m_param1 = 0; + + m_param2_type = ADDR_IN_IMM_X | BITPOS; + m_param2 = READ8(); + m_bitpos = b0 & 0x7; + break; + + case 0xe0: + // src prefix + decode_source(ADDR_IN_BASE+(b0&0x7), READ8()); + break; + + case 0xe1: + case 0xe2: + case 0xe3: + decode_source(ADDR_IN_BASE+(b0&0x7), 0); + break; + + case 0xe4: + decode_source(ADDR_IN_BASE+(b0&0x7), READ8()); + break; + + case 0xe5: + case 0xe6: + case 0xe7: + decode_source(ADDR_IN_BASE+(b0&0x7), 0); + break; + + case 0xe8: + case 0xe9: + case 0xea: + case 0xeb: + case 0xec: + case 0xed: + case 0xee: + case 0xef: + // register prefix: g/gg + decode_register_prefix(b0); + break; + + case 0xf0: // 1111 0000 xxxx xxxx 0101 0rrr + // destination memory prefix (dst) + m_param1_type = ADDR_IN_BASE+(b0&0x7); + m_param1 = READ8(); + decode_dest(b0); + break; + + case 0xf2: // 1111 001p 0101 0rrr + case 0xf3: // 1111 001p 0101 0rrr + // destination memory prefix (dst) + m_param1_type = ADDR_IN_BASE+(b0&0x7); + decode_dest(b0); + break; + + + case 0xf4: // 1111 0100 dddd dddd 0101 0rrr + // destination memory prefix (dst) + m_param1_type = ADDR_IN_BASE+(b0&0x7); + m_param1 = READ8(); + decode_dest(b0); + break; + + case 0xf6: // 1110 0110 0101 0rrr + case 0xf7: // 1111 0111 0101 0rrr + // destination memory prefix (dst) + m_param1_type = ADDR_IN_BASE+(b0&0x7); + decode_dest(b0); + break; + + case 0xf1: + case 0xf5: + // invalid dst memory prefix + break; + + + case 0xf8: + case 0xf9: + // unused + break; + + case 0xfa: + // LD SP,mn + m_op = LD; // Flags / Cycles 1--- / 3 + m_flagsaffected |= FLAG_J; + + m_param1_type = STACKPOINTER; + //m_param1 = 0; + + m_param2_type = ABSOLUTE_VAL_16; + m_param2 = READ16(); + + break; + + case 0xfb: + { + // JR a + m_op = JR; + + m_param2_type = ABSOLUTE_VAL_16; + + int val = READ8(); + if (val & 0x80) val -= 0x100; + + m_param2 = tmppc + 2 + val; + + break; + } + + break; + + case 0xfc: + // CALL mn + m_op = CALL; + + m_param1_type = ABSOLUTE_VAL_16; + m_param1 = READ16(); + break; + + case 0xfd: + // CALLP n + m_op = CALLP; + + m_param1_type = ABSOLUTE_VAL_16; + m_param1 = READ8()+0xff00; + + break; + + case 0xfe: + // JP mn + m_op = JP; + + m_param2_type = ABSOLUTE_VAL_16; + m_param2 = READ16(); + + break; + + case 0xff: + // SWI + m_op = SWI; + + break; + } +} + +// e8 - ef use this table +void tlcs870_disassembler::decode_register_prefix(uint8_t b0) +{ + uint8_t bx; + + bx = READ8(); + + switch (bx) + { + case 0x00: + // nothing + break; + + case 0x01: + // SWAP g + m_op = SWAP; + + m_param1_type = REG_8BIT; + m_param1 = b0 & 0x7; + break; + + case 0x02: + // MUL ggG, ggL + m_op = MUL; + + m_param1_type = REG_16BIT; // odd syntax + m_param1 = b0 & 0x3; + break; + + case 0x03: + // DIV gg,C + m_op = DIV; + m_param1_type = REG_16BIT; + m_param1 = b0 & 3; + + m_param2_type = REG_8BIT; + m_param2 = 2; // C + + break; + + case 0x04: + // with E8 only + // RETN + if (b0 == 0xe8) + { + m_op = RETN; + } + + break; + + case 0x05: + break; + + case 0x06: + // POP gg + m_op = POP; + m_param1_type = REG_16BIT; + m_param1 = b0 & 3; + // b0 & 4 = invalid? + + break; + + case 0x07: + // PUSH gg + m_op = PUSH; + m_param1_type = REG_16BIT; + m_param1 = b0 & 3; + // b0 & 4 = invalid? + + break; + + case 0x08: + case 0x09: + break; + + case 0x0a: + // DAA g + m_op = DAA; + + m_param1_type = REG_8BIT; + m_param1 = b0 & 0x7; + + break; + + case 0x0b: + // DAS g + m_op = DAS; + + m_param1_type = REG_8BIT; + m_param1 = b0 & 0x7; + + break; + + case 0x0c: + case 0x0d: + case 0x0e: + case 0x0f: + break; + + case 0x10: + case 0x11: + case 0x12: + case 0x13: + // XCH rr,gg + m_op = XCH; + + m_param1_type = REG_16BIT; + m_param1 = bx & 0x3; + + m_param2_type = REG_16BIT; + m_param2 = b0 & 0x3; + break; + + case 0x14: + case 0x15: + case 0x16: + case 0x17: + // LD rr,gg + m_op = LD; // Flags / Cycles 1--- / 2 + m_flagsaffected |= FLAG_J; + + m_param1_type = REG_16BIT; + m_param1 = bx & 0x3; + + m_param2_type = REG_16BIT; + m_param2 = b0 & 0x3; + + break; + + case 0x18: + case 0x19: + case 0x1a: + case 0x1b: + break; + + case 0x1c: + // SHLC g + m_op = SHLC; + + m_param1_type = REG_8BIT; + m_param1 = b0 & 0x7; + + break; + + case 0x1d: + // SHRC g + m_op = SHRC; + + m_param1_type = REG_8BIT; + m_param1 = b0 & 0x7; + + break; + + case 0x1e: + // ROLC g + m_op = ROLC; + + m_param1_type = REG_8BIT; + m_param1 = b0 & 0x7; + + break; + + case 0x1f: + // RORC g + m_op = RORC; + + m_param1_type = REG_8BIT; + m_param1 = b0 & 0x7; + + break; + + case 0x20: + case 0x21: + case 0x22: + case 0x23: + case 0x24: + case 0x25: + case 0x26: + case 0x27: + case 0x28: + case 0x29: + case 0x2a: + case 0x2b: + case 0x2c: + case 0x2d: + case 0x2e: + case 0x2f: + break; + + case 0x30: + case 0x31: + case 0x32: + case 0x33: + case 0x34: + case 0x35: + case 0x36: + case 0x37: + // (ALU OP) WA,gg + m_op = (bx & 0x7)+ALU_ADDC; + + m_param1_type = REG_16BIT; + m_param1 = 0; + + m_param2_type = REG_16BIT; + m_param2 = b0 & 3; + // b0 & 4 would be invalid? + + + break; + + case 0x38: + case 0x39: + case 0x3a: + case 0x3b: + case 0x3c: + case 0x3d: + case 0x3e: + case 0x3f: + // (ALU OP) gg,mn + m_op = (bx & 0x7)+ALU_ADDC; + + m_param1_type = REG_16BIT; + m_param1 = b0 & 0x3; + + m_param2_type = ABSOLUTE_VAL_16; // absolute value + m_param2 = READ16(); // 16-bit + + break; + + case 0x40: + case 0x41: + case 0x42: + case 0x43: + case 0x44: + case 0x45: + case 0x46: + case 0x47: + // SET g.b + m_op = SET; + + m_param1_type = REG_8BIT | BITPOS; + m_param1 = b0 & 0x7; + m_bitpos = bx & 0x7; + + + break; + + case 0x48: + case 0x49: + case 0x4a: + case 0x4b: + case 0x4c: + case 0x4d: + case 0x4e: + case 0x4f: + // CLR g.b + m_op = CLR; + + m_param1_type = REG_8BIT | BITPOS; + m_param1 = b0 & 0x7; + m_bitpos = bx & 0x7; + + break; + + case 0x50: + case 0x51: + case 0x52: + case 0x53: + case 0x54: + case 0x55: + case 0x56: + case 0x57: + break; + + case 0x58: + case 0x59: + case 0x5a: + case 0x5b: + case 0x5c: + case 0x5d: + case 0x5e: + case 0x5f: + // LD r,g + m_op = LD; // Flags / Cycles 1Z-- / 2 + m_flagsaffected |= FLAG_J | FLAG_Z; + + m_param1_type = REG_8BIT; + m_param1 = bx & 0x7; + + m_param2_type = REG_8BIT; + m_param2 = b0 & 0x7; + break; + + case 0x60: + case 0x61: + case 0x62: + case 0x63: + case 0x64: + case 0x65: + case 0x66: + case 0x67: + // (ALU OP) A,g + m_op = (bx & 0x7)+ALU_ADDC; + + m_param2_type = REG_8BIT; + m_param2 = b0 & 0x7; + + m_param1_type = REG_8BIT; + m_param1 = 0; // A + break; + + case 0x68: + case 0x69: + case 0x6a: + case 0x6b: + case 0x6c: + case 0x6d: + case 0x6e: + case 0x6f: + // (ALU OP) g,A + m_op = (bx & 0x7)+ALU_ADDC; + + m_param1_type = REG_8BIT; + m_param1 = b0 & 0x7; + + m_param2_type = REG_8BIT; + m_param2 = 0; // A + break; + + case 0x70: + case 0x71: + case 0x72: + case 0x73: + case 0x74: + case 0x75: + case 0x76: + case 0x77: + // (ALU OP) g,n + m_op = (bx & 0x7)+ALU_ADDC; + + m_param1_type = REG_8BIT; + m_param1 = b0 & 0x7; + + m_param2_type = ABSOLUTE_VAL_8; + m_param2 = READ8(); + + + break; + + case 0x78: + case 0x79: + case 0x7a: + case 0x7b: + case 0x7c: + case 0x7d: + case 0x7e: + case 0x7f: + break; + + + case 0x80: + case 0x81: + break; + + case 0x82: + case 0x83: + // SET (pp).g + m_op = SET; + m_param1_type = (ADDR_IN_DE+(bx&1)) | BITPOS | BITPOS_INDIRECT; + //m_param1 = 0; + m_bitpos = b0 & 7; + break; + + case 0x84: + case 0x85: + case 0x86: + case 0x87: + break; + + case 0x88: + case 0x89: + break; + + case 0x8a: + case 0x8b: + // CLR (pp).g + m_op = CLR; + m_param1_type = (ADDR_IN_DE+(bx&1)) | BITPOS | BITPOS_INDIRECT; + //m_param1 = 0; + m_bitpos = b0 & 7; + break; + + case 0x8c: + case 0x8d: + case 0x8e: + case 0x8f: + break; + + + case 0x90: + case 0x91: + break; + + case 0x92: + case 0x93: + // CPL (pp).g + m_op = CPL; + m_param1_type = (ADDR_IN_DE+(bx&1)) | BITPOS | BITPOS_INDIRECT; + //m_param1 = 0; + m_bitpos = b0 & 7; + break; + + case 0x94: + case 0x95: + case 0x96: + case 0x97: + break; + + case 0x9a: + case 0x9b: + // LD (pp).g,CF + m_op = LD; // Flags / Cycles 1--- / 5 + m_flagsaffected |= FLAG_J; + + m_param1_type = (ADDR_IN_DE+(bx&1)) | BITPOS | BITPOS_INDIRECT; + //m_para1 = 0; + m_bitpos = b0 & 7; + + m_param2_type = CARRYFLAG; + //m_param2 = 0; + break; + + case 0x9c: + case 0x9d: + break; + + case 0x9e: + case 0x9f: + // LD CF,(pp).g aka TEST (pp).g + m_op = LD; // Flags / Cycles %-*- / 4 + m_flagsaffected |= FLAG_J | FLAG_C; + + m_param1_type = CARRYFLAG; + //m_param1 = 0; + + m_param2_type = (ADDR_IN_DE+(bx&1)) | BITPOS | BITPOS_INDIRECT; + //m_param2 = 0; + m_bitpos = b0 & 7; + break; + + case 0xa0: + case 0xa1: + case 0xa2: + case 0xa3: + case 0xa4: + case 0xa5: + case 0xa6: + case 0xa7: + break; + + case 0xb0: + case 0xb1: + case 0xb2: + case 0xb3: + case 0xb4: + case 0xb5: + case 0xb6: + case 0xb7: + case 0xb8: + case 0xb9: + case 0xba: + case 0xbb: + case 0xbc: + case 0xbd: + case 0xbe: + case 0xbf: + break; + + case 0xc0: + case 0xc1: + case 0xc2: + case 0xc3: + case 0xc4: + case 0xc5: + case 0xc6: + case 0xc7: + // CPL g.b + m_op = CPL; + + m_param1_type = REG_8BIT | BITPOS; + m_param1 = b0 & 0x7; + m_bitpos = bx & 0x7; + break; + + case 0xc8: + case 0xc9: + case 0xca: + case 0xcb: + case 0xcc: + case 0xcd: + case 0xce: + case 0xcf: + // LD g.b,CF + m_op = LD; // Flags / Cycles 1--- / 2 + m_flagsaffected |= FLAG_J; + + m_param2_type = CARRYFLAG; + //m_param2 = 0; + + m_param1_type = REG_8BIT | BITPOS; + m_param1 = b0 & 0x7; + m_bitpos = bx & 0x7; + + break; + + case 0xd0: + case 0xd1: + case 0xd2: + case 0xd3: + case 0xd4: + case 0xd5: + case 0xd6: + case 0xd7: + // XOR CF,g.b + m_op = ALU_XOR; + + m_param1_type = CARRYFLAG; + //m_param1 = 0; + + m_param2_type = REG_8BIT | BITPOS; + m_param2 = b0 & 0x7; + m_bitpos = bx & 0x7; + + break; + + case 0xd8: + case 0xd9: + case 0xda: + case 0xdb: + case 0xdc: + case 0xdd: + case 0xde: + case 0xdf: + // LD CF,g.b aka TEST g.b + m_op = LD; // Flags / Cycles %-*- / 2 + m_flagsaffected |= FLAG_J | FLAG_C; + + m_param1_type = CARRYFLAG; + //m_param1 = 0; + + m_param2_type = REG_8BIT | BITPOS; + m_param2 = b0 & 0x7; + m_bitpos = bx & 0x7; + + break; + + case 0xe0: + case 0xe1: + case 0xe2: + case 0xe3: + case 0xe4: + case 0xe5: + case 0xe6: + case 0xe7: + case 0xe8: + case 0xe9: + case 0xea: + case 0xeb: + case 0xec: + case 0xed: + case 0xee: + case 0xef: + break; + + case 0xf0: + case 0xf1: + case 0xf2: + case 0xf3: + case 0xf4: + case 0xf5: + case 0xf6: + case 0xf7: + break; + + case 0xf8: + case 0xf9: + break; + + case 0xfa: + // LD SP,gg + m_op = LD; // Flags / Cycles 1--- / 3 + m_flagsaffected |= FLAG_J; + + m_param2_type = REG_16BIT; + m_param2 = b0 & 3; + // b0 & 4 would be invalid? + + m_param1_type = STACKPOINTER; + // m_param1 = 0; + + break; + + case 0xfb: + // LD gg,SP + m_op = LD; // Flags / Cycles 1--- / 3 + m_flagsaffected |= FLAG_J; + + m_param1_type = REG_16BIT; + m_param1 = b0 & 3; + // b0 & 4 would be invalid? + + m_param2_type = STACKPOINTER; + // m_param2 = 0; + break; + + case 0xfc: + // CALL gg + m_op = CALL; + + m_param2_type = REG_16BIT; + m_param2 = b0 & 3; + // b0 & 4 would be invalid? + + break; + + case 0xfd: + break; + + case 0xfe: + // JP gg + m_op = JP; + + m_param2_type = REG_16BIT; + m_param2 = b0 & 3; + // b0 & 4 would be invalid? + + break; + + case 0xff: + break; + + } + +} + +// e0 - e7 use this table +void tlcs870_disassembler::decode_source(int type, uint16_t val) +{ + uint8_t bx; + + bx = READ8(); + + switch (bx) + { + case 0x00: + case 0x01: + case 0x02: + case 0x03: + case 0x04: + case 0x05: + case 0x06: + case 0x07: + break; + + case 0x08: + // ROLD A,(src) + m_op = ROLD; + m_param2_type = type; + m_param2 = val; + + m_param1_type = REG_8BIT; + m_param1 = 0; // A + break; + + case 0x09: + // RORD A,(src) + m_op = RORD; + m_param2_type = type; + m_param2 = val; + + m_param1_type = REG_8BIT; + m_param1 = 0; // A + break; + + case 0x0a: + case 0x0b: + case 0x0c: + case 0x0d: + case 0x0e: + case 0x0f: + + case 0x10: + case 0x11: + case 0x12: + case 0x13: + // see dst + break; + + case 0x14: + case 0x15: + case 0x16: + case 0x17: + // LD rr, (src) + m_op = LD; // Flags / Cycles 1--- / x + m_flagsaffected |= FLAG_J; + + m_param1_type = REG_16BIT; + m_param1 = bx & 0x3; + + m_param2_type = type | IS16BIT; + m_param2 = val; + break; + + case 0x18: + case 0x19: + case 0x1a: + case 0x1b: + case 0x1c: + case 0x1d: + case 0x1e: + case 0x1f: + break; + + case 0x20: + // INC (src) + m_op = INC; + m_param1_type = type; + m_param1 = val; + + break; + + case 0x21: + case 0x22: + case 0x23: + case 0x24: + case 0x25: + break; + + case 0x26: // invalid if (src) is also (x) ? (not specified) + // LD (x),(src) + m_op = LD; // Flags / Cycles 1U-- / x + m_flagsaffected |= FLAG_J /*| FLAG_Z*/; // Z is undefined! + + m_param1_type = ADDR_IN_IMM_X; + m_param1 = READ8(); + + m_param2_type = type; + m_param2 = val; + break; + + case 0x27: + // LD (HL),(src) + m_op = LD; // Flags / Cycles 1Z-- / x + m_flagsaffected |= FLAG_J | FLAG_Z; + + m_param1_type = ADDR_IN_HL; + //m_param1 = 0; + + m_param2_type = type; + m_param2 = val; + break; + + + case 0x28: + // DEC (src) + m_op = DEC; + m_param1_type = type; + m_param1 = val; + + break; + + case 0x29: + case 0x2a: + case 0x2b: + case 0x2c: + case 0x2d: + case 0x2e: + break; + + case 0x2f: + // MCMP (src), n + m_op = MCMP; + m_param1_type = type; + m_param1 = val; + + m_param2_type = ABSOLUTE_VAL_8; + m_param2 = READ8(); + break; + + case 0x30: + case 0x31: + case 0x32: + case 0x33: + case 0x34: + case 0x35: + case 0x36: + case 0x37: + case 0x38: + case 0x39: + case 0x3a: + case 0x3b: + case 0x3c: + case 0x3d: + case 0x3e: + case 0x3f: + break; + + case 0x40: + case 0x41: + case 0x42: + case 0x43: + case 0x44: + case 0x45: + case 0x46: + case 0x47: + // SET (src).b + m_op = SET; + + m_param1_type = type | BITPOS; + m_param1 = val; + m_bitpos = bx & 0x7; + break; + + case 0x48: + case 0x49: + case 0x4a: + case 0x4b: + case 0x4c: + case 0x4d: + case 0x4e: + case 0x4f: + // CLR (src).b + m_op = CLR; + + m_param1_type = type | BITPOS; + m_param1 = val; + m_bitpos = bx & 0x7; + break; + + case 0x50: + case 0x51: + case 0x52: + case 0x53: + case 0x54: + case 0x55: + case 0x56: + case 0x57: + // see dst + break; + + case 0x58: + case 0x59: + case 0x5a: + case 0x5b: + case 0x5c: + case 0x5d: + case 0x5e: + case 0x5f: + // LD r, (src) + m_op = LD; // Flags / Cycles 1Z-- / x + m_flagsaffected |= FLAG_J | FLAG_Z; + + m_param1_type = REG_8BIT; + m_param1 = bx & 0x7; + + m_param2_type = type; + m_param2 = val; + break; + + case 0x60: + case 0x61: + case 0x62: + case 0x63: + case 0x64: + case 0x65: + case 0x66: + case 0x67: + // (ALU OP) (src), (HL) + m_op = (bx & 0x7)+ALU_ADDC; + m_param1_type = type; + m_param1 = val; + + m_param2_type = ADDR_IN_HL; + //m_param2 = 0; + break; + + case 0x68: + case 0x69: + case 0x6a: + case 0x6b: + case 0x6c: + case 0x6d: + case 0x6e: + case 0x6f: + break; + + case 0x70: + case 0x71: + case 0x72: + case 0x73: + case 0x74: + case 0x75: + case 0x76: + case 0x77: + // (ALU OP) (src), n + m_op = (bx & 0x7)+ALU_ADDC; + m_param1_type = type; + m_param1 = val; + + m_param2_type = ABSOLUTE_VAL_8; + m_param2 = READ8(); + break; + + case 0x78: + case 0x79: + case 0x7a: + case 0x7b: + case 0x7c: + case 0x7d: + case 0x7e: + case 0x7f: + // (ALU OP) A, (src) + + m_op = (bx & 0x7)+ALU_ADDC; + m_param2_type = type; + m_param2 = val; + + m_param1_type = REG_8BIT; + m_param1 = 0; // A + break; + + case 0x80: + case 0x81: + case 0x82: + case 0x83: + case 0x84: + case 0x85: + case 0x86: + case 0x87: + case 0x88: + case 0x89: + case 0x8a: + case 0x8b: + case 0x8c: + case 0x8d: + case 0x8e: + case 0x8f: + break; + + case 0x90: + case 0x91: + case 0x92: + case 0x93: + case 0x94: + case 0x95: + case 0x96: + case 0x97: + case 0x98: + case 0x99: + case 0x9a: + case 0x9b: + case 0x9c: + case 0x9d: + case 0x9e: + case 0x9f: + break; + + case 0xa0: + case 0xa1: + case 0xa2: + case 0xa3: + case 0xa4: + case 0xa5: + case 0xa6: + case 0xa7: + break; + + case 0xa8: + case 0xa9: + case 0xaa: + case 0xab: + case 0xac: + case 0xad: + case 0xae: + case 0xaf: + // XCH r,(src) + m_op = XCH; + + m_param1_type = REG_8BIT; + m_param1 = bx & 0x7; + + m_param2_type = type; + m_param2 = val; + break; + + + case 0xb0: + case 0xb1: + case 0xb2: + case 0xb3: + case 0xb4: + case 0xb5: + case 0xb6: + case 0xb7: + case 0xb8: + case 0xb9: + case 0xba: + case 0xbb: + case 0xbc: + case 0xbd: + case 0xbe: + case 0xbf: + break; + + case 0xc0: + case 0xc1: + case 0xc2: + case 0xc3: + case 0xc4: + case 0xc5: + case 0xc6: + case 0xc7: + // CPL (src).b + m_op = CPL; + + m_param1_type = type | BITPOS; + m_param1 = val; + m_bitpos = bx & 0x7; + break; + + case 0xc8: + case 0xc9: + case 0xca: + case 0xcb: + case 0xcc: + case 0xcd: + case 0xce: + case 0xcf: + // LD (src).b,CF + m_op = LD; // Flags / Cycles 1--- / x + m_flagsaffected |= FLAG_J; + + m_param1_type = type | BITPOS; + m_param1 = val; + m_bitpos = bx & 0x7; + + m_param2_type = CARRYFLAG; + //m_param2 = 0; + break; + + + case 0xd0: + case 0xd1: + case 0xd2: + case 0xd3: + case 0xd4: + case 0xd5: + case 0xd6: + case 0xd7: + // XOR CF,(src).b + m_op = ALU_XOR; + m_param1_type = CARRYFLAG; + //m_param1 = 0; + + m_param2_type = type | BITPOS; + m_param2 = val; + m_bitpos = bx & 0x7; + break; + + case 0xd8: + case 0xd9: + case 0xda: + case 0xdb: + case 0xdc: + case 0xdd: + case 0xde: + case 0xdf: + // LD CF,(src).b aka TEST (src).b + m_op = LD; // Flags / Cycles %-*- / x + m_flagsaffected |= FLAG_J | FLAG_C; + + m_param2_type = type | BITPOS; + m_param2 = val; + m_bitpos = bx & 0x7; + + m_param1_type = CARRYFLAG; + //m_param1 = 0; + break; + + + case 0xe0: + case 0xe1: + case 0xe2: + case 0xe3: + case 0xe4: + case 0xe5: + case 0xe6: + case 0xe7: + case 0xe8: + case 0xe9: + case 0xea: + case 0xeb: + case 0xec: + case 0xed: + case 0xee: + case 0xef: + break; + + case 0xf0: + case 0xf1: + case 0xf2: + case 0xf3: + case 0xf4: + case 0xf5: + case 0xf6: + case 0xf7: + break; + + case 0xf8: + case 0xf9: + case 0xfa: + case 0xfb: + case 0xfc: + // CALL (src) + m_op = CALL; + m_param1_type = type; + m_param1 = val; + break; + + case 0xfd: + break; + + case 0xfe: + // JP (src) + m_op = JP; + m_param2_type = type | IS16BIT; + m_param2 = val; + break; + + case 0xff: + break; + } +} + +// f0 - f7 use this table +// note, same table is shown as above in manual, there's no overlap between src/dest, but they're not compatible +void tlcs870_disassembler::decode_dest(uint8_t b0) +{ + uint8_t bx; + + bx = READ8(); + + switch (bx) + { + case 0x10: + case 0x11: + case 0x12: + case 0x13: + // LD (dst),rr // (dst) can only be (x) (pp) or (HL+d) ? not (HL+) or (-HL) ? + m_op = LD; // Flags / Cycles 1--- / x + m_flagsaffected |= FLAG_J; + + m_param1_type |= IS16BIT; + + + m_param2_type = REG_16BIT; + m_param2 = bx&0x3; + break; + + case 0x2c: + // LD (dst),n // (dst) can only be (DE), (HL+), (-HL), or (HL+d) because (x) and (HL) are redundant encodings? + m_op = LD; // Flags / Cycles 1--- / x + m_flagsaffected |= FLAG_J; + + m_param2_type = ABSOLUTE_VAL_8; + m_param2 = READ8(); + break; + + case 0x50: + case 0x51: + case 0x52: + case 0x53: + case 0x54: + case 0x55: + case 0x56: + case 0x57: + // LD (dst),r + m_op = LD; // Flags / Cycles 1--- / x + m_flagsaffected |= FLAG_J; + + m_param2_type = REG_8BIT; + m_param2 = bx&0x7; + break; + + default: + break; + } +} + +void tlcs870_disassembler::disassemble_param(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms, int type, uint16_t val) +{ + int basetype = type & MODE_MASK; + + if (basetype==ADDR_IN_IMM_X) util::stream_format(stream, " ($%02x)", val); // direct + if (basetype==ADDR_IN_PC_PLUS_REG_A) util::stream_format(stream, " %s", type_x[1]); + if (basetype==ADDR_IN_DE) util::stream_format(stream, " %s", type_x[2]); + if (basetype==ADDR_IN_HL) util::stream_format(stream, " %s", type_x[3]); + if (basetype==ADDR_IN_HL_PLUS_IMM_D) util::stream_format(stream, " (HL+$%04x)", val); // todo, sign extend + if (basetype==ADDR_IN_HL_PLUS_REG_C) util::stream_format(stream, " %s", type_x[5]); + if (basetype==ADDR_IN_HLINC) util::stream_format(stream, " %s", type_x[6]); + if (basetype==ADDR_IN_DECHL) util::stream_format(stream, " %s", type_x[7]); + + if (basetype==REG_8BIT) + { + if (type&IS16BIT) util::stream_format(stream, " %s", reg16[val&3]); + else util::stream_format(stream, " %s", reg8[val & 7]); + } + + if (basetype==CONDITIONAL) util::stream_format(stream, " %s", conditions[val]); + if (basetype==(STACKPOINTER & MODE_MASK)) util::stream_format(stream, " SP"); + if (basetype==REGISTERBANK) util::stream_format(stream, " RBS"); + if (basetype==PROGRAMSTATUSWORD) util::stream_format(stream, " PSW"); + if (basetype==MEMVECTOR_16BIT) util::stream_format(stream, " ($%04x)", val); + if (basetype==ABSOLUTE_VAL_8) + { + if (type&IS16BIT) util::stream_format(stream, "$%04x", val); + else util::stream_format(stream, "$%02x", val); + } + + if (basetype == (CARRYFLAG & MODE_MASK)) + { + util::stream_format(stream, " CF"); + } + else if (type&BITPOS) + { + if (type & BITPOS_INDIRECT) util::stream_format(stream, ".BIT_%s", reg8[m_bitpos&7]); + else util::stream_format(stream, ".BIT_%d", m_bitpos); + } +} + +offs_t tlcs870_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + m_addr = pc; + + decode(); + + util::stream_format (stream, "%-5s", op_names[ m_op ] ); + + if (m_param1_type) + { + disassemble_param(stream, pc, opcodes, params, m_param1_type, m_param1); + } + + if (m_param2_type) + { + if (m_param1_type) util::stream_format(stream, ","); + + disassemble_param(stream, pc, opcodes, params, m_param2_type, m_param2); + + } + + return (m_addr - pc) | SUPPORTED; +} diff --git a/src/devices/cpu/tlcs870/tlcs870d.h b/src/devices/cpu/tlcs870/tlcs870d.h new file mode 100644 index 00000000000..a19a64e029b --- /dev/null +++ b/src/devices/cpu/tlcs870/tlcs870d.h @@ -0,0 +1,89 @@ +// license:BSD-3-Clause +// copyright-holders:David Haywood +/************************************************************************************************************* + + Toshiba TLCS-870 Series MCUs + + The TLCS-870/X expands on this instruction set using the same base encoding. + + The TLCS-870/C appears to have a completely different encoding. + + loosely baesd on the tlcs90 core by Luca Elia + +*************************************************************************************************************/ + +#ifndef MAME_CPU_TLCS870_TLCS870D_H +#define MAME_CPU_TLCS870_TLCS870D_H + +#pragma once + +class tlcs870_disassembler : public util::disasm_interface +{ +public: + tlcs870_disassembler() = default; + virtual ~tlcs870_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum _e_op { + UNKNOWN = 0x00, + CALL, CALLP, CALLV, CLR, CPL, + DAA, DAS, DEC, /*DI,*/ DIV, + /*EI,*/ + INC, + /*J,*/ JP, JR, JRS, + LD, LDW, + MCMP, MUL, + NOP, + POP, PUSH, + RET, RETI, RETN, ROLC, ROLD, RORC, RORD, + SET, SHLC, SHRC, SWAP, SWI, + /*TEST,*/ XCH, + + ALU_ADDC, + ALU_ADD, + ALU_SUBB, + ALU_SUB, + ALU_AND, + ALU_XOR, + ALU_OR, + ALU_CMP + }; + + static const char *const op_names[]; + static const char *const reg8[]; + static const char *const type_x[]; + static const char *const conditions[]; + static const char *const reg16[]; + static const char *const reg16p[]; + + uint16_t m_op; + int m_param2_type; + uint16_t m_param2; + + int m_param1_type; + uint16_t m_param1; + uint16_t m_temppc; // this is just PPC? use generic reg? + + uint8_t m_bitpos; + uint8_t m_flagsaffected; + uint8_t m_cycles; + + uint32_t m_addr; + + const data_buffer *m_opcodes; + + inline uint8_t READ8(); + inline uint16_t READ16(); + + void decode(); + void decode_register_prefix(uint8_t b0); + void decode_source(int type, uint16_t val); + void decode_dest(uint8_t b0); + + void disassemble_param(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms, int type, uint16_t val); +}; + +#endif diff --git a/src/devices/cpu/tlcs90/tlcs90.cpp b/src/devices/cpu/tlcs90/tlcs90.cpp index 7a99a60bbe4..593e454605f 100644 --- a/src/devices/cpu/tlcs90/tlcs90.cpp +++ b/src/devices/cpu/tlcs90/tlcs90.cpp @@ -15,8 +15,7 @@ #include "emu.h" #include "debugger.h" #include "tlcs90.h" - -static const char *const op_names[] = { "??", "nop", "ex", "exx", "ld", "ldw", "lda", "ldi", "ldir", "ldd", "lddr", "cpi", "cpir", "cpd", "cpdr", "push", "pop", "jp", "jr", "call", "callr", "ret", "reti", "halt", "di", "ei", "swi", "daa", "cpl", "neg", "ldar", "rcf", "scf", "ccf", "tset", "bit", "set", "res", "inc", "dec", "incx", "decx", "incw", "decw", "add", "adc", "sub", "sbc", "and", "xor", "or", "cp", "rlc", "rrc", "rl", "rr", "sla", "sra", "sll", "srl", "rld", "rrd", "djnz", "mul", "div" }; +#include "tlcs90d.h" ALLOW_SAVE_TYPE(tlcs90_device::e_mode); // allow save_item on a non-fundamental type @@ -154,9 +153,6 @@ enum { #define F m_af.b.l -static const char *const r8_names[] = { "b", "c", "d", "e", "h", "l", "a" }; -static const char *const r16_names[] = { "bc", "de", "hl", "??", "ix", "iy", "sp", "af", "af'", "pc" }; - // Condition Codes #define FLS 0x0 @@ -198,8 +194,6 @@ static uint8_t SZP[256]; /* zero, sign and parity flags */ static uint8_t SZHV_inc[256]; /* zero, sign, half carry and overflow flags INC r8 */ static uint8_t SZHV_dec[256]; /* zero, sign, half carry and overflow flags DEC r8 */ -static const char *const cc_names[] = { "f", "lt", "le", "ule", "ov", "mi", "z", "c", "", "ge", "gt", "ugt", "nov", "pl", "nz", "nc" }; - // Opcodes #define OP_16 0x80 @@ -1009,81 +1003,6 @@ void tlcs90_device::decode() OP( UNKNOWN,2 ) NONE( 1 ) NONE( 2 ) } -static const char *const ir_names[] = { - "P0", "P1", "P01CR/IRFL", "IRFH", "P2", "P2CR", "P3", "P3CR", - "P4", "P4CR", "P5", "SMMOD", "P6", "P7", "P67CR", "SMCR", - "P8", "P8CR", "WDMOD", "WDCR", "TREG0", "TREG1", "TREG2", "TREG3", - "TCLK", "TFFCR", "TMOD", "TRUN", "CAP1L", "CAP1H", "CAP2L", "CAL2H", - "TREG4L", "TREG4H", "TREG5L", "TREG5H", "T4MOD", "T4FFCR", "INTEL", "INTEH", - "DMAEH", "SCMOD", "SCCR", "SCBUF", "BX", "BY", "ADREG", "ADMOD" -}; - -const char *tlcs90_device::internal_registers_names(uint16_t x) -{ - if (type() != TMP90PH44) - { - // FIXME: TMP90PH44 and many other models have completely different SFR maps - int ir = x - 0xffc0; - if ( ir >= 0 && ir < ARRAY_LENGTH(ir_names) ) - return ir_names[ir]; - } - return nullptr; -} - -bool tlcs90_device::stream_arg(std::ostream &stream, uint32_t pc, const char *pre, const e_mode mode, const uint16_t r, const uint16_t rb) -{ - const char *reg_name; - switch ( mode ) - { - case e_mode::NONE: return false; - - case e_mode::BIT8: util::stream_format(stream, "%s%d", pre, r ); return true; - case e_mode::I8: util::stream_format(stream, "%s$%02X", pre, r ); return true; - case e_mode::D8: util::stream_format(stream, "%s$%04X", pre, (pc+2+(r&0x7f)-(r&0x80))&0xffff ); return true; - case e_mode::I16: util::stream_format(stream, "%s$%04X", pre, r ); return true; - case e_mode::D16: util::stream_format(stream, "%s$%04X", pre, (pc+2+(r&0x7fff)-(r&0x8000))&0xffff ); return true; - case e_mode::MI16: - reg_name = internal_registers_names(r); - if (reg_name) - util::stream_format(stream, "%s(%s)", pre, reg_name); - else - util::stream_format(stream, "%s($%04X)", pre, r ); - return true; - case e_mode::R8: util::stream_format(stream, "%s%s", pre, r8_names[r] ); return true; - case e_mode::R16: util::stream_format(stream, "%s%s", pre, r16_names[r] ); return true; - case e_mode::MR16: util::stream_format(stream, "%s(%s)", pre, r16_names[r] ); return true; - - case e_mode::MR16R8: util::stream_format(stream, "%s(%s+%s)", pre, r16_names[r], r8_names[rb] ); return true; - case e_mode::MR16D8: util::stream_format(stream, "%s(%s%c$%02X)", pre, r16_names[r], (rb&0x80)?'-':'+', (rb&0x80)?((rb^0xff)+1):rb ); return true; - - case e_mode::CC: util::stream_format(stream, "%s%s", pre, cc_names[r] ); return true; - - case e_mode::R16R8: util::stream_format(stream, "%s%s+%s", pre, r16_names[r], r8_names[rb] ); return true; - case e_mode::R16D8: util::stream_format(stream, "%s%s%c$%02X", pre, r16_names[r], (rb&0x80)?'-':'+', (rb&0x80)?((rb^0xff)+1):rb ); return true; - - default: - fatalerror("%04x: unimplemented addr mode = %d\n",pc,std::underlying_type_t(mode)); - } - - // never executed - return false; -} - -offs_t tlcs90_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) -{ - m_addr = pc; - - decode(); - m_op &= ~OP_16; - - util::stream_format (stream, "%-5s", op_names[ m_op ] ); // strlen("callr") == 5 - bool streamed = stream_arg (stream, pc, " ", m_mode1, m_r1, m_r1b ); - stream_arg (stream, pc, streamed ?",":"", m_mode2, m_r2, m_r2b ); - - return (m_addr - pc) | DASMFLAG_SUPPORTED; -} - - uint16_t tlcs90_device::r8( const uint16_t r ) { switch( r ) @@ -2938,3 +2857,8 @@ void tlcs90_device::state_string_export(const device_state_entry &entry, std::st break; } } + +util::disasm_interface *tlcs90_device::create_disassembler() +{ + return new tlcs90_disassembler; +} diff --git a/src/devices/cpu/tlcs90/tlcs90.h b/src/devices/cpu/tlcs90/tlcs90.h index abde3d87b6a..589eae3025c 100644 --- a/src/devices/cpu/tlcs90/tlcs90.h +++ b/src/devices/cpu/tlcs90/tlcs90.h @@ -119,9 +119,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 6; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: enum class e_mode : u8 { @@ -190,8 +188,6 @@ private: inline uint8_t READ8(); inline uint16_t READ16(); void decode(); - const char *internal_registers_names(uint16_t x); - bool stream_arg(std::ostream &stream, uint32_t pc, const char *pre, const e_mode mode, const uint16_t r, const uint16_t rb); inline uint16_t r8( const uint16_t r ); inline void w8( const uint16_t r, uint16_t value ); inline uint16_t r16( const uint16_t r ); diff --git a/src/devices/cpu/tlcs90/tlcs90d.cpp b/src/devices/cpu/tlcs90/tlcs90d.cpp new file mode 100644 index 00000000000..66787e84528 --- /dev/null +++ b/src/devices/cpu/tlcs90/tlcs90d.cpp @@ -0,0 +1,952 @@ +// license:BSD-3-Clause +// copyright-holders:Luca Elia +/************************************************************************************************************* + + Toshiba TLCS-90 Series MCU's + + emulation by Luca Elia, based on the Z80 core by Juergen Buchmueller + + ChangeLog: + + 20150517 Fixed TRUN bit masking (timers start/stop handling) [Rainer Keuchel] + +*************************************************************************************************************/ + +#include "emu.h" +#include "tlcs90d.h" + +const char *const tlcs90_disassembler::op_names[] = { "??", "nop", "ex", "exx", "ld", "ldw", "lda", "ldi", "ldir", "ldd", "lddr", "cpi", "cpir", "cpd", "cpdr", "push", "pop", "jp", "jr", "call", "callr", "ret", "reti", "halt", "di", "ei", "swi", "daa", "cpl", "neg", "ldar", "rcf", "scf", "ccf", "tset", "bit", "set", "res", "inc", "dec", "incx", "decx", "incw", "decw", "add", "adc", "sub", "sbc", "and", "xor", "or", "cp", "rlc", "rrc", "rl", "rr", "sla", "sra", "sll", "srl", "rld", "rrd", "djnz", "mul", "div" }; + +const char *const tlcs90_disassembler::r8_names[] = { "b", "c", "d", "e", "h", "l", "a" }; +const char *const tlcs90_disassembler::r16_names[] = { "bc", "de", "hl", "??", "ix", "iy", "sp", "af", "af'", "pc" }; + +const char *const tlcs90_disassembler::cc_names[] = { "f", "lt", "le", "ule", "ov", "mi", "z", "c", "", "ge", "gt", "ugt", "nov", "pl", "nz", "nc" }; + +u32 tlcs90_disassembler::opcode_alignment() const +{ + return 1; +} + +const char *const tlcs90_disassembler::ir_names[] = { + "P0", "P1", "P01CR/IRFL", "IRFH", "P2", "P2CR", "P3", "P3CR", + "P4", "P4CR", "P5", "SMMOD", "P6", "P7", "P67CR", "SMCR", + "P8", "P8CR", "WDMOD", "WDCR", "TREG0", "TREG1", "TREG2", "TREG3", + "TCLK", "TFFCR", "TMOD", "TRUN", "CAP1L", "CAP1H", "CAP2L", "CAL2H", + "TREG4L", "TREG4H", "TREG5L", "TREG5H", "T4MOD", "T4FFCR", "INTEL", "INTEH", + "DMAEH", "SCMOD", "SCCR", "SCBUF", "BX", "BY", "ADREG", "ADMOD" +}; + +#define T90_IOBASE 0xffc0 + +const char *tlcs90_disassembler::internal_registers_names(uint16_t x) +{ + // FIXME: TMP90PH44 and many other models have completely different SFR maps + int ir = x - T90_IOBASE; + if ( ir >= 0 && ir < ARRAY_LENGTH(ir_names) ) + return ir_names[ir]; + return nullptr; +} + +#define B 0 +#define C 1 +#define D 2 +#define E 3 +#define H 4 +#define L 5 +#define A 6 + +#define BC 0 +#define DE 1 +#define HL 2 +// 3 +#define IX 4 +#define IY 5 +#define SP 6 + +#define AF 7 +#define AF2 8 +#define PC 9 + +#define FLS 0x0 +#define LT 0x1 +#define LE 0x2 +#define ULE 0x3 +#define OV 0x4 +#define PE 0x4 +#define MI 0x5 +#define Z 0x6 +#define EQ 0x6 +#define CR 0x7 +#define ULT 0x7 +#define T 0x8 +#define GE 0x9 +#define GT 0xa +#define UGT 0xb +#define NOV 0xc +#define PO 0xc +#define PL 0xd +#define NZ 0xe +#define NE 0xe +#define NC 0xf +#define UGE 0xf + +#define CF 0x01 +#define NF 0x02 +#define PF 0x04 +#define VF PF +#define XCF 0x08 +#define HF 0x10 +#define IF 0x20 +#define ZF 0x40 +#define SF 0x80 + +#define OP( X,CT ) m_op = X; +#define OP16( X,CT ) m_op = X; + +#define OPCC( X,CF,CT ) m_op = X; +#define OPCC16( X,CF,CT ) m_op = X; + +#define BIT8( N,I ) m_mode##N = e_mode::BIT8; m_r##N = I; +#define I8( N,I ) m_mode##N = e_mode::I8; m_r##N = I; +#define D8( N,I ) m_mode##N = e_mode::D8; m_r##N = I; +#define I16( N,I ) m_mode##N = e_mode::I16; m_r##N = I; +#define D16( N,I ) m_mode##N = e_mode::D16; m_r##N = I; +#define R8( N,R ) m_mode##N = e_mode::R8; m_r##N = R; +#define R16( N,R ) m_mode##N = e_mode::R16; m_r##N = R; +#define Q16( N,R ) m_mode##N = e_mode::R16; m_r##N = R; if (m_r##N == SP) m_r##N = AF; +#define MI16( N,I ) m_mode##N = e_mode::MI16; m_r##N = I; +#define MR16( N,R ) m_mode##N = e_mode::MR16; m_r##N = R; +#define MR16D8( N,R,I ) m_mode##N = e_mode::MR16D8; m_r##N = R; m_r##N##b = I; +#define MR16R8( N,R,g ) m_mode##N = e_mode::MR16R8; m_r##N = R; m_r##N##b = g; +#define NONE( N ) m_mode##N = e_mode::NONE; +#define CC( N,cc ) m_mode##N = e_mode::CC; m_r##N = cc; +#define R16D8( N,R,I ) m_mode##N = e_mode::R16D8; m_r##N = R; m_r##N##b = I; +#define R16R8( N,R,g ) m_mode##N = e_mode::R16R8; m_r##N = R; m_r##N##b = g; + +uint8_t tlcs90_disassembler::READ8() +{ + uint8_t b0 = m_opcodes->r8( m_addr++ ); + m_addr &= 0xffff; + return b0; +} +uint16_t tlcs90_disassembler::READ16() +{ + uint8_t b0 = READ8(); + return b0 | (READ8() << 8); +} + +void tlcs90_disassembler::decode() +{ + uint8_t b0, b1, b2, b3; + uint16_t imm16; + + b0 = READ8(); + + switch ( b0 ) + { + case 0x00: + OP( NOP,2 ) NONE( 1 ) NONE( 2 ) return; // NOP + + case 0x01: + OP( HALT,4 ) NONE( 1 ) NONE( 2 ) return; // HALT + case 0x02: + OP( DI,2 ) NONE( 1 ) NONE( 2 ) return; // DI + case 0x03: + OP( EI,2 ) NONE( 1 ) NONE( 2 ) return; // EI + + case 0x07: + OPCC( INCX,6,10 ) MI16( 1, 0xFF00|READ8() ) NONE( 2 ) return; // INCX ($FF00+n) + + case 0x08: + OP( EX,2 ) R16( 1, DE ) R16( 2, HL ) return; // EX DE,HL + case 0x09: + OP( EX,2 ) R16( 1, AF ) R16( 2, AF2 ) return; // EX AF,AF' + case 0x0a: + OP( EXX,2 ) NONE( 1 ) NONE( 2 ) return; // EXX + + case 0x0b: + OP( DAA,4 ) R8( 1, A ) NONE( 2 ) return; // DAA A + + case 0x0c: + OP( RCF,2 ) NONE( 1 ) NONE( 2 ) return; // RCF + case 0x0d: + OP( SCF,2 ) NONE( 1 ) NONE( 2 ) return; // SCF + case 0x0e: + OP( CCF,2 ) NONE( 1 ) NONE( 2 ) return; // CCF + + case 0x0f: + OPCC( DECX,6,10 ) MI16( 1, 0xFF00|READ8() ) NONE( 2 ) return; // DECX ($FF00+n) + + case 0x10: + OP( CPL,2 ) R8( 1, A ) NONE( 2 ) return; // CPL A + case 0x11: + OP( NEG,2 ) R8( 1, A ) NONE( 2 ) return; // NEG A + + case 0x12: // MUL HL,n + case 0x13: // DIV HL,n + OP( MUL+b0-0x12,16) R16( 1, HL ) I8( 2, READ8() ) return; + + case 0x14: case 0x15: case 0x16: + OP16( ADD,6 ) R16( 1, IX+b0-0x14 ) I16( 2, READ16() ) return; // ADD ix,mn + + case 0x17: + OP( LDAR,8 ) R16( 1, HL ) D16( 2, READ16() ) return; // LDAR HL,+cd + + case 0x18: + OP( DJNZ,10 ) D8( 1, READ8() ) NONE( 2 ) return; // DJNZ +d + case 0x19: + OP16( DJNZ,10 ) R16( 1, BC ) D8( 2, READ8() ) return; // DJNZ BC,+d + + case 0x1a: + OPCC( JP,8,8 ) CC( 1, T ) I16( 2, READ16() ) return; // JP T,mn + case 0x1b: + OPCC16( JR,10,10 ) CC( 1, T ) D16( 2, READ16() ) return; // JR T,+cd + + case 0x1c: + OPCC( CALL,14,14 ) CC( 1, T ) I16( 2, READ16() ) return; // CALL T,mn + case 0x1d: + OP( CALLR,16 ) D16( 1, READ16() ) NONE( 2 ) return; // CALLR +cd + + case 0x1e: + OPCC( RET,10,10 ) CC( 1, T ) NONE( 2 ) return; // RET T + case 0x1f: + OP( RETI,14 ) NONE( 1 ) NONE( 2 ) return; // RETI + + case 0x20: case 0x21: case 0x22: case 0x23: case 0x24: case 0x25: case 0x26: + OP( LD,2 ) R8( 1, A ) R8( 2, b0 - 0x20 ) return; // LD A,r + + case 0x27: + OP( LD,8 ) R8( 1, A ) MI16( 2, 0xFF00|READ8() ) return; // LD A,($FF00+n) + + case 0x28: case 0x29: case 0x2a: case 0x2b: case 0x2c: case 0x2d: case 0x2e: + OP( LD,2 ) R8( 1, b0 - 0x28 ) R8( 2, A ) return; // LD r,A + + case 0x2f: + OP( LD,8 ) MI16( 1, 0xFF00|READ8() ) R8( 2, A ) return; // LD ($FF00+n), A + + case 0x30: case 0x31: case 0x32: case 0x33: case 0x34: case 0x35: case 0x36: + OP( LD,4 ) R8( 1, b0 - 0x30 ) I8( 2, READ8() ) return; // LD r,n + + case 0x37: + OP( LD,10 ) MI16( 1, 0xFF00|READ8() ) I8( 2, READ8() ) return; // LD ($FF00+w),n + + case 0x38: case 0x39: case 0x3a: /*case 0x3b:*/ case 0x3c: case 0x3d: case 0x3e: + OP16( LD,6 ) R16( 1, b0 - 0x38 ) I16( 2, READ16() ) return; // LD rr,nn + + case 0x3f: + OP( LDW,14 ) MI16( 1, 0xFF00|READ8() ) I16( 2, READ16() ) return; // LDW ($FF00+w),mn + + case 0x40: case 0x41: case 0x42: /*case 0x43:*/ case 0x44: case 0x45: case 0x46: + OP16( LD,4 ) R16( 1, HL ) R16( 2, b0 - 0x40 ) return; // LD HL,rr + + case 0x47: + OP16( LD,10 ) R16( 1, HL ) MI16( 2, 0xFF00|READ8() ) return; // LD HL,($FF00+n) + + case 0x48: case 0x49: case 0x4a: /*case 0x4b:*/ case 0x4c: case 0x4d: case 0x4e: + OP16( LD,4 ) R16( 1, b0 - 0x48 ) R16( 2, HL ) return; // LD rr,HL + + case 0x4f: + OP16( LD,10 ) MI16( 1, 0xFF00|READ8() ) R16( 2, HL ) return; // LD ($FF00+n), HL + + case 0x50: case 0x51: case 0x52: /*case 0x53:*/ case 0x54: case 0x55: case 0x56: + OP( PUSH,8 ) Q16( 1, b0 - 0x50 ) NONE( 2 ) return; // PUSH qq + case 0x58: case 0x59: case 0x5a: /*case 0x5b:*/ case 0x5c: case 0x5d: case 0x5e: + OP( POP,10 ) Q16( 1, b0 - 0x58 ) NONE( 2 ) return; // POP qq + + case 0x60: // ADD A,($FF00+n) + case 0x61: // ADC A,($FF00+n) + case 0x62: // SUB A,($FF00+n) + case 0x63: // SBC A,($FF00+n) + case 0x64: // AND A,($FF00+n) + case 0x65: // XOR A,($FF00+n) + case 0x66: // OR A,($FF00+n) + case 0x67: // CP A,($FF00+n) + OP( ADD+b0-0x60,8 ) R8( 1, A ) MI16( 2, 0xFF00|READ8() ) return; + + case 0x68: // ADD A,n + case 0x69: // ADC A,n + case 0x6a: // SUB A,n + case 0x6b: // SBC A,n + case 0x6c: // AND A,n + case 0x6d: // XOR A,n + case 0x6e: // OR A,n + case 0x6f: // CP A,n + OP( ADD+b0-0x68,4 ) R8( 1, A ) I8( 2, READ8() ) return; + + case 0x70: // ADD HL,($FF00+n) + case 0x71: // ADC HL,($FF00+n) + case 0x72: // SUB HL,($FF00+n) + case 0x73: // SBC HL,($FF00+n) + case 0x74: // AND HL,($FF00+n) + case 0x75: // XOR HL,($FF00+n) + case 0x76: // OR HL,($FF00+n) + case 0x77: // CP HL,($FF00+n) + OP16( ADD+b0-0x70,10 ) R16( 1, HL ) MI16( 2, 0xFF00|READ8() ) return; + + case 0x78: // ADD HL,mn + case 0x79: // ADC HL,mn + case 0x7a: // SUB HL,mn + case 0x7b: // SBC HL,mn + case 0x7c: // AND HL,mn + case 0x7d: // XOR HL,mn + case 0x7e: // OR HL,mn + case 0x7f: // CP HL,mn + OP16( ADD+b0-0x78,6 ) R16( 1, HL ) I16( 2, READ16() ) return; + + case 0x80: case 0x81: case 0x82: case 0x83: case 0x84: case 0x85: case 0x86: + OP( INC,2 ) R8( 1, b0 - 0x80 ) NONE( 2 ) return; // INC r + case 0x87: + OP( INC,10 ) MI16( 1, 0xFF00|READ8() ) NONE( 2 ) return; // INC ($FF00+n) + + case 0x88: case 0x89: case 0x8a: case 0x8b: case 0x8c: case 0x8d: case 0x8e: + OP( DEC,2 ) R8( 1, b0 - 0x88 ) NONE( 2 ) return; // DEC r + case 0x8f: + OP( DEC,10 ) MI16( 1, 0xFF00|READ8() ) NONE( 2 ) return; // DEC ($FF00+n) + + case 0x90: case 0x91: case 0x92: /*case 0x93:*/ case 0x94: case 0x95: case 0x96: + OP16( INC,4 ) R16( 1, b0 - 0x90 ) NONE( 2 ) return; // INC rr + case 0x97: + OP( INCW,14 ) MI16( 1, 0xFF00|READ8() ) NONE( 2 ) return; // INCW ($FF00+n) + case 0x98: case 0x99: case 0x9a: /*case 0x9b:*/ case 0x9c: case 0x9d: case 0x9e: + OP16( DEC,4 ) R16( 1, b0 - 0x98 ) NONE( 2 ) return; // DEC rr + case 0x9f: + OP( DECW,14 ) MI16( 1, 0xFF00|READ8() ) NONE( 2 ) return; // DECW ($FF00+n) + + case 0xa0: // RLC A + case 0xa1: // RRC A + case 0xa2: // RL A + case 0xa3: // RR A + case 0xa4: // SLA A + case 0xa5: // SRA A + case 0xa6: // SLL A + case 0xa7: // SRL A + OP( RLC+b0-0xa0,2 ) R8( 1, A ) NONE( 2 ) return; + + case 0xa8: case 0xa9: case 0xaa: case 0xab: case 0xac: case 0xad: case 0xae: case 0xaf: + OP( BIT,8 ) BIT8( 1, b0 - 0xa8 ) MI16( 2, 0xFF00|READ8() ) return; // BIT b,($FF00+n) + case 0xb0: case 0xb1: case 0xb2: case 0xb3: case 0xb4: case 0xb5: case 0xb6: case 0xb7: + OP( RES,12 ) BIT8( 1, b0 - 0xb0 ) MI16( 2, 0xFF00|READ8() ) return; // RES b,($FF00+n) + case 0xb8: case 0xb9: case 0xba: case 0xbb: case 0xbc: case 0xbd: case 0xbe: case 0xbf: + OP( SET,12 ) BIT8( 1, b0 - 0xb8 ) MI16( 2, 0xFF00|READ8() ) return; // SET b,($FF00+n) + + case 0xc0: case 0xc1: case 0xc2: case 0xc3: case 0xc4: case 0xc5: case 0xc6: case 0xc7: + case 0xc8: case 0xc9: case 0xca: case 0xcb: case 0xcc: case 0xcd: case 0xce: case 0xcf: + OPCC( JR,4,8 ) CC( 1, b0 - 0xc0 ) D8( 2, READ8() ) return; // JR cc,+d + + case 0xe0: case 0xe1: case 0xe2: /*case 0xe3:*/ case 0xe4: case 0xe5: case 0xe6: + b1 = READ8(); + switch ( b1 ) { + case 0x10: // RLD (gg) + case 0x11: // RRD (gg) + OP( RLD+b1-0x10,12 ) MR16( 1, b0 - 0xe0 ) NONE( 2 ) return; + + case 0x12: // MUL HL,(gg) + case 0x13: // DIV HL,(gg) + OP( MUL+b1-0x12,18 ) R16( 1, HL ) MR16( 2, b0 - 0xe0 ) return; + + case 0x14: case 0x15: case 0x16: + OP16( ADD,8 ) R16( 1, IX+b1-0x14 ) MR16( 2, b0 - 0xe0 ) return; // ADD ix,(gg) + + case 0x28: case 0x29: case 0x2a: case 0x2b: case 0x2c: case 0x2d: case 0x2e: + OP( LD,6 ) R8( 1, b1 - 0x28 ) MR16( 2, b0 - 0xe0 ) return; // LD r,(gg) + case 0x48: case 0x49: case 0x4a: /*case 0x4b:*/ case 0x4c: case 0x4d: case 0x4e: + OP16( LD,8 ) R16( 1, b1 - 0x48 ) MR16( 2, b0 - 0xe0 ) return; // LD rr,(gg) + + case 0x50: case 0x51: case 0x52: /*case 0x53:*/ case 0x54: case 0x55: case 0x56: + OP( EX,14 ) MR16( 1, b0 - 0xe0 ) R16( 2, b1 - 0x50 ) return; // EX (gg),rr + + case 0x60: // ADD A,(gg) + case 0x61: // ADC A,(gg) + case 0x62: // SUB A,(gg) + case 0x63: // SBC A,(gg) + case 0x64: // AND A,(gg) + case 0x65: // XOR A,(gg) + case 0x66: // OR A,(gg) + case 0x67: // CP A,(gg) + OP( ADD+b1-0x60,6 ) R8( 1, A ) MR16( 2, b0 - 0xe0 ) return; + + case 0x70: // ADD HL,(gg) + case 0x71: // ADC HL,(gg) + case 0x72: // SUB HL,(gg) + case 0x73: // SBC HL,(gg) + case 0x74: // AND HL,(gg) + case 0x75: // XOR HL,(gg) + case 0x76: // OR HL,(gg) + case 0x77: // CP HL,(gg) + OP16( ADD+b1-0x70,8 ) R16( 1, HL ) MR16( 2, b0 - 0xe0 ) return; + + case 0x87: + OP( INC,8 ) MR16( 1, b0 - 0xe0 ) NONE( 2 ) return; // INC (gg) + case 0x8f: + OP( DEC,8 ) MR16( 1, b0 - 0xe0 ) NONE( 2 ) return; // DEC (gg) + + case 0x97: + OP( INCW,12 ) MR16( 1, b0 - 0xe0 ) NONE( 2 ) return; // INCW (gg) + case 0x9f: + OP( DECW,12 ) MR16( 1, b0 - 0xe0 ) NONE( 2 ) return; // DECW (gg) + + case 0xa0: // RLC (gg) + case 0xa1: // RRC (gg) + case 0xa2: // RL (gg) + case 0xa3: // RR (gg) + case 0xa4: // SLA (gg) + case 0xa5: // SRA (gg) + case 0xa6: // SLL (gg) + case 0xa7: // SRL (gg) + OP( RLC+b1-0xa0,8 ) MR16( 1, b0 - 0xe0 ) NONE( 2 ) return; + + case 0x18: case 0x19: case 0x1a: case 0x1b: case 0x1c: case 0x1d: case 0x1e: case 0x1f: + OP( TSET,12 ) BIT8( 1, b1 - 0x18 ) MR16( 2, b0 - 0xe0 ) return; // TSET b,(gg) + case 0xa8: case 0xa9: case 0xaa: case 0xab: case 0xac: case 0xad: case 0xae: case 0xaf: + OP( BIT,6 ) BIT8( 1, b1 - 0xa8 ) MR16( 2, b0 - 0xe0 ) return; // BIT b,(gg) + case 0xb0: case 0xb1: case 0xb2: case 0xb3: case 0xb4: case 0xb5: case 0xb6: case 0xb7: + OP( RES,10 ) BIT8( 1, b1 - 0xb0 ) MR16( 2, b0 - 0xe0 ) return; // RES b,(gg) + case 0xb8: case 0xb9: case 0xba: case 0xbb: case 0xbc: case 0xbd: case 0xbe: case 0xbf: + OP( SET,10 ) BIT8( 1, b1 - 0xb8 ) MR16( 2, b0 - 0xe0 ) return; // SET b,(gg) + } break; + case 0xe3: + imm16 = READ16(); + b3 = READ8(); + switch ( b3 ) { + case 0x10: // RLD (mn) + case 0x11: // RRD (mn) + OP( RLD+b3-0x10,16 ) MI16( 1, imm16 ) NONE( 2 ) return; + + case 0x12: // MUL HL,(mn) + case 0x13: // DIV HL,(mn) + OP( MUL+b3-0x12,22 ) R16( 1, HL ) MI16( 2, imm16 ) return; + + case 0x14: case 0x15: case 0x16: + OP16( ADD,12 ) R16( 1, IX+b3-0x14 ) MI16( 2, imm16 ) return; // ADD ix,(mn) + + case 0x28: case 0x29: case 0x2a: case 0x2b: case 0x2c: case 0x2d: case 0x2e: + OP( LD,10 ) R8( 1, b3 - 0x28 ) MI16( 2, imm16 ) return; // LD r,(mn) + case 0x48: case 0x49: case 0x4a: /*case 0x4b:*/ case 0x4c: case 0x4d: case 0x4e: + OP16( LD,12 ) R16( 1, b3 - 0x48 ) MI16( 2, imm16 ) return; // LD rr,(mn) + + case 0x50: case 0x51: case 0x52: /*case 0x53:*/ case 0x54: case 0x55: case 0x56: + OP( EX,18 ) MI16( 1, imm16 ) R16( 2, b3 - 0x50 ) return; // EX (mn),rr + + case 0x60: // ADD A,(mn) + case 0x61: // ADC A,(mn) + case 0x62: // SUB A,(mn) + case 0x63: // SBC A,(mn) + case 0x64: // AND A,(mn) + case 0x65: // XOR A,(mn) + case 0x66: // OR A,(mn) + case 0x67: // CP A,(mn) + OP( ADD+b3-0x60,10 ) R8( 1, A ) MI16( 2, imm16 ) return; + + case 0x70: // ADD HL,(mn) + case 0x71: // ADC HL,(mn) + case 0x72: // SUB HL,(mn) + case 0x73: // SBC HL,(mn) + case 0x74: // AND HL,(mn) + case 0x75: // XOR HL,(mn) + case 0x76: // OR HL,(mn) + case 0x77: // CP HL,(mn) + OP16( ADD+b3-0x70,12 ) R16( 1, HL ) MI16( 2, imm16 ) return; + + case 0x87: + OP( INC,12 ) MI16( 1, imm16 ) NONE( 2 ) return; // INC (mn) + case 0x8f: + OP( DEC,12 ) MI16( 1, imm16 ) NONE( 2 ) return; // DEC (mn) + + case 0x97: + OP( INCW,16 ) MI16( 1, imm16 ) NONE( 2 ) return; // INCW (mn) + case 0x9f: + OP( DECW,16 ) MI16( 1, imm16 ) NONE( 2 ) return; // DECW (mn) + + case 0xa0: // RLC (mn) + case 0xa1: // RRC (mn) + case 0xa2: // RL (mn) + case 0xa3: // RR (mn) + case 0xa4: // SLA (mn) + case 0xa5: // SRA (mn) + case 0xa6: // SLL (mn) + case 0xa7: // SRL (mn) + OP( RLC+b3-0xa0,12 ) MI16( 1, imm16 ) NONE( 2 ) return; + + case 0x18: case 0x19: case 0x1a: case 0x1b: case 0x1c: case 0x1d: case 0x1e: case 0x1f: + OP( TSET,16 ) BIT8( 1, b3 - 0x18 ) MI16( 2, imm16 ) return; // TSET b,(mn) + case 0xa8: case 0xa9: case 0xaa: case 0xab: case 0xac: case 0xad: case 0xae: case 0xaf: + OP( BIT,10 ) BIT8( 1, b3 - 0xa8 ) MI16( 2, imm16 ) return; // BIT b,(mn) + case 0xb0: case 0xb1: case 0xb2: case 0xb3: case 0xb4: case 0xb5: case 0xb6: case 0xb7: + OP( RES,14 ) BIT8( 1, b3 - 0xb0 ) MI16( 2, imm16 ) return; // RES b,(mn) + case 0xb8: case 0xb9: case 0xba: case 0xbb: case 0xbc: case 0xbd: case 0xbe: case 0xbf: + OP( SET,14 ) BIT8( 1, b3 - 0xb8 ) MI16( 2, imm16 ) return; // SET b,(mn) + } break; + + case 0xe7: + b1 = READ8(); + b2 = READ8(); + switch ( b2 ) { + case 0x10: // RLD ($FF00+n) + case 0x11: // RRD ($FF00+n) + OP( RLD+b2-0x10,14 ) MI16( 1, 0xFF00|b1 ) NONE( 2 ) return; + + case 0x12: // MUL HL,($FF00+n) + case 0x13: // DIV HL,($FF00+n) + OP( MUL+b2-0x12,20 ) R16( 1, HL ) MI16( 2, 0xFF00|b1 ) return; + + case 0x14: case 0x15: case 0x16: + OP16( ADD,10 ) R16( 1, IX+b2-0x14 ) MI16( 2, 0xFF00|b1 ) return; // ADD ix,($FF00+n) + + case 0x18: case 0x19: case 0x1a: case 0x1b: case 0x1c: case 0x1d: case 0x1e: case 0x1f: + OP( TSET,14 ) BIT8( 1, b2 - 0x18 ) MI16( 2, 0xFF00|b1 ) return; // TSET b,($FF00+n) + case 0x28: case 0x29: case 0x2a: case 0x2b: case 0x2c: case 0x2d: case 0x2e: + OP( LD,8 ) R8( 1, b2 - 0x28 ) MI16( 2, 0xFF00|b1 ) return; // LD r,($FF00+n) + case 0x48: case 0x49: case 0x4a: /*case 0x4b:*/ case 0x4c: case 0x4d: case 0x4e: + OP16( LD,10 ) R16( 1, b2 - 0x48 ) MI16( 2, 0xFF00|b1 ) return; // LD rr,($FF00+n) + + case 0x50: case 0x51: case 0x52: /*case 0x53:*/ case 0x54: case 0x55: case 0x56: + OP( EX,16 ) MI16( 1, 0xFF00|b1 ) R16( 2, b2 - 0x50 ) return; // EX ($FF00+n),rr + + case 0xa0: // RLC ($FF00+n) + case 0xa1: // RRC ($FF00+n) + case 0xa2: // RL ($FF00+n) + case 0xa3: // RR ($FF00+n) + case 0xa4: // SLA ($FF00+n) + case 0xa5: // SRA ($FF00+n) + case 0xa6: // SLL ($FF00+n) + case 0xa7: // SRL ($FF00+n) + OP( RLC+b2-0xa0,10 ) MI16( 1, 0xFF00|b1 ) NONE( 2 ) return; + } break; + + case 0xe8: case 0xe9: case 0xea: /*case 0xeb:*/ case 0xec: case 0xed: case 0xee: + b1 = READ8(); + switch ( b1 ) { + case 0x20: case 0x21: case 0x22: case 0x23: case 0x24: case 0x25: case 0x26: + OP( LD,6 ) MR16( 1, b0 - 0xe8 ) R8( 2, b1 - 0x20 ) return; // LD (gg),r + case 0x37: + OP( LD,8 ) MR16( 1, b0 - 0xe8 ) I8( 2, READ8() ) return; // LD (gg),n + case 0x3f: + OP( LDW,12 ) MR16( 1, b0 - 0xe8 ) I16( 2, READ16() ) return; // LDW (gg),mn + case 0x40: case 0x41: case 0x42: /*case 0x43:*/ case 0x44: case 0x45: case 0x46: + OP16( LD,8 ) MR16( 1, b0 - 0xe8 ) R16( 2, b1 - 0x40 ) return; // LD (gg),rr + + case 0x68: // ADD (gg),n + case 0x69: // ADC (gg),n + case 0x6a: // SUB (gg),n + case 0x6b: // SBC (gg),n + case 0x6c: // AND (gg),n + case 0x6d: // XOR (gg),n + case 0x6e: // OR (gg),n + OP( ADD+b1-0x68,10 ) MR16( 1, b0 - 0xe8 ) I8( 2, READ8() ) return; + case 0x6f: // CP (gg),n + OP( CP,8 ) MR16( 1, b0 - 0xe8 ) I8( 2, READ8() ) return; + + case 0xc0: case 0xc1: case 0xc2: case 0xc3: case 0xc4: case 0xc5: case 0xc6: case 0xc7: + case 0xc8: case 0xc9: case 0xca: case 0xcb: case 0xcc: case 0xcd: case 0xce: case 0xcf: + OPCC( JP,6,8 ) CC( 1, b1 - 0xc0 ) R16( 2, b0 - 0xe8 ) return; // JP [cc,]gg + case 0xd0: case 0xd1: case 0xd2: case 0xd3: case 0xd4: case 0xd5: case 0xd6: case 0xd7: + case 0xd8: case 0xd9: case 0xda: case 0xdb: case 0xdc: case 0xdd: case 0xde: case 0xdf: + OPCC( CALL,6,14 ) CC( 1, b1 - 0xd0 ) R16( 2, b0 - 0xe8 ) return; // CALL [cc,]gg + } break; + case 0xeb: + imm16 = READ16(); + b3 = READ8(); + switch ( b3 ) { + case 0x20: case 0x21: case 0x22: case 0x23: case 0x24: case 0x25: case 0x26: + OP( LD,10 ) MI16( 1, imm16 ) R8( 2, b3 - 0x20 ) return; // LD (mn),r + case 0x37: + OP( LD,12 ) MI16( 1, imm16 ) I8( 2, READ8() ) return; // LD (vw),n + case 0x3f: + OP( LDW,16 ) MI16( 1, imm16 ) I16( 2, READ16() ) return; // LDW (vw),mn + case 0x40: case 0x41: case 0x42: /*case 0x43:*/ case 0x44: case 0x45: case 0x46: + OP16( LD,12 ) MI16( 1, imm16 ) R16( 2, b3 - 0x40 ) return; // LD (mn),rr + + case 0x68: // ADD (vw),n + case 0x69: // ADC (vw),n + case 0x6a: // SUB (vw),n + case 0x6b: // SBC (vw),n + case 0x6c: // AND (vw),n + case 0x6d: // XOR (vw),n + case 0x6e: // OR (vw),n + OP( ADD+b3-0x68,14 ) MI16( 1, imm16 ) I8( 2, READ8() ) return; + case 0x6f: // CP (vw),n + OP( ADD+b3-0x68,12 ) MI16( 1, imm16 ) I8( 2, READ8() ) return; + + case 0xc0: case 0xc1: case 0xc2: case 0xc3: case 0xc4: case 0xc5: case 0xc6: case 0xc7: + case 0xc8: case 0xc9: case 0xca: case 0xcb: case 0xcc: case 0xcd: case 0xce: case 0xcf: + OPCC( JP,10,12 ) CC( 1, b3 - 0xc0 ) I16( 2, imm16 ) return; // JP cc,mn + case 0xd0: case 0xd1: case 0xd2: case 0xd3: case 0xd4: case 0xd5: case 0xd6: case 0xd7: + case 0xd8: case 0xd9: case 0xda: case 0xdb: case 0xdc: case 0xdd: case 0xde: case 0xdf: + OPCC( CALL,10,18 ) CC( 1, b3 - 0xd0 ) I16( 2, imm16 ) return; // CALL cc,mn + } break; + + case 0xef: + b1 = READ8(); + b2 = READ8(); + switch ( b2 ) { + case 0x20: case 0x21: case 0x22: case 0x23: case 0x24: case 0x25: case 0x26: + OP( LD,8 ) MI16( 1, 0xFF00|b1 ) R8( 2, b2 - 0x20 ) return; // LD ($FF00+n),r + case 0x40: case 0x41: case 0x42: /*case 0x43:*/ case 0x44: case 0x45: case 0x46: + OP16( LD,10 ) MI16( 1, 0xFF00|b1 ) R16( 2, b2 - 0x40 ) return; // LD ($FF00+n),rr + + case 0x68: // ADD ($FF00+w),n + case 0x69: // ADC ($FF00+w),n + case 0x6a: // SUB ($FF00+w),n + case 0x6b: // SBC ($FF00+w),n + case 0x6c: // AND ($FF00+w),n + case 0x6d: // XOR ($FF00+w),n + case 0x6e: // OR ($FF00+w),n + OP( ADD+b2-0x68,12 ) MI16( 1, 0xFF00|b1 ) I8( 2, READ8() ) return; + case 0x6f: // CP ($FF00+w),n + OP( ADD+b2-0x68,10 ) MI16( 1, 0xFF00|b1 ) I8( 2, READ8() ) return; + } break; + + case 0xf0: case 0xf1: case 0xf2: + b1 = READ8(); + b2 = READ8(); + switch ( b2 ) { + case 0x10: // RLD (ix+d) + case 0x11: // RRD (ix+d) + OP( RLD+b2-0x10,16 ) MR16D8( 1, IX + b0 - 0xf0, b1 ) NONE( 2 ) return; + + case 0x12: // MUL HL,(ix+d) + case 0x13: // DIV HL,(ix+d) + OP( MUL+b2-0x12,22 ) R16( 1, HL ) MR16D8( 2, IX + b0 - 0xf0, b1 ) return; + + case 0x14: case 0x15: case 0x16: + OP16( ADD,12 ) R16( 1, IX+b2-0x14 ) MR16D8( 2, IX + b0 - 0xf0, b1 ) return; // ADD ix,(jx+d) + + case 0x28: case 0x29: case 0x2a: case 0x2b: case 0x2c: case 0x2d: case 0x2e: + OP( LD,10 ) R8( 1, b2 - 0x28 ) MR16D8( 2, IX + b0 - 0xf0, b1 ) return; // LD r,(ix+d) + case 0x48: case 0x49: case 0x4a: /*case 0x4b:*/ case 0x4c: case 0x4d: case 0x4e: + OP16( LD,12 ) R16( 1, b2 - 0x48 ) MR16D8( 2, IX + b0 - 0xf0, b1 ) return; // LD rr,(ix+d) + + case 0x50: case 0x51: case 0x52: /*case 0x53:*/ case 0x54: case 0x55: case 0x56: + OP( EX,18 ) MR16D8( 1, IX + b0 - 0xf0, b1 ) R16( 2, b2 - 0x50 ) return; // EX (ix+d),rr + + case 0x60: // ADD A,(ix+d) + case 0x61: // ADC A,(ix+d) + case 0x62: // SUB A,(ix+d) + case 0x63: // SBC A,(ix+d) + case 0x64: // AND A,(ix+d) + case 0x65: // XOR A,(ix+d) + case 0x66: // OR A,(ix+d) + case 0x67: // CP A,(ix+d) + OP( ADD+b2-0x60,10 ) R8( 1, A ) MR16D8( 2, IX + b0 - 0xf0, b1 ) return; + + case 0x70: // ADD HL,(ix+d) + case 0x71: // ADC HL,(ix+d) + case 0x72: // SUB HL,(ix+d) + case 0x73: // SBC HL,(ix+d) + case 0x74: // AND HL,(ix+d) + case 0x75: // XOR HL,(ix+d) + case 0x76: // OR HL,(ix+d) + case 0x77: // CP HL,(ix+d) + OP16( ADD+b2-0x70,12 ) R16( 1, HL ) MR16D8( 2, IX + b0 - 0xf0, b1 ) return; + + case 0x87: + OP( INC,12 ) MR16D8( 1, IX + b0 - 0xf0, b1 ) NONE( 2 ) return; // INC (ix+d) + case 0x8f: + OP( DEC,12 ) MR16D8( 1, IX + b0 - 0xf0, b1 ) NONE( 2 ) return; // DEC (ix+d) + + case 0x97: + OP( INCW,16 ) MR16D8( 1, IX + b0 - 0xf0, b1 ) NONE( 2 ) return; // INCW (ix+d) + case 0x9f: + OP( DECW,16 ) MR16D8( 1, IX + b0 - 0xf0, b1 ) NONE( 2 ) return; // DECW (ix+d) + + case 0xa0: // RLC (ix+d) + case 0xa1: // RRC (ix+d) + case 0xa2: // RL (ix+d) + case 0xa3: // RR (ix+d) + case 0xa4: // SLA (ix+d) + case 0xa5: // SRA (ix+d) + case 0xa6: // SLL (ix+d) + case 0xa7: // SRL (ix+d) + OP( RLC+b2-0xa0,12 ) MR16D8( 1, IX + b0 - 0xf0, b1 ) NONE( 2 ) return; + + case 0x18: case 0x19: case 0x1a: case 0x1b: case 0x1c: case 0x1d: case 0x1e: case 0x1f: + OP( TSET,16 ) BIT8( 1, b2 - 0x18 ) MR16D8( 2, IX + b0 - 0xf0, b1 ) return; // TSET b,(ix+d) + case 0xa8: case 0xa9: case 0xaa: case 0xab: case 0xac: case 0xad: case 0xae: case 0xaf: + OP( BIT,10 ) BIT8( 1, b2 - 0xa8 ) MR16D8( 2, IX + b0 - 0xf0, b1 ) return; // BIT b,(ix+d) + case 0xb0: case 0xb1: case 0xb2: case 0xb3: case 0xb4: case 0xb5: case 0xb6: case 0xb7: + OP( RES,14 ) BIT8( 1, b2 - 0xb0 ) MR16D8( 2, IX + b0 - 0xf0, b1 ) return; // RES b,(ix+d) + case 0xb8: case 0xb9: case 0xba: case 0xbb: case 0xbc: case 0xbd: case 0xbe: case 0xbf: + OP( SET,14 ) BIT8( 1, b2 - 0xb8 ) MR16D8( 2, IX + b0 - 0xf0, b1 ) return; // SET b,(ix+d) + } break; + + case 0xf3: + b1 = READ8(); + switch ( b1 ) { + case 0x10: // RLD (HL+A) + case 0x11: // RRD (HL+A) + OP( RLD+b1-0x10,20 ) MR16R8( 1, HL, A ) NONE( 2 ) return; + + case 0x12: // MUL HL,(HL+A) + case 0x13: // DIV HL,(HL+A) + OP( MUL+b1-0x12,26 ) R16( 1, HL ) MR16R8( 2, HL, A ) return; + + case 0x14: case 0x15: case 0x16: + OP16( ADD,16 ) R16( 1, IX+b1-0x14 ) MR16R8( 2, HL, A ) return; // ADD ix,(HL+A) + + case 0x28: case 0x29: case 0x2a: case 0x2b: case 0x2c: case 0x2d: case 0x2e: + OP( LD,14 ) R8( 1, b1 - 0x28 ) MR16R8( 2, HL, A ) return; // LD r,(HL+A) + case 0x48: case 0x49: case 0x4a: /*case 0x4b:*/ case 0x4c: case 0x4d: case 0x4e: + OP16( LD,16 ) R16( 1, b1 - 0x48 ) MR16R8( 2, HL, A ) return; // LD rr,(HL+A) + + case 0x50: case 0x51: case 0x52: /*case 0x53:*/ case 0x54: case 0x55: case 0x56: + OP( EX,22 ) MR16R8( 1, HL, A ) R16( 2, b1 - 0x50 ) return; // EX (HL+A),rr + + case 0x60: // ADD A,(HL+A) + case 0x61: // ADC A,(HL+A) + case 0x62: // SUB A,(HL+A) + case 0x63: // SBC A,(HL+A) + case 0x64: // AND A,(HL+A) + case 0x65: // XOR A,(HL+A) + case 0x66: // OR A,(HL+A) + case 0x67: // CP A,(HL+A) + OP( ADD+b1-0x60,14 ) R8( 1, A ) MR16R8( 2, HL, A ) return; + + case 0x70: // ADD HL,(HL+A) + case 0x71: // ADC HL,(HL+A) + case 0x72: // SUB HL,(HL+A) + case 0x73: // SBC HL,(HL+A) + case 0x74: // AND HL,(HL+A) + case 0x75: // XOR HL,(HL+A) + case 0x76: // OR HL,(HL+A) + case 0x77: // CP HL,(HL+A) + OP16( ADD+b1-0x70,16 ) R16( 1, HL ) MR16R8( 2, HL, A ) return; + + case 0x87: + OP( INC,16 ) MR16R8( 1, HL, A ) NONE( 2 ) return; // INC (HL+A) + case 0x8f: + OP( DEC,16 ) MR16R8( 1, HL, A ) NONE( 2 ) return; // DEC (HL+A) + + case 0x97: + OP( INCW,20 ) MR16R8( 1, HL, A ) NONE( 2 ) return; // INCW (HL+A) + case 0x9f: + OP( DECW,20 ) MR16R8( 1, HL, A ) NONE( 2 ) return; // DECW (HL+A) + + case 0xa0: // RLC (HL+A) + case 0xa1: // RRC (HL+A) + case 0xa2: // RL (HL+A) + case 0xa3: // RR (HL+A) + case 0xa4: // SLA (HL+A) + case 0xa5: // SRA (HL+A) + case 0xa6: // SLL (HL+A) + case 0xa7: // SRL (HL+A) + OP( RLC+b1-0xa0,16 ) MR16R8( 1, HL, A ) NONE( 2 ) return; + + case 0x18: case 0x19: case 0x1a: case 0x1b: case 0x1c: case 0x1d: case 0x1e: case 0x1f: + OP( TSET,20 ) BIT8( 1, b1 - 0x18 ) MR16R8( 2, HL, A ) return; // TSET b,(HL+A) + case 0xa8: case 0xa9: case 0xaa: case 0xab: case 0xac: case 0xad: case 0xae: case 0xaf: + OP( BIT,14 ) BIT8( 1, b1 - 0xa8 ) MR16R8( 2, HL, A ) return; // BIT b,(HL+A) + case 0xb0: case 0xb1: case 0xb2: case 0xb3: case 0xb4: case 0xb5: case 0xb6: case 0xb7: + OP( RES,18 ) BIT8( 1, b1 - 0xb0 ) MR16R8( 2, HL, A ) return; // RES b,(HL+A) + case 0xb8: case 0xb9: case 0xba: case 0xbb: case 0xbc: case 0xbd: case 0xbe: case 0xbf: + OP( SET,18 ) BIT8( 1, b1 - 0xb8 ) MR16R8( 2, HL, A ) return; // SET b,(HL+A) + } break; + + case 0xf4: case 0xf5: case 0xf6: + b1 = READ8(); + b2 = READ8(); + switch ( b2 ) { + case 0x20: case 0x21: case 0x22: case 0x23: case 0x24: case 0x25: case 0x26: + OP( LD,10 ) MR16D8( 1, IX + b0 - 0xf4, b1 ) R8( 2, b2 - 0x20 ) return; // LD (ix+d),r + case 0x37: + OP( LD,12 ) MR16D8( 1, IX + b0 - 0xf4, b1 ) I8( 2, READ8() ) return; // LD (ix+d),n + case 0x38: case 0x39: case 0x3a: /*case 0x3b:*/ case 0x3c: case 0x3d: case 0x3e: + OP( LDA,10 ) R16( 1, b2 - 0x38 ) R16D8( 2, IX + b0 - 0xf4, b1 ) return; // LDA rr,ix+d + case 0x3f: + OP( LDW,16 ) MR16D8( 1, IX + b0 - 0xf4, b1 ) I16( 2, READ16() ) return; // LDW (ix+d),mn + case 0x40: case 0x41: case 0x42: /*case 0x43:*/ case 0x44: case 0x45: case 0x46: + OP16( LD,12 ) MR16D8( 1, IX + b0 - 0xf4, b1 ) R16( 2, b2 - 0x40 ) return; // LD (ix+d),rr + + case 0x68: // ADD (ix+d),n + case 0x69: // ADC (ix+d),n + case 0x6a: // SUB (ix+d),n + case 0x6b: // SBC (ix+d),n + case 0x6c: // AND (ix+d),n + case 0x6d: // XOR (ix+d),n + case 0x6e: // OR (ix+d),n + OP( ADD+b2-0x68,14) MR16D8( 1, IX + b0 - 0xf4, b1 ) I8( 2, READ8() ) return; + case 0x6f: // CP (ix+d),n + OP( ADD+b2-0x68,12) MR16D8( 1, IX + b0 - 0xf4, b1 ) I8( 2, READ8() ) return; + + case 0xc0: case 0xc1: case 0xc2: case 0xc3: case 0xc4: case 0xc5: case 0xc6: case 0xc7: + case 0xc8: case 0xc9: case 0xca: case 0xcb: case 0xcc: case 0xcd: case 0xce: case 0xcf: + OPCC( JP,10,12 ) CC( 1, b2 - 0xc0 ) R16D8( 2, IX + b0 - 0xf4, b1 ) return; // JP [cc,]ix+d + case 0xd0: case 0xd1: case 0xd2: case 0xd3: case 0xd4: case 0xd5: case 0xd6: case 0xd7: + case 0xd8: case 0xd9: case 0xda: case 0xdb: case 0xdc: case 0xdd: case 0xde: case 0xdf: + OPCC( CALL,10,18 ) CC( 1, b2 - 0xd0 ) R16D8( 2, IX + b0 - 0xf4, b1 ) return; // CALL [cc,]ix+d + } break; + + case 0xf7: + b1 = READ8(); + switch ( b1 ) { + case 0x20: case 0x21: case 0x22: case 0x23: case 0x24: case 0x25: case 0x26: + OP( LD,14 ) MR16R8( 1, HL, A ) R8( 2, b1 - 0x20 ) return; // LD (HL+A),r + case 0x37: + OP( LD,16 ) MR16R8( 1, HL, A ) I8( 2, READ8() ) return; // LD (HL+A),n + case 0x38: case 0x39: case 0x3a: /*case 0x3b:*/ case 0x3c: case 0x3d: case 0x3e: + OP( LDA,14 ) R16( 1, b1 - 0x38 ) R16R8( 2, HL, A ) return; // LDA rr,HL+A + case 0x3f: + OP( LDW,20 ) MR16R8( 1, HL, A ) I16( 2, READ16() ) return; // LDW (HL+A),mn + case 0x40: case 0x41: case 0x42: /*case 0x43:*/ case 0x44: case 0x45: case 0x46: + OP16( LD,16 ) MR16R8( 1, HL, A ) R16( 2, b1 - 0x40 ) return; // LD (HL+A),rr + + case 0x68: // ADD (HL+A),n + case 0x69: // ADC (HL+A),n + case 0x6a: // SUB (HL+A),n + case 0x6b: // SBC (HL+A),n + case 0x6c: // AND (HL+A),n + case 0x6d: // XOR (HL+A),n + case 0x6e: // OR (HL+A),n + OP( ADD+b1-0x68,18) MR16R8( 1, HL, A ) I8( 2, READ8() ) return; + case 0x6f: // CP (HL+A),n + OP( ADD+b1-0x68,16) MR16R8( 1, HL, A ) I8( 2, READ8() ) return; + + case 0xc0: case 0xc1: case 0xc2: case 0xc3: case 0xc4: case 0xc5: case 0xc6: case 0xc7: + case 0xc8: case 0xc9: case 0xca: case 0xcb: case 0xcc: case 0xcd: case 0xce: case 0xcf: + OPCC( JP,14,16 ) CC( 1, b1 - 0xc0 ) R16R8( 2, HL, A ) return; // JP [cc,]HL+A + case 0xd0: case 0xd1: case 0xd2: case 0xd3: case 0xd4: case 0xd5: case 0xd6: case 0xd7: + case 0xd8: case 0xd9: case 0xda: case 0xdb: case 0xdc: case 0xdd: case 0xde: case 0xdf: + OPCC( CALL,14,22 ) CC( 1, b1 - 0xd0 ) R16R8( 2, HL, A ) return; // CALL [cc,]HL+A + } break; + + case 0xf8: case 0xf9: case 0xfa: case 0xfb: case 0xfc: case 0xfd: case 0xfe: + b1 = READ8(); + switch ( b1 ) { + case 0x12: // MUL HL,g + case 0x13: // DIV HL,g + OP( MUL+b1-0x12,18) R16( 1, HL ) R8( 2, b0 - 0xf8 ) return; + + case 0x14: case 0x15: case 0x16: + OP16( ADD,8 ) R16( 1, IX+b1-0x14 ) R16( 2, b0 - 0xf8 ) return; // ADD ix,gg + + case 0x30: case 0x31: case 0x32: case 0x33: case 0x34: case 0x35: case 0x36: + OP( LD,4 ) R8( 1, b1 - 0x30 ) R8( 2, b0 - 0xf8 ) return; // LD r,g + case 0x38: case 0x39: case 0x3a: /*case 0x3b:*/ case 0x3c: case 0x3d: case 0x3e: + OP16( LD,6 ) R16( 1, b1 - 0x38 ) R16( 2, b0 - 0xf8 ) return; // LD rr,gg + + case 0x58: // LDI + case 0x59: // LDIR + case 0x5a: // LDD + case 0x5b: // LDDR + case 0x5c: // CPI + case 0x5d: // CPIR + case 0x5e: // CPD + case 0x5f: // CPDR + if (b0 == 0xfe) { + OPCC( LDI+b1-0x58,14,18 ) NONE( 1 ) NONE( 2 ) return; + } + + case 0x60: // ADD A,g + case 0x61: // ADC A,g + case 0x62: // SUB A,g + case 0x63: // SBC A,g + case 0x64: // AND A,g + case 0x65: // XOR A,g + case 0x66: // OR A,g + case 0x67: // CP A,g + OP( ADD+b1-0x60,4 ) R8( 1, A ) R8( 2, b0 - 0xf8 ) return; + + case 0x68: // ADD g,n + case 0x69: // ADC g,n + case 0x6a: // SUB g,n + case 0x6b: // SBC g,n + case 0x6c: // AND g,n + case 0x6d: // XOR g,n + case 0x6e: // OR g,n + case 0x6f: // CP g,n + OP( ADD+b1-0x68,6 ) R8( 1, b0 - 0xf8 ) I8( 2, READ8() ) return; + + case 0x70: // ADD HL,gg + case 0x71: // ADC HL,gg + case 0x72: // SUB HL,gg + case 0x73: // SBC HL,gg + case 0x74: // AND HL,gg + case 0x75: // XOR HL,gg + case 0x76: // OR HL,gg + case 0x77: // CP HL,gg + OP16( ADD+b1-0x70,8 ) R16( 1, HL ) R16( 2, b0 - 0xf8 ) return; + + case 0xa0: // RLC g + case 0xa1: // RRC g + case 0xa2: // RL g + case 0xa3: // RR g + case 0xa4: // SLA g + case 0xa5: // SRA g + case 0xa6: // SLL g + case 0xa7: // SRL g + OP( RLC+b1-0xa0,4 ) R8( 1, b0 - 0xf8 ) NONE( 2 ) return; + + case 0x18: case 0x19: case 0x1a: case 0x1b: case 0x1c: case 0x1d: case 0x1e: case 0x1f: + OP( TSET,8 ) BIT8( 1, b1 - 0x18 ) R8( 2, b0 - 0xf8 ) return; // TSET b,g + case 0xa8: case 0xa9: case 0xaa: case 0xab: case 0xac: case 0xad: case 0xae: case 0xaf: + OP( BIT,4 ) BIT8( 1, b1 - 0xa8 ) R8( 2, b0 - 0xf8 ) return; // BIT b,g + case 0xb0: case 0xb1: case 0xb2: case 0xb3: case 0xb4: case 0xb5: case 0xb6: case 0xb7: + OP( RES,4 ) BIT8( 1, b1 - 0xb0 ) R8( 2, b0 - 0xf8 ) return; // RES b,g + case 0xb8: case 0xb9: case 0xba: case 0xbb: case 0xbc: case 0xbd: case 0xbe: case 0xbf: + OP( SET,4 ) BIT8( 1, b1 - 0xb8 ) R8( 2, b0 - 0xf8 ) return; // SET b,g + + case 0xd0: case 0xd1: case 0xd2: case 0xd3: case 0xd4: case 0xd5: case 0xd6: case 0xd7: + case 0xd8: case 0xd9: case 0xda: case 0xdb: case 0xdc: case 0xdd: case 0xde: case 0xdf: + if (b0 == 0xfe) { + OPCC( RET,6,14 ) CC( 1, b1 - 0xd0 ) NONE( 2 ) return; // RET cc + } + } break; + + case 0xff: + OP( SWI,20 ) NONE( 1 ) NONE( 2 ) return; // SWI + } + + OP( UNKNOWN,2 ) NONE( 1 ) NONE( 2 ) +} + +bool tlcs90_disassembler::stream_arg(std::ostream &stream, uint32_t pc, const char *pre, const e_mode mode, const uint16_t r, const uint16_t rb) +{ + const char *reg_name; + switch ( mode ) + { + case e_mode::NONE: return false; + + case e_mode::BIT8: util::stream_format(stream, "%s%d", pre, r ); return true; + case e_mode::I8: util::stream_format(stream, "%s$%02X", pre, r ); return true; + case e_mode::D8: util::stream_format(stream, "%s$%04X", pre, (pc+2+(r&0x7f)-(r&0x80))&0xffff ); return true; + case e_mode::I16: util::stream_format(stream, "%s$%04X", pre, r ); return true; + case e_mode::D16: util::stream_format(stream, "%s$%04X", pre, (pc+2+(r&0x7fff)-(r&0x8000))&0xffff ); return true; + case e_mode::MI16: + reg_name = internal_registers_names(r); + if (reg_name) + util::stream_format(stream, "%s(%s)", pre, reg_name); + else + util::stream_format(stream, "%s($%04X)", pre, r ); + return true; + case e_mode::R8: util::stream_format(stream, "%s%s", pre, r8_names[r] ); return true; + case e_mode::R16: util::stream_format(stream, "%s%s", pre, r16_names[r] ); return true; + case e_mode::MR16: util::stream_format(stream, "%s(%s)", pre, r16_names[r] ); return true; + + case e_mode::MR16R8: util::stream_format(stream, "%s(%s+%s)", pre, r16_names[r], r8_names[rb] ); return true; + case e_mode::MR16D8: util::stream_format(stream, "%s(%s%c$%02X)", pre, r16_names[r], (rb&0x80)?'-':'+', (rb&0x80)?((rb^0xff)+1):rb ); return true; + + case e_mode::CC: util::stream_format(stream, "%s%s", pre, cc_names[r] ); return true; + + case e_mode::R16R8: util::stream_format(stream, "%s%s+%s", pre, r16_names[r], r8_names[rb] ); return true; + case e_mode::R16D8: util::stream_format(stream, "%s%s%c$%02X", pre, r16_names[r], (rb&0x80)?'-':'+', (rb&0x80)?((rb^0xff)+1):rb ); return true; + + default: + fatalerror("%04x: unimplemented addr mode = %d\n",pc,std::underlying_type_t(mode)); + } + + // never executed + return false; +} + +offs_t tlcs90_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + m_addr = pc; + m_opcodes = &opcodes; + + decode(); + + util::stream_format (stream, "%-5s", op_names[ m_op ] ); // strlen("callr") == 5 + bool streamed = stream_arg (stream, pc, " ", m_mode1, m_r1, m_r1b ); + stream_arg (stream, pc, streamed ?",":"", m_mode2, m_r2, m_r2b ); + + return (m_addr - pc) | SUPPORTED; +} diff --git a/src/devices/cpu/tlcs90/tlcs90d.h b/src/devices/cpu/tlcs90/tlcs90d.h new file mode 100644 index 00000000000..8db7509512c --- /dev/null +++ b/src/devices/cpu/tlcs90/tlcs90d.h @@ -0,0 +1,65 @@ +// license:BSD-3-Clause +// copyright-holders:Luca Elia +/************************************************************************************************************* + + Toshiba TLCS-90 Series MCU's + + emulation by Luca Elia, based on the Z80 core by Juergen Buchmueller + + ChangeLog: + + 20150517 Fixed TRUN bit masking (timers start/stop handling) [Rainer Keuchel] + +*************************************************************************************************************/ + +#ifndef MAME_CPU_TLCS90_TLCS90D_H +#define MAME_CPU_TLCS90_TLCS90D_H + +#pragma once + +class tlcs90_disassembler : public util::disasm_interface +{ +public: + tlcs90_disassembler() = default; + virtual ~tlcs90_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum _e_op { UNKNOWN, NOP, EX, EXX, LD, LDW, LDA, LDI, LDIR, LDD, LDDR, CPI, CPIR, CPD, CPDR, PUSH, POP, JP, JR, CALL, CALLR, RET, RETI, HALT, DI, EI, SWI, DAA, CPL, NEG, LDAR, RCF, SCF, CCF, TSET, BIT, SET, RES, INC, DEC, INCX, DECX, INCW, DECW, ADD, ADC, SUB, SBC, AND, XOR, OR, CP, RLC, RRC, RL, RR, SLA, SRA, SLL, SRL, RLD, RRD, DJNZ, MUL, DIV }; + + enum class e_mode : u8 { + NONE, BIT8, CC, + I8, D8, R8, + I16, D16, R16, + MI16, MR16, MR16D8, MR16R8, + R16D8, R16R8 + }; + + static const char *const op_names[]; + static const char *const r8_names[]; + static const char *const r16_names[]; + static const char *const cc_names[]; + static const char *const ir_names[]; + + uint8_t m_op; + + e_mode m_mode1; + uint16_t m_r1,m_r1b; + + e_mode m_mode2; + uint16_t m_r2,m_r2b; + + offs_t m_addr; + const data_buffer *m_opcodes; + + inline uint8_t READ8(); + inline uint16_t READ16(); + void decode(); + + bool stream_arg(std::ostream &stream, uint32_t pc, const char *pre, const e_mode mode, const uint16_t r, const uint16_t rb); + const char *internal_registers_names(uint16_t x); +}; + +#endif diff --git a/src/devices/cpu/tlcs900/dasm900.cpp b/src/devices/cpu/tlcs900/dasm900.cpp index 64c8c6ba099..b700bf6341a 100644 --- a/src/devices/cpu/tlcs900/dasm900.cpp +++ b/src/devices/cpu/tlcs900/dasm900.cpp @@ -7,36 +7,9 @@ Toshiba TLCS-900/H disassembly *******************************************************************/ #include "emu.h" -#include "debugger.h" -#include "tlcs900.h" +#include "dasm900.h" -enum e_mnemonics -{ - M_ADC, M_ADD, M_AND, M_ANDCF, M_BIT, M_BS1B, - M_BS1F, M_CALL, M_CALR, M_CCF, M_CHG, M_CP, - M_CPD, M_CPDW, M_CPDR, M_CPDRW, M_CPI, M_CPIR, - M_CPIRW, M_CPIW, M_CPL, M_DAA, M_DB, M_DEC, - M_DECF, M_DECW, M_DIV, M_DIVS, M_DJNZ, M_EI, - M_EX, M_EXTS, M_EXTZ, M_HALT, M_INC, M_INCF, - M_INCW, M_JP, M_JR, M_JRL, M_LD, M_LDA, - M_LDC, M_LDCF, M_LDD, M_LDDR, M_LDDRW, M_LDDW, - M_LDF, M_LDI, M_LDIR, M_LDIRW, M_LDIW, M_LDW, - M_LDX, M_LINK, M_MAX, M_MDEC1, M_MDEC2, M_MDEC4, - M_MINC1, M_MINC2, M_MINC4, M_MIRR, M_MUL, M_MULA, - M_MULS, M_NEG, M_NOP, M_NORMAL, M_OR, M_ORCF, - M_PAA, M_POP, M_POPW, M_PUSH, M_PUSHW, M_RCF, - M_RES, M_RET, M_RETD, M_RETI, M_RL, M_RLC, - M_RLCW, M_RLD, M_RLW, M_RR, M_RRC, M_RRCW, - M_RRD, M_RRW, M_SBC, M_SCC, M_SCF, M_SET, - M_SLA, M_SLAW, M_SLL, M_SLLW, M_SRA, M_SRAW, - M_SRL, M_SRLW, M_STCF, M_SUB, M_SWI, M_TSET, - M_UNLK, M_XOR, M_XORCF, M_ZCF, - M_80, M_88, M_90, M_98, M_A0, M_A8, M_B0, M_B8, - M_C0, oC8, M_D0, oD8, M_E0, M_E8, M_F0 -}; - - -static const char *const s_mnemonic[] = +const char *const tlcs900_disassembler::s_mnemonic[] = { "adc", "add", "and", "andcf", "bit", "bs1b", "bs1f", "call", "calr", "ccf", "chg", "cp", @@ -62,43 +35,7 @@ static const char *const s_mnemonic[] = }; -enum e_operand -{ - O_NONE, - O_A, /* current register set register A */ - O_C8, /* current register set byte */ - O_C16, /* current register set word */ - O_C32, /* current register set long word */ - O_MC16, /* current register set mul/div register word */ - O_CC, /* condition */ - O_CR8, /* byte control register */ - O_CR16, /* word control register */ - O_CR32, /* long word control register */ - O_D8, /* byte displacement */ - O_D16, /* word displacement */ - O_F, /* F register */ - O_I3, /* immediate 3 bit (part of last byte) */ - O_I8, /* immediate byte */ - O_I16, /* immediate word */ - O_I24, /* immediate 3 byte address */ - O_I32, /* immediate long word */ - O_M, /* memory location (defined by extension) */ - O_M8, /* (8) */ - O_M16, /* (i16) */ - O_R, /* register */ - O_SR /* status register */ -}; - - -struct tlcs900inst -{ - e_mnemonics mnemonic; - e_operand operand1; - e_operand operand2; -}; - - -static const tlcs900inst mnemonic_80[256] = +const tlcs900_disassembler::tlcs900inst tlcs900_disassembler::mnemonic_80[256] = { /* 00 - 1F */ { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, @@ -182,7 +119,7 @@ static const tlcs900inst mnemonic_80[256] = }; -static const tlcs900inst mnemonic_88[256] = +const tlcs900_disassembler::tlcs900inst tlcs900_disassembler::mnemonic_88[256] = { /* 00 - 1F */ { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, @@ -266,7 +203,7 @@ static const tlcs900inst mnemonic_88[256] = }; -static const tlcs900inst mnemonic_90[256] = +const tlcs900_disassembler::tlcs900inst tlcs900_disassembler::mnemonic_90[256] = { /* 00 - 1F */ { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, @@ -350,7 +287,7 @@ static const tlcs900inst mnemonic_90[256] = }; -static const tlcs900inst mnemonic_98[256] = +const tlcs900_disassembler::tlcs900inst tlcs900_disassembler::mnemonic_98[256] = { /* 00 - 1F */ { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, @@ -434,7 +371,7 @@ static const tlcs900inst mnemonic_98[256] = }; -static const tlcs900inst mnemonic_a0[256] = +const tlcs900_disassembler::tlcs900inst tlcs900_disassembler::mnemonic_a0[256] = { /* 00 - 1F */ { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, @@ -518,7 +455,7 @@ static const tlcs900inst mnemonic_a0[256] = }; -static const tlcs900inst mnemonic_b0[256] = +const tlcs900_disassembler::tlcs900inst tlcs900_disassembler::mnemonic_b0[256] = { /* 00 - 1F */ { M_LD, O_M, O_I8 }, { M_DB, O_NONE, O_NONE }, { M_LD, O_M, O_I16 }, { M_DB, O_NONE, O_NONE }, @@ -602,7 +539,7 @@ static const tlcs900inst mnemonic_b0[256] = }; -static const tlcs900inst mnemonic_b8[256] = +const tlcs900_disassembler::tlcs900inst tlcs900_disassembler::mnemonic_b8[256] = { /* 00 - 1F */ { M_LD, O_M, O_I8 }, { M_DB, O_NONE, O_NONE }, { M_LD, O_M, O_I16 }, { M_DB, O_NONE, O_NONE }, @@ -686,7 +623,7 @@ static const tlcs900inst mnemonic_b8[256] = }; -static const tlcs900inst mnemonic_c0[256] = +const tlcs900_disassembler::tlcs900inst tlcs900_disassembler::mnemonic_c0[256] = { /* 00 - 1F */ { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, @@ -771,7 +708,7 @@ static const tlcs900inst mnemonic_c0[256] = /* TODO: M_MUL_O_I8, M_MULS_O_I8, M_DIV_O_I8, M_DIVS_O_i8 need to be fixed */ -static const tlcs900inst mnemonic_c8[256] = +const tlcs900_disassembler::tlcs900inst tlcs900_disassembler::mnemonic_c8[256] = { /* 00 - 1F */ { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_LD, O_R, O_I8 }, @@ -855,7 +792,7 @@ static const tlcs900inst mnemonic_c8[256] = }; -static const tlcs900inst mnemonic_d0[256] = +const tlcs900_disassembler::tlcs900inst tlcs900_disassembler::mnemonic_d0[256] = { /* 00 - 1F */ { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, @@ -939,7 +876,7 @@ static const tlcs900inst mnemonic_d0[256] = }; -static const tlcs900inst mnemonic_d8[256] = +const tlcs900_disassembler::tlcs900inst tlcs900_disassembler::mnemonic_d8[256] = { /* 00 - 1F */ { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_LD, O_R, O_I16 }, @@ -1023,7 +960,7 @@ static const tlcs900inst mnemonic_d8[256] = }; -static const tlcs900inst mnemonic_e0[256] = +const tlcs900_disassembler::tlcs900inst tlcs900_disassembler::mnemonic_e0[256] = { /* 00 - 1F */ { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, @@ -1107,7 +1044,7 @@ static const tlcs900inst mnemonic_e0[256] = }; -static const tlcs900inst mnemonic_e8[256] = +const tlcs900_disassembler::tlcs900inst tlcs900_disassembler::mnemonic_e8[256] = { /* 00 - 1F */ { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_DB, O_NONE, O_NONE }, { M_LD, O_R, O_I32 }, @@ -1191,7 +1128,7 @@ static const tlcs900inst mnemonic_e8[256] = }; -static const tlcs900inst mnemonic_f0[256] = +const tlcs900_disassembler::tlcs900inst tlcs900_disassembler::mnemonic_f0[256] = { /* 00 - 1F */ { M_LD, O_M, O_I8 }, { M_DB, O_NONE, O_NONE }, { M_LD, O_M, O_I16 }, { M_DB, O_NONE, O_NONE }, @@ -1275,7 +1212,7 @@ static const tlcs900inst mnemonic_f0[256] = }; -static const tlcs900inst mnemonic[256] = +const tlcs900_disassembler::tlcs900inst tlcs900_disassembler::mnemonic[256] = { /* 00 - 1F */ { M_NOP, O_NONE, O_NONE }, { M_NORMAL, O_NONE, O_NONE }, { M_PUSH, O_SR, O_NONE }, { M_POP, O_SR, O_NONE }, @@ -1360,11 +1297,11 @@ static const tlcs900inst mnemonic[256] = -static const char *const s_reg8[8] = { "W", "A", "B", "C", "D", "E", "H", "L" }; -static const char *const s_reg16[8] = { "WA", "BC", "DE", "HL", "IX", "IY", "IZ", "SP" }; -static const char *const s_reg32[8] = { "XWA", "XBC", "XDE", "XHL", "XIX", "XIY", "XIZ", "XSP" }; -static const char *const s_mulreg16[8] = { "??", "WA", "??", "BC", "??", "DE", "??", "HL" }; -static const char *const s_allreg8[256] = +const char *const tlcs900_disassembler::s_reg8[8] = { "W", "A", "B", "C", "D", "E", "H", "L" }; +const char *const tlcs900_disassembler::s_reg16[8] = { "WA", "BC", "DE", "HL", "IX", "IY", "IZ", "SP" }; +const char *const tlcs900_disassembler::s_reg32[8] = { "XWA", "XBC", "XDE", "XHL", "XIX", "XIY", "XIZ", "XSP" }; +const char *const tlcs900_disassembler::s_mulreg16[8] = { "??", "WA", "??", "BC", "??", "DE", "??", "HL" }; +const char *const tlcs900_disassembler::s_allreg8[256] = { "RA0" ,"RW0" ,"QA0" ,"QW0" ,"RC0" ,"RB0" ,"QC0" ,"QB0" ,"RE0" ,"RD0" ,"QE0" ,"QD0" ,"RL0" ,"RH0" ,"QL0" ,"QH0" , "RA1" ,"RW1" ,"QA1" ,"QW1" ,"RC1" ,"RB1" ,"QC1" ,"QB1" ,"RE1" ,"RD1" ,"QE1" ,"QD1" ,"RL1" ,"RH1" ,"QL1" ,"QH1" , @@ -1385,7 +1322,7 @@ static const char *const s_allreg8[256] = }; -static const char *const s_allreg16[256] = +const char *const tlcs900_disassembler::s_allreg16[256] = { "RWA0","r01W","QWA0","r03W","RBC0","r05W","QBC0","r07W","RDE0","r09W","QDE0","r0BW","RHL0","r0DW","QHL0","r0FW", "RWA1","r11W","QWA1","r13W","RBC1","r15W","QBC1","r17W","RDE1","r19W","QDE1","r1BW","RHL1","r1DW","QHL1","r1FW", @@ -1406,7 +1343,7 @@ static const char *const s_allreg16[256] = }; -static const char *const s_allreg32[256] = +const char *const tlcs900_disassembler::s_allreg32[256] = { "XWA0","XWA0","XWA0","r03L","XBC0","XBC0","XBC0","r07L","XDE0","XDE0","XDE0","r0BL","XHL0","XHL0","XHL0","r0FL", "XWA1","XWA1","XWA1","r13L","XBC1","XBC1","XBC1","r17L","XDE1","XDE1","XDE1","r1BL","XHL1","XHL1","XHL1","r1FL", @@ -1427,22 +1364,27 @@ static const char *const s_allreg32[256] = }; -static const char *const s_cond[16] = +const char *const tlcs900_disassembler::s_cond[16] = { "F","LT","LE","ULE","PE/OV","M/MI","Z","C","T","GE","GT","UGT","PO/NOV","P/PL","NZ","NC" }; -CPU_DISASSEMBLE(tlcs900) +u32 tlcs900_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t tlcs900_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { const tlcs900inst *dasm; std::string buf; uint8_t op, op1; uint32_t imm; int flags = 0; - int pos = 0; + offs_t pos = pc; - op = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); dasm = &mnemonic[ op ]; @@ -1454,53 +1396,53 @@ CPU_DISASSEMBLE(tlcs900) case M_80: buf = string_format("%s", s_reg32[op & 0x07]); - op = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); dasm = &mnemonic_80[ op ]; break; case M_88: - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("%s+0x%02x", s_reg32[op & 0x07], imm); - op = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); dasm = &mnemonic_88[ op ]; break; case M_90: buf = string_format("%s", s_reg32[op & 0x07]); - op = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); dasm = &mnemonic_90[ op ]; break; case M_98: - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("%s+0x%02x", s_reg32[op & 0x07], imm); - op = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); dasm = &mnemonic_98[ op ]; break; case M_A0: buf = string_format("%s", s_reg32[op & 0x07]); - op = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); dasm = &mnemonic_a0[ op ]; break; case M_A8: - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("%s+0x%02x", s_reg32[op & 0x07], imm); - op = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); dasm = &mnemonic_a0[ op ]; break; case M_B0: buf = string_format("%s", s_reg32[op & 0x07]); - op = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); dasm = &mnemonic_b0[ op ]; break; case M_B8: - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("%s+0x%02x", s_reg32[op & 0x07], imm); - op = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); dasm = &mnemonic_b8[ op ]; break; @@ -1508,25 +1450,25 @@ CPU_DISASSEMBLE(tlcs900) switch( op & 0x07 ) { case 0x00: /* 0xC0 */ - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("0x%02x", imm); break; case 0x01: /* 0xC1 */ - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); buf = string_format("0x%04x", imm); break; case 0x02: /* 0xC2 */ - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); - imm = imm | (oprom[ pos++ ] << 16); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); + imm = imm | (opcodes.r8( pos++ ) << 16); buf = string_format("0x%06x", imm); break; case 0x03: /* 0xC3 */ - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); switch( imm & 0x03 ) { case 0x00: @@ -1535,8 +1477,8 @@ CPU_DISASSEMBLE(tlcs900) case 0x01: op = imm; - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); buf = string_format("%s+0x%04x", s_allreg32[op], imm); break; @@ -1548,20 +1490,20 @@ CPU_DISASSEMBLE(tlcs900) switch( imm ) { case 0x03: - op = oprom[ pos++ ]; - op1 = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); + op1 = opcodes.r8( pos++ ); buf = string_format("%s+%s", s_allreg32[op], s_allreg8[op1]); break; case 0x07: - op = oprom[ pos++ ]; - op1 = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); + op1 = opcodes.r8( pos++ ); buf = string_format("%s+%s", s_allreg32[op], s_allreg16[op1]); break; case 0x13: - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); buf = string_format("0x%06x", pc + pos + (int16_t)imm); break; } @@ -1570,16 +1512,16 @@ CPU_DISASSEMBLE(tlcs900) break; case 0x04: /* 0xC4 */ - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("-%s", s_allreg32[imm]); break; case 0x05: /* 0xC5 */ - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("%s+", s_allreg32[imm]); break; } - op = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); dasm = &mnemonic_c0[ op ]; break; @@ -1590,10 +1532,10 @@ CPU_DISASSEMBLE(tlcs900) } else { - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("%s", s_allreg8[imm]); } - op = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); dasm = &mnemonic_c8[ op ]; break; @@ -1601,25 +1543,25 @@ CPU_DISASSEMBLE(tlcs900) switch( op & 0x07 ) { case 0x00: /* 0xD0 */ - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("0x%02x", imm); break; case 0x01: /* 0xD1 */ - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); buf = string_format("0x%04x", imm); break; case 0x02: /* 0xD2 */ - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); - imm = imm | (oprom[ pos++ ] << 16); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); + imm = imm | (opcodes.r8( pos++ ) << 16); buf = string_format("0x%06x", imm); break; case 0x03: /* 0xD3 */ - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); switch( imm & 0x03 ) { case 0x00: @@ -1628,8 +1570,8 @@ CPU_DISASSEMBLE(tlcs900) case 0x01: op = imm; - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); buf = string_format("%s+0x%04x", s_allreg32[op], imm); break; @@ -1641,20 +1583,20 @@ CPU_DISASSEMBLE(tlcs900) switch( imm ) { case 0x03: - op = oprom[ pos++ ]; - op1 = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); + op1 = opcodes.r8( pos++ ); buf = string_format("%s+%s", s_allreg32[op], s_allreg8[op1]); break; case 0x07: - op = oprom[ pos++ ]; - op1 = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); + op1 = opcodes.r8( pos++ ); buf = string_format("%s+%s", s_allreg32[op], s_allreg16[op1]); break; case 0x13: - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); buf = string_format("0x%06x", pc + pos + (int16_t)imm); break; } @@ -1663,16 +1605,16 @@ CPU_DISASSEMBLE(tlcs900) break; case 0x04: /* 0xD4 */ - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("-%s", s_allreg32[imm]); break; case 0x05: /* 0xD5 */ - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("%s+", s_allreg32[imm]); break; } - op = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); dasm = &mnemonic_d0[ op ]; break; @@ -1683,11 +1625,11 @@ CPU_DISASSEMBLE(tlcs900) } else { - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("%s", s_allreg16[imm]); } - op = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); dasm = &mnemonic_d8[ op ]; break; @@ -1695,25 +1637,25 @@ CPU_DISASSEMBLE(tlcs900) switch( op & 0x07 ) { case 0x00: /* 0xE0 */ - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("0x%02x", imm); break; case 0x01: /* 0xE1 */ - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); buf = string_format("0x%04x", imm); break; case 0x02: /* 0xE2 */ - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); - imm = imm | (oprom[ pos++ ] << 16); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); + imm = imm | (opcodes.r8( pos++ ) << 16); buf = string_format("0x%06x", imm); break; case 0x03: /* 0xE3 */ - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); switch( imm & 0x03 ) { case 0x00: @@ -1722,8 +1664,8 @@ CPU_DISASSEMBLE(tlcs900) case 0x01: op = imm; - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); buf = string_format("%s+0x%04x", s_allreg32[op], imm); break; @@ -1735,20 +1677,20 @@ CPU_DISASSEMBLE(tlcs900) switch( imm ) { case 0x03: - op = oprom[ pos++ ]; - op1 = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); + op1 = opcodes.r8( pos++ ); buf = string_format("%s+%s", s_allreg32[op], s_allreg8[op1]); break; case 0x07: - op = oprom[ pos++ ]; - op1 = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); + op1 = opcodes.r8( pos++ ); buf = string_format("%s+%s", s_allreg32[op], s_allreg16[op1]); break; case 0x13: - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); buf = string_format("0x%06x", pc + pos + (int16_t)imm); break; } @@ -1757,16 +1699,16 @@ CPU_DISASSEMBLE(tlcs900) break; case 0x04: /* 0xE4 */ - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("-%s", s_allreg32[imm]); break; case 0x05: /* 0xE5 */ - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("%s+", s_allreg32[imm]); break; } - op = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); dasm = &mnemonic_e0[ op ]; break; @@ -1777,10 +1719,10 @@ CPU_DISASSEMBLE(tlcs900) } else { - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("%s", s_allreg32[imm]); } - op = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); dasm = &mnemonic_e8[ op ]; break; @@ -1788,25 +1730,25 @@ CPU_DISASSEMBLE(tlcs900) switch( op & 0x07 ) { case 0x00: /* 0xF0 */ - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("0x%02x", imm); break; case 0x01: /* 0xF1 */ - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); buf = string_format("0x%04x", imm); break; case 0x02: /* 0xF2 */ - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); - imm = imm | (oprom[ pos++ ] << 16); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); + imm = imm | (opcodes.r8( pos++ ) << 16); buf = string_format("0x%06x", imm); break; case 0x03: /* 0xF3 */ - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); switch( imm & 0x03 ) { case 0x00: @@ -1815,8 +1757,8 @@ CPU_DISASSEMBLE(tlcs900) case 0x01: op = imm; - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); buf = string_format("%s+0x%04x", s_allreg32[op], imm); break; @@ -1828,20 +1770,20 @@ CPU_DISASSEMBLE(tlcs900) switch( imm ) { case 0x03: - op = oprom[ pos++ ]; - op1 = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); + op1 = opcodes.r8( pos++ ); buf = string_format("%s+%s", s_allreg32[op], s_allreg8[op1]); break; case 0x07: - op = oprom[ pos++ ]; - op1 = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); + op1 = opcodes.r8( pos++ ); buf = string_format("%s+%s", s_allreg32[op], s_allreg16[op1]); break; case 0x13: - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); buf = string_format("0x%06x", pc + pos + (int16_t)imm); break; } @@ -1850,16 +1792,16 @@ CPU_DISASSEMBLE(tlcs900) break; case 0x04: /* 0xF4 */ - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("-%s", s_allreg32[imm]); break; case 0x05: /* 0xF5 */ - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); buf = string_format("%s+", s_allreg32[imm]); break; } - op = oprom[ pos++ ]; + op = opcodes.r8( pos++ ); dasm = &mnemonic_f0[ op ]; break; } @@ -1873,12 +1815,12 @@ CPU_DISASSEMBLE(tlcs900) break; case M_CALL: case M_CALR: - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case M_RET: case M_RETD: case M_RETI: - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; } @@ -1912,7 +1854,7 @@ CPU_DISASSEMBLE(tlcs900) break; case O_CR8: - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); switch( imm ) { case 0x22: @@ -1934,7 +1876,7 @@ CPU_DISASSEMBLE(tlcs900) break; case O_CR16: - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); switch( imm ) { case 0x20: @@ -1956,7 +1898,7 @@ CPU_DISASSEMBLE(tlcs900) break; case O_CR32: - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); switch( imm ) { case 0x00: @@ -1990,13 +1932,13 @@ CPU_DISASSEMBLE(tlcs900) break; case O_D8: - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); util::stream_format(stream, " 0x%06x", ( pc + pos + (int8_t)imm ) & 0xFFFFFF); break; case O_D16: - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); util::stream_format(stream, " 0x%06x", ( pc + pos + (int16_t)imm ) & 0xFFFFFF); break; @@ -2009,28 +1951,28 @@ CPU_DISASSEMBLE(tlcs900) break; case O_I8: - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); util::stream_format(stream, " 0x%02x", imm); break; case O_I16: - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); util::stream_format(stream, " 0x%04x", imm); break; case O_I24: - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); - imm = imm | (oprom[ pos++ ] << 16); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); + imm = imm | (opcodes.r8( pos++ ) << 16); util::stream_format(stream, " 0x%06x", imm); break; case O_I32: - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); - imm = imm | (oprom[ pos++ ] << 16); - imm = imm | (oprom[ pos++ ] << 24); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); + imm = imm | (opcodes.r8( pos++ ) << 16); + imm = imm | (opcodes.r8( pos++ ) << 24); util::stream_format(stream, "0x%08x", imm); break; @@ -2049,13 +1991,13 @@ CPU_DISASSEMBLE(tlcs900) break; case O_M8: - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); util::stream_format(stream, " (0x%02x)", imm); break; case O_M16: - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); util::stream_format(stream, " (0x%04x)", imm); break; @@ -2098,7 +2040,7 @@ CPU_DISASSEMBLE(tlcs900) break; case O_CR8: - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); switch( imm ) { case 0x22: @@ -2120,7 +2062,7 @@ CPU_DISASSEMBLE(tlcs900) break; case O_CR16: - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); switch( imm ) { case 0x20: @@ -2142,7 +2084,7 @@ CPU_DISASSEMBLE(tlcs900) break; case O_CR32: - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); switch( imm ) { case 0x00: @@ -2176,13 +2118,13 @@ CPU_DISASSEMBLE(tlcs900) break; case O_D8: - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); util::stream_format(stream, ",0x%06x", ( pc + pos + (int8_t)imm ) & 0xFFFFFF); break; case O_D16: - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); util::stream_format(stream, ",0x%06x", ( pc + pos + (int16_t)imm ) & 0xFFFFFF); break; @@ -2195,28 +2137,28 @@ CPU_DISASSEMBLE(tlcs900) break; case O_I8: - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); util::stream_format(stream, ",0x%02x", imm); break; case O_I16: - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); util::stream_format(stream, ",0x%04x", imm); break; case O_I24: - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); - imm = imm | (oprom[ pos++ ] << 16); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); + imm = imm | (opcodes.r8( pos++ ) << 16); util::stream_format(stream, ",0x%06x", imm); break; case O_I32: - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); - imm = imm | (oprom[ pos++ ] << 16); - imm = imm | (oprom[ pos++ ] << 24); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); + imm = imm | (opcodes.r8( pos++ ) << 16); + imm = imm | (opcodes.r8( pos++ ) << 24); util::stream_format(stream, ",0x%08x", imm); break; @@ -2235,13 +2177,13 @@ CPU_DISASSEMBLE(tlcs900) break; case O_M8: - imm = oprom[ pos++ ]; + imm = opcodes.r8( pos++ ); util::stream_format(stream, ",(0x%02x)", imm); break; case O_M16: - imm = oprom[ pos++ ]; - imm = imm | (oprom[ pos++ ] << 8); + imm = opcodes.r8( pos++ ); + imm = imm | (opcodes.r8( pos++ ) << 8); util::stream_format(stream, ",(0x%04x)", imm); break; @@ -2254,5 +2196,5 @@ CPU_DISASSEMBLE(tlcs900) break; } - return pos | flags | DASMFLAG_SUPPORTED; + return (pos - pc) | flags | SUPPORTED; } diff --git a/src/devices/cpu/tlcs900/dasm900.h b/src/devices/cpu/tlcs900/dasm900.h new file mode 100644 index 00000000000..8fb067a299a --- /dev/null +++ b/src/devices/cpu/tlcs900/dasm900.h @@ -0,0 +1,111 @@ +// license:BSD-3-Clause +// copyright-holders:Wilbert Pol +/******************************************************************* + +Toshiba TLCS-900/H disassembly + +*******************************************************************/ + +#ifndef MAME_CPU_TLCS900_DASM900_H +#define MAME_CPU_TLCS900_DASM900_H + +#pragma once + +class tlcs900_disassembler : public util::disasm_interface +{ +public: + tlcs900_disassembler() = default; + virtual ~tlcs900_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum e_mnemonics + { + M_ADC, M_ADD, M_AND, M_ANDCF, M_BIT, M_BS1B, + M_BS1F, M_CALL, M_CALR, M_CCF, M_CHG, M_CP, + M_CPD, M_CPDW, M_CPDR, M_CPDRW, M_CPI, M_CPIR, + M_CPIRW, M_CPIW, M_CPL, M_DAA, M_DB, M_DEC, + M_DECF, M_DECW, M_DIV, M_DIVS, M_DJNZ, M_EI, + M_EX, M_EXTS, M_EXTZ, M_HALT, M_INC, M_INCF, + M_INCW, M_JP, M_JR, M_JRL, M_LD, M_LDA, + M_LDC, M_LDCF, M_LDD, M_LDDR, M_LDDRW, M_LDDW, + M_LDF, M_LDI, M_LDIR, M_LDIRW, M_LDIW, M_LDW, + M_LDX, M_LINK, M_MAX, M_MDEC1, M_MDEC2, M_MDEC4, + M_MINC1, M_MINC2, M_MINC4, M_MIRR, M_MUL, M_MULA, + M_MULS, M_NEG, M_NOP, M_NORMAL, M_OR, M_ORCF, + M_PAA, M_POP, M_POPW, M_PUSH, M_PUSHW, M_RCF, + M_RES, M_RET, M_RETD, M_RETI, M_RL, M_RLC, + M_RLCW, M_RLD, M_RLW, M_RR, M_RRC, M_RRCW, + M_RRD, M_RRW, M_SBC, M_SCC, M_SCF, M_SET, + M_SLA, M_SLAW, M_SLL, M_SLLW, M_SRA, M_SRAW, + M_SRL, M_SRLW, M_STCF, M_SUB, M_SWI, M_TSET, + M_UNLK, M_XOR, M_XORCF, M_ZCF, + M_80, M_88, M_90, M_98, M_A0, M_A8, M_B0, M_B8, + M_C0, oC8, M_D0, oD8, M_E0, M_E8, M_F0 + }; + + enum e_operand + { + O_NONE, + O_A, /* current register set register A */ + O_C8, /* current register set byte */ + O_C16, /* current register set word */ + O_C32, /* current register set long word */ + O_MC16, /* current register set mul/div register word */ + O_CC, /* condition */ + O_CR8, /* byte control register */ + O_CR16, /* word control register */ + O_CR32, /* long word control register */ + O_D8, /* byte displacement */ + O_D16, /* word displacement */ + O_F, /* F register */ + O_I3, /* immediate 3 bit (part of last byte) */ + O_I8, /* immediate byte */ + O_I16, /* immediate word */ + O_I24, /* immediate 3 byte address */ + O_I32, /* immediate long word */ + O_M, /* memory location (defined by extension) */ + O_M8, /* (8) */ + O_M16, /* (i16) */ + O_R, /* register */ + O_SR /* status register */ + }; + + struct tlcs900inst + { + e_mnemonics mnemonic; + e_operand operand1; + e_operand operand2; + }; + + static const char *const s_mnemonic[]; + static const tlcs900inst mnemonic_80[256]; + static const tlcs900inst mnemonic_88[256]; + static const tlcs900inst mnemonic_90[256]; + static const tlcs900inst mnemonic_98[256]; + static const tlcs900inst mnemonic_a0[256]; + static const tlcs900inst mnemonic_b0[256]; + static const tlcs900inst mnemonic_b8[256]; + static const tlcs900inst mnemonic_c0[256]; + static const tlcs900inst mnemonic_c8[256]; + static const tlcs900inst mnemonic_d0[256]; + static const tlcs900inst mnemonic_d8[256]; + static const tlcs900inst mnemonic_e0[256]; + static const tlcs900inst mnemonic_e8[256]; + static const tlcs900inst mnemonic_f0[256]; + static const tlcs900inst mnemonic[256]; + + static const char *const s_reg8[8]; + static const char *const s_reg16[8]; + static const char *const s_reg32[8]; + static const char *const s_mulreg16[8]; + static const char *const s_allreg8[256]; + static const char *const s_allreg16[256]; + static const char *const s_allreg32[256]; + static const char *const s_cond[16]; + +}; + +#endif diff --git a/src/devices/cpu/tlcs900/tlcs900.cpp b/src/devices/cpu/tlcs900/tlcs900.cpp index 69eef7121e0..26e1678078d 100644 --- a/src/devices/cpu/tlcs900/tlcs900.cpp +++ b/src/devices/cpu/tlcs900/tlcs900.cpp @@ -17,6 +17,7 @@ TODO: #include "emu.h" #include "tlcs900.h" +#include "dasm900.h" #include "debugger.h" @@ -148,10 +149,9 @@ void tmp95c063_device::device_config_complete() } -offs_t tlcs900h_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *tlcs900h_device::create_disassembler() { - extern CPU_DISASSEMBLE( tlcs900 ); - return CPU_DISASSEMBLE_NAME(tlcs900)(this, stream, pc, oprom, opram, options); + return new tlcs900_disassembler; } diff --git a/src/devices/cpu/tlcs900/tlcs900.h b/src/devices/cpu/tlcs900/tlcs900.h index 28552bd3c17..0fbedad0f23 100644 --- a/src/devices/cpu/tlcs900/tlcs900.h +++ b/src/devices/cpu/tlcs900/tlcs900.h @@ -72,9 +72,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 7; } /* FIXME */ - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; protected: int m_am8_16; diff --git a/src/devices/cpu/tms1000/tms0980.cpp b/src/devices/cpu/tms1000/tms0980.cpp index 3059ff7b1d1..e0c36ce7b4e 100644 --- a/src/devices/cpu/tms1000/tms0980.cpp +++ b/src/devices/cpu/tms1000/tms0980.cpp @@ -8,6 +8,7 @@ #include "emu.h" #include "tms0980.h" +#include "tms1k_dasm.h" #include "debugger.h" // TMS0980 @@ -31,7 +32,7 @@ DEFINE_DEVICE_TYPE(TMS1980, tms1980_cpu_device, "tms1980", "TMS1980") // 28-pin // internal memory maps static ADDRESS_MAP_START(program_11bit_9, AS_PROGRAM, 16, tms1k_base_device) - AM_RANGE(0x000, 0xfff) AM_ROM + AM_RANGE(0x000, 0x7ff) AM_ROM ADDRESS_MAP_END static ADDRESS_MAP_START(data_144x4, AS_DATA, 8, tms1k_base_device) @@ -84,10 +85,9 @@ MACHINE_CONFIG_END // disasm -offs_t tms0980_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +util::disasm_interface *tms0980_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE(tms0980); - return CPU_DISASSEMBLE_NAME(tms0980)(this, stream, pc, oprom, opram, options); + return new tms0980_disassembler; } diff --git a/src/devices/cpu/tms1000/tms0980.h b/src/devices/cpu/tms1000/tms0980.h index c258eadc12b..2a4fa810008 100644 --- a/src/devices/cpu/tms1000/tms0980.h +++ b/src/devices/cpu/tms1000/tms0980.h @@ -29,9 +29,7 @@ protected: virtual void device_add_mconfig(machine_config &config) override; - virtual u32 disasm_min_opcode_bytes() const override { return 2; } - virtual u32 disasm_max_opcode_bytes() const override { return 2; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; virtual u8 read_k_input() override; virtual void set_cki_bus() override; diff --git a/src/devices/cpu/tms1000/tms1000.cpp b/src/devices/cpu/tms1000/tms1000.cpp index 55ac2a01d8c..5aa2ecf8272 100644 --- a/src/devices/cpu/tms1000/tms1000.cpp +++ b/src/devices/cpu/tms1000/tms1000.cpp @@ -13,6 +13,7 @@ #include "emu.h" #include "tms1000.h" +#include "tms1k_dasm.h" #include "debugger.h" // TMS1000 @@ -112,10 +113,9 @@ mc141200_cpu_device::mc141200_cpu_device(const machine_config &mconfig, const ch MACHINE_CONFIG_END // disasm -offs_t tms1000_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +util::disasm_interface *tms1000_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE(tms1000); - return CPU_DISASSEMBLE_NAME(tms1000)(this, stream, pc, oprom, opram, options); + return new tms1000_disassembler; } diff --git a/src/devices/cpu/tms1000/tms1000.h b/src/devices/cpu/tms1000/tms1000.h index ae85b7ed579..8db0fd6f64e 100644 --- a/src/devices/cpu/tms1000/tms1000.h +++ b/src/devices/cpu/tms1000/tms1000.h @@ -26,8 +26,7 @@ protected: virtual void device_reset() override; virtual void device_add_mconfig(machine_config &config) override; - - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; }; class tms1070_cpu_device : public tms1000_cpu_device diff --git a/src/devices/cpu/tms1000/tms1100.cpp b/src/devices/cpu/tms1000/tms1100.cpp index a67f1261512..70c38bc72c1 100644 --- a/src/devices/cpu/tms1000/tms1100.cpp +++ b/src/devices/cpu/tms1000/tms1100.cpp @@ -8,6 +8,7 @@ #include "emu.h" #include "tms1100.h" +#include "tms1k_dasm.h" #include "debugger.h" // TMS1100 is nearly the same as TMS1000, some different opcodes, and with double the RAM and ROM @@ -55,13 +56,11 @@ tms1370_cpu_device::tms1370_cpu_device(const machine_config &mconfig, const char // disasm -offs_t tms1100_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +util::disasm_interface *tms1100_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE(tms1100); - return CPU_DISASSEMBLE_NAME(tms1100)(this, stream, pc, oprom, opram, options); + return new tms1100_disassembler; } - // device_reset void tms1100_cpu_device::device_reset() { diff --git a/src/devices/cpu/tms1000/tms1100.h b/src/devices/cpu/tms1000/tms1100.h index 26a3ffbc578..86a0028a3aa 100644 --- a/src/devices/cpu/tms1000/tms1100.h +++ b/src/devices/cpu/tms1000/tms1100.h @@ -25,7 +25,7 @@ protected: // overrides virtual void device_reset() override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void op_setr() override; virtual void op_rstr() override; diff --git a/src/devices/cpu/tms1000/tms1k_base.cpp b/src/devices/cpu/tms1000/tms1k_base.cpp index 985784570e8..6e4fe14a93c 100644 --- a/src/devices/cpu/tms1000/tms1k_base.cpp +++ b/src/devices/cpu/tms1000/tms1k_base.cpp @@ -72,7 +72,7 @@ unknown cycle: CME, SSE, SSS tms1k_base_device::tms1k_base_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, u32 clock, u8 o_pins, u8 r_pins, u8 pc_bits, u8 byte_bits, u8 x_bits, int prgwidth, address_map_constructor program, int datawidth, address_map_constructor data) : cpu_device(mconfig, type, tag, owner, clock) - , m_program_config("program", ENDIANNESS_BIG, byte_bits > 8 ? 16 : 8, prgwidth, 0, program) + , m_program_config("program", ENDIANNESS_BIG, byte_bits > 8 ? 16 : 8, prgwidth, byte_bits > 8 ? -1 : 0, program) , m_data_config("data", ENDIANNESS_BIG, 8, datawidth, 0, data) , m_mpla(*this, "mpla") , m_ipla(*this, "ipla") diff --git a/src/devices/cpu/tms1000/tms1k_base.h b/src/devices/cpu/tms1000/tms1k_base.h index b8cd7e2a589..4fb9f353178 100644 --- a/src/devices/cpu/tms1000/tms1k_base.h +++ b/src/devices/cpu/tms1000/tms1k_base.h @@ -168,10 +168,6 @@ protected: // device_memory_interface overrides virtual space_config_vector memory_space_config() const override; - // device_disasm_interface overrides - virtual u32 disasm_min_opcode_bytes() const override { return 1; } - virtual u32 disasm_max_opcode_bytes() const override { return 1; } - // device_state_interface overrides virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; diff --git a/src/devices/cpu/tms1000/tms1k_dasm.cpp b/src/devices/cpu/tms1000/tms1k_dasm.cpp index f0afd660470..36d275b330b 100644 --- a/src/devices/cpu/tms1000/tms1k_dasm.cpp +++ b/src/devices/cpu/tms1000/tms1k_dasm.cpp @@ -7,23 +7,9 @@ */ #include "emu.h" -#include "debugger.h" -#include "tms1k_base.h" +#include "tms1k_dasm.h" - -enum e_mnemonics -{ - zILL = 0, - zA10AAC, zA6AAC, zA8AAC, zAC1AC, zACACC, zACNAA, zALEC, zALEM, zAMAAC, zBRANCH, zCALL, zCCLA, - zCLA, zCLO, zCOMC, zCOMX, zCOMX8, zCPAIZ, zCTMDYN, zDAN, zDMAN, zDMEA, zDNAA, - zDYN, zIA, zIMAC, zIYC, zKNEZ, zLDP, zLDX2, zLDX3, zLDX4, zMNEA, zMNEZ, - zNDMEA, zOFF, zRBIT, zREAC, zRETN, zRSTR, zSAL, zSAMAN, zSBIT, - zSBL, zSEAC, zSETR, zTAM, zTAMACS, zTAMDYN, zTAMIY, zTAMIYC, zTAMZA, - zTAY, zTBIT, zTCMIY, zTCY, zTDO, zTKA, zTKM, zTMA, - zTMY, zTYA, zXDA, zXMA, zYMCY, zYNEA, zYNEC -}; - -static const char *const s_mnemonic[] = +const char *const tms1000_base_disassembler::s_mnemonic[] = { "?", "A10AAC", "A6AAC", "A8AAC", "AC1AC", "ACACC", "ACNAA", "ALEC", "ALEM", "AMAAC", "BRANCH", "CALL", "CCLA", @@ -35,29 +21,19 @@ static const char *const s_mnemonic[] = "TMY", "TYA", "XDA", "XMA", "YMCY", "YNEA", "YNEC" }; - -#define _OVER DASMFLAG_STEP_OVER -#define _OUT DASMFLAG_STEP_OUT - -static const u32 s_flags[] = +const u32 tms1000_base_disassembler::s_flags[] = { 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, _OVER, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, STEP_OVER, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, _OUT, 0, 0, 0, 0, + 0, 0, 0, 0, STEP_OUT, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; - -enum e_addressing -{ - zB0 = 0, zI2, zI3, zI4, zB7 -}; - -static const u8 s_addressing[] = +const u8 tms1000_base_disassembler::s_addressing[] = { zB0, zB0, zB0, zB0, zI4, zI4, zI4, zI4, zB0, zB0, zB7, zB7, zB0, @@ -73,7 +49,7 @@ static const u8 s_addressing[] = // opcode luts -static const u8 tms1000_mnemonic[256] = +const u8 tms1000_disassembler::tms1000_mnemonic[256] = { /* 0x00 */ zCOMX, zA8AAC, zYNEA, zTAM, zTAMZA, zA10AAC, zA6AAC, zDAN, zTKA, zKNEZ, zTDO, zCLO, zRSTR, zSETR, zIA, zRETN, // 0 @@ -97,7 +73,7 @@ static const u8 tms1000_mnemonic[256] = }; -static const u8 tms1100_mnemonic[256] = +const u8 tms1100_disassembler::tms1100_mnemonic[256] = { /* 0x00 */ zMNEA, zALEM, zYNEA, zXMA, zDYN, zIYC, zAMAAC, zDMAN, zTKA, zCOMX, zTDO, zCOMC, zRSTR, zSETR, zKNEZ, zRETN, // 0 @@ -121,7 +97,7 @@ static const u8 tms1100_mnemonic[256] = }; -static const u8 tms0980_mnemonic[512] = +const u8 tms0980_disassembler::tms0980_mnemonic[512] = { /* 0x000 */ zCOMX, zALEM, zYNEA, zXMA, zDYN, zIYC, zCLA, zDMAN, zTKA, zMNEA, zTKM, 0, 0, zSETR, zKNEZ, 0, // 0 @@ -163,7 +139,7 @@ static const u8 tms0980_mnemonic[512] = }; -static const u8 tp0320_mnemonic[512] = +const u8 tp0320_disassembler::tp0320_mnemonic[512] = { /* 0x000 */ 0, zALEM, zYNEA, zXMA, zDYN, zIYC, zCLA, zDMAN, zTKA, zMNEA, zTKM, 0, 0, zSETR, zKNEZ, 0, // 0 @@ -208,31 +184,27 @@ static const u8 tp0320_mnemonic[512] = // disasm -static const u8 i2_value[4] = +const u8 tms1000_base_disassembler::i2_value[4] = { 0, 2, 1, 3 }; -static const u8 i3_value[8] = +const u8 tms1000_base_disassembler::i3_value[8] = { 0, 4, 2, 6, 1, 5, 3, 7 }; -static const u8 i4_value[16] = +const u8 tms1000_base_disassembler::i4_value[16] = { 0x0, 0x8, 0x4, 0xc, 0x2, 0xa, 0x6, 0xe, 0x1, 0x9, 0x5, 0xd, 0x3, 0xb, 0x7, 0xf }; -static offs_t tms1k_dasm(std::ostream &stream, const u8 *oprom, const u8 *lut_mnemonic, u16 opcode_mask) +offs_t tms1000_base_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - // get current opcode - int pos = 0; - u16 op = oprom[pos++]; - if (opcode_mask & 0x100) - op = (op << 8 | oprom[pos++]) & 0x1ff; + u16 op = m_opcode_9bits ? opcodes.r16(pc) & 0x1ff : opcodes.r8(pc); // convert to mnemonic/param - u16 instr = lut_mnemonic[op]; + u16 instr = m_lut_mnemonic[op]; util::stream_format(stream, "%-8s ", s_mnemonic[instr]); switch( s_addressing[instr] ) @@ -247,7 +219,7 @@ static offs_t tms1k_dasm(std::ostream &stream, const u8 *oprom, const u8 *lut_mn util::stream_format(stream, "%d", i4_value[op & 0x0f]); break; case zB7: - if (opcode_mask & 0x100) + if (m_opcode_9bits) util::stream_format(stream, "$%02X", op << 1 & 0xfe); else util::stream_format(stream, "$%02X", op & 0x3f); @@ -256,26 +228,104 @@ static offs_t tms1k_dasm(std::ostream &stream, const u8 *oprom, const u8 *lut_mn break; } - return pos | s_flags[instr] | DASMFLAG_SUPPORTED; + return 1 | s_flags[instr] | SUPPORTED; } +tms1000_disassembler::tms1000_disassembler() : tms1000_base_disassembler(tms1000_mnemonic, false, 6) +{ +} + +tms1100_disassembler::tms1100_disassembler() : tms1000_base_disassembler(tms1100_mnemonic, false, 6) +{ +} -CPU_DISASSEMBLE(tms1000) +tms0980_disassembler::tms0980_disassembler() : tms1000_base_disassembler(tms0980_mnemonic, true, 7) { - return tms1k_dasm(stream, oprom, tms1000_mnemonic, 0xff); } -CPU_DISASSEMBLE(tms1100) +tp0320_disassembler::tp0320_disassembler() : tms1000_base_disassembler(tp0320_mnemonic, true, 7) { - return tms1k_dasm(stream, oprom, tms1100_mnemonic, 0xff); } -CPU_DISASSEMBLE(tms0980) +tms1000_base_disassembler::tms1000_base_disassembler(const u8 *lut_mnemonic, bool opcode_9bits, int pc_bits) : m_lut_mnemonic(lut_mnemonic), m_opcode_9bits(opcode_9bits), m_pc_bits(pc_bits) { - return tms1k_dasm(stream, oprom, tms0980_mnemonic, 0x1ff); } -CPU_DISASSEMBLE(tp0320) +u32 tms1000_base_disassembler::opcode_alignment() const { - return tms1k_dasm(stream, oprom, tp0320_mnemonic, 0x1ff); + return 1; } + +u32 tms1000_base_disassembler::interface_flags() const +{ + return NONLINEAR_PC | PAGED2LEVEL; +} + +u32 tms1000_base_disassembler::page_address_bits() const +{ + return m_pc_bits; +} + +u32 tms1000_base_disassembler::page2_address_bits() const +{ + return 4; +} + +offs_t tms1000_base_disassembler::pc_linear_to_real(offs_t pc) const +{ + switch(m_pc_bits) { + case 6: { + static const u8 l2r6[64] = { + 0x00, 0x01, 0x03, 0x07, 0x0f, 0x1f, 0x3f, 0x3e, 0x3d, 0x3b, 0x37, 0x2f, 0x1e, 0x3c, 0x39, 0x33, + 0x27, 0x0e, 0x1d, 0x3a, 0x35, 0x2b, 0x16, 0x2c, 0x18, 0x30, 0x21, 0x02, 0x05, 0x0b, 0x17, 0x2e, + 0x1c, 0x38, 0x31, 0x23, 0x06, 0x0d, 0x1b, 0x36, 0x2d, 0x1a, 0x34, 0x29, 0x12, 0x24, 0x08, 0x11, + 0x22, 0x04, 0x09, 0x13, 0x26, 0x0c, 0x19, 0x32, 0x25, 0x0a, 0x15, 0x2a, 0x14, 0x28, 0x10, 0x20, + }; + return (pc & ~0x3f) | l2r6[pc & 0x3f]; + } + case 7: { + static const u8 l2r7[128] = { + 0x00, 0x01, 0x03, 0x07, 0x0f, 0x1f, 0x3f, 0x7f, 0x7e, 0x7d, 0x7b, 0x77, 0x6f, 0x5f, 0x3e, 0x7c, + 0x79, 0x73, 0x67, 0x4f, 0x1e, 0x3d, 0x7a, 0x75, 0x6b, 0x57, 0x2e, 0x5c, 0x38, 0x70, 0x61, 0x43, + 0x06, 0x0d, 0x1b, 0x37, 0x6e, 0x5d, 0x3a, 0x74, 0x69, 0x53, 0x26, 0x4c, 0x18, 0x31, 0x62, 0x45, + 0x0a, 0x15, 0x2b, 0x56, 0x2c, 0x58, 0x30, 0x60, 0x41, 0x02, 0x05, 0x0b, 0x17, 0x2f, 0x5e, 0x3c, + 0x78, 0x71, 0x63, 0x47, 0x0e, 0x1d, 0x3b, 0x76, 0x6d, 0x5b, 0x36, 0x6c, 0x59, 0x32, 0x64, 0x49, + 0x12, 0x25, 0x4a, 0x14, 0x29, 0x52, 0x24, 0x48, 0x10, 0x21, 0x42, 0x04, 0x09, 0x13, 0x27, 0x4e, + 0x1c, 0x39, 0x72, 0x65, 0x4b, 0x16, 0x2d, 0x5a, 0x34, 0x68, 0x51, 0x22, 0x44, 0x08, 0x11, 0x23, + 0x46, 0x0c, 0x19, 0x33, 0x66, 0x4d, 0x1a, 0x35, 0x6a, 0x55, 0x2a, 0x54, 0x28, 0x50, 0x20, 0x40, + }; + return (pc & ~0x7f) | l2r7[pc & 0x7f]; + } + } + return 0; +} + +offs_t tms1000_base_disassembler::pc_real_to_linear(offs_t pc) const +{ + switch(m_pc_bits) { + case 6: { + static const u8 r2l6[64] = { + 0x00, 0x01, 0x1b, 0x02, 0x31, 0x1c, 0x24, 0x03, 0x2e, 0x32, 0x39, 0x1d, 0x35, 0x25, 0x11, 0x04, + 0x3e, 0x2f, 0x2c, 0x33, 0x3c, 0x3a, 0x16, 0x1e, 0x18, 0x36, 0x29, 0x26, 0x20, 0x12, 0x0c, 0x05, + 0x3f, 0x1a, 0x30, 0x23, 0x2d, 0x38, 0x34, 0x10, 0x3d, 0x2b, 0x3b, 0x15, 0x17, 0x28, 0x1f, 0x0b, + 0x19, 0x22, 0x37, 0x0f, 0x2a, 0x14, 0x27, 0x0a, 0x21, 0x0e, 0x13, 0x09, 0x0d, 0x08, 0x07, 0x06, + }; + return (pc & ~0x3f) | r2l6[pc & 0x3f]; + } + case 7: { + static const u8 r2l7[128] = { + 0x00, 0x01, 0x39, 0x02, 0x5b, 0x3a, 0x20, 0x03, 0x6d, 0x5c, 0x30, 0x3b, 0x71, 0x21, 0x44, 0x04, + 0x58, 0x6e, 0x50, 0x5d, 0x53, 0x31, 0x65, 0x3c, 0x2c, 0x72, 0x76, 0x22, 0x60, 0x45, 0x14, 0x05, + 0x7e, 0x59, 0x6b, 0x6f, 0x56, 0x51, 0x2a, 0x5e, 0x7c, 0x54, 0x7a, 0x32, 0x34, 0x66, 0x1a, 0x3d, + 0x36, 0x2d, 0x4d, 0x73, 0x68, 0x77, 0x4a, 0x23, 0x1c, 0x61, 0x26, 0x46, 0x3f, 0x15, 0x0e, 0x06, + 0x7f, 0x38, 0x5a, 0x1f, 0x6c, 0x2f, 0x70, 0x43, 0x57, 0x4f, 0x52, 0x64, 0x2b, 0x75, 0x5f, 0x13, + 0x7d, 0x6a, 0x55, 0x29, 0x7b, 0x79, 0x33, 0x19, 0x35, 0x4c, 0x67, 0x49, 0x1b, 0x25, 0x3e, 0x0d, + 0x37, 0x1e, 0x2e, 0x42, 0x4e, 0x63, 0x74, 0x12, 0x69, 0x28, 0x78, 0x18, 0x4b, 0x48, 0x24, 0x0c, + 0x1d, 0x41, 0x62, 0x11, 0x27, 0x17, 0x47, 0x0b, 0x40, 0x10, 0x16, 0x0a, 0x0f, 0x09, 0x08, 0x07, + }; + return (pc & ~0x7f) | r2l7[pc & 0x7f]; + } + } + return 0; +} + diff --git a/src/devices/cpu/tms1000/tms1k_dasm.h b/src/devices/cpu/tms1000/tms1k_dasm.h new file mode 100644 index 00000000000..8ffad64272a --- /dev/null +++ b/src/devices/cpu/tms1000/tms1k_dasm.h @@ -0,0 +1,98 @@ +// license:BSD-3-Clause +// copyright-holders:Wilbert Pol, hap +/* + + TMS0980/TMS1000-family disassembler + +*/ + +#ifndef MAME_CPU_TMS1000_TMS1K_DASM_H +#define MAME_CPU_TMS1000_TMS1K_DASM_H + +#pragma once + +class tms1000_base_disassembler : public util::disasm_interface +{ +public: + tms1000_base_disassembler(const u8 *lut_mnemonic, bool opcode_9bits, int pc_bits); + virtual ~tms1000_base_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual u32 interface_flags() const override; + virtual u32 page_address_bits() const override; + virtual u32 page2_address_bits() const override; + virtual offs_t pc_linear_to_real(offs_t pc) const override; + virtual offs_t pc_real_to_linear(offs_t pc) const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +protected: + enum e_mnemonics + { + zILL = 0, + zA10AAC, zA6AAC, zA8AAC, zAC1AC, zACACC, zACNAA, zALEC, zALEM, zAMAAC, zBRANCH, zCALL, zCCLA, + zCLA, zCLO, zCOMC, zCOMX, zCOMX8, zCPAIZ, zCTMDYN, zDAN, zDMAN, zDMEA, zDNAA, + zDYN, zIA, zIMAC, zIYC, zKNEZ, zLDP, zLDX2, zLDX3, zLDX4, zMNEA, zMNEZ, + zNDMEA, zOFF, zRBIT, zREAC, zRETN, zRSTR, zSAL, zSAMAN, zSBIT, + zSBL, zSEAC, zSETR, zTAM, zTAMACS, zTAMDYN, zTAMIY, zTAMIYC, zTAMZA, + zTAY, zTBIT, zTCMIY, zTCY, zTDO, zTKA, zTKM, zTMA, + zTMY, zTYA, zXDA, zXMA, zYMCY, zYNEA, zYNEC + }; + + enum e_addressing + { + zB0 = 0, zI2, zI3, zI4, zB7 + }; + + static const char *const s_mnemonic[]; + static const u32 s_flags[]; + static const u8 s_addressing[]; + static const u8 i2_value[4]; + static const u8 i3_value[8]; + static const u8 i4_value[16]; + + const u8 *m_lut_mnemonic; + bool m_opcode_9bits; + int m_pc_bits; +}; + +class tms1000_disassembler : public tms1000_base_disassembler +{ +public: + tms1000_disassembler(); + virtual ~tms1000_disassembler() = default; + +protected: + static const u8 tms1000_mnemonic[256]; +}; + +class tms1100_disassembler : public tms1000_base_disassembler +{ +public: + tms1100_disassembler(); + virtual ~tms1100_disassembler() = default; + +protected: + static const u8 tms1100_mnemonic[256]; +}; + +class tms0980_disassembler : public tms1000_base_disassembler +{ +public: + tms0980_disassembler(); + virtual ~tms0980_disassembler() = default; + +protected: + static const u8 tms0980_mnemonic[512]; +}; + +class tp0320_disassembler : public tms1000_base_disassembler +{ +public: + tp0320_disassembler(); + virtual ~tp0320_disassembler() = default; + +protected: + static const u8 tp0320_mnemonic[512]; +}; + +#endif diff --git a/src/devices/cpu/tms1000/tp0320.cpp b/src/devices/cpu/tms1000/tp0320.cpp index 02e961f6473..65487b9871a 100644 --- a/src/devices/cpu/tms1000/tp0320.cpp +++ b/src/devices/cpu/tms1000/tp0320.cpp @@ -11,6 +11,7 @@ #include "emu.h" #include "tp0320.h" +#include "tms1k_dasm.h" #include "debugger.h" // TP0320 is TI's first CMOS MCU with integrated LCD controller, the die is still very similar to TMS0980 @@ -55,10 +56,9 @@ MACHINE_CONFIG_END // disasm -offs_t tp0320_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +util::disasm_interface *tp0320_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE(tp0320); - return CPU_DISASSEMBLE_NAME(tp0320)(this, stream, pc, oprom, opram, options); + return new tp0320_disassembler; } diff --git a/src/devices/cpu/tms1000/tp0320.h b/src/devices/cpu/tms1000/tp0320.h index e740ae83320..9b23155f1c4 100644 --- a/src/devices/cpu/tms1000/tp0320.h +++ b/src/devices/cpu/tms1000/tp0320.h @@ -26,7 +26,7 @@ protected: virtual u32 decode_fixed(u16 op) override { return 0; } // not yet virtual u32 decode_micro(u8 sel) override; virtual void device_reset() override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void device_add_mconfig(machine_config &config) override; }; diff --git a/src/devices/cpu/tms32010/32010dsm.cpp b/src/devices/cpu/tms32010/32010dsm.cpp index 040a24b11b6..9dcbb1df485 100644 --- a/src/devices/cpu/tms32010/32010dsm.cpp +++ b/src/devices/cpu/tms32010/32010dsm.cpp @@ -25,153 +25,130 @@ \**************************************************************************/ #include "emu.h" -#include "debugger.h" +#include "32010dsm.h" #include -#include "tms32010.h" +const char *const tms32010_disassembler::arith[4] = { "*" , "*-" , "*+" , "??" } ; +const char *const tms32010_disassembler::nextar[4] = { ",AR0" , ",AR1" , "" , "" } ; - -typedef unsigned char byte; -typedef unsigned short int word; - -#define FMT(a,b) a, b -#define PTRS_PER_FORMAT 2 - -static const char *const arith[4] = { "*" , "*-" , "*+" , "??" } ; -static const char *const nextar[4] = { ",AR0" , ",AR1" , "" , "" } ; - - -static const char *const TMS32010Formats[] = { - FMT("0000ssss0aaaaaaa", "add %A%S"), - FMT("0000ssss10mmn00n", "add %M%S%N"), - FMT("0001ssss0aaaaaaa", "sub %A%S"), - FMT("0001ssss10mmn00n", "sub %M%S%N"), - FMT("0010ssss0aaaaaaa", "lac %A%S"), - FMT("0010ssss10mmn00n", "lac %M%S%N"), - FMT("0011000r0aaaaaaa", "sar %R,%A"), - FMT("0011000r10mmn00n", "sar %R%M%N"), - FMT("0011100r0aaaaaaa", "lar %R,%A"), - FMT("0011100r10mmn00n", "lar %R%M%N"), - FMT("01000ppp0aaaaaaa", "in %A,%P"), - FMT("01000ppp10mmn00n", "in %M,%P%N"), - FMT("01001ppp0aaaaaaa", "out %A,%P"), - FMT("01001ppp10mmn00n", "out %M,%P%N"), - FMT("01010sss0aaaaaaa", "sacl %A"), /* This instruction has a shift but */ - FMT("01010sss10mmn00n", "sacl %M%N"), /* is documented as not performed */ - FMT("01011sss0aaaaaaa", "sach %A%S"), - FMT("01011sss10mmn00n", "sach %M%S%N"), - FMT("011000000aaaaaaa", "addh %A"), - FMT("0110000010mmn00n", "addh %M%N"), - FMT("011000010aaaaaaa", "adds %A"), - FMT("0110000110mmn00n", "adds %M%N"), - FMT("011000100aaaaaaa", "subh %A"), - FMT("0110001010mmn00n", "subh %M%N"), - FMT("011000110aaaaaaa", "subs %A"), - FMT("0110001110mmn00n", "subs %M%N"), - FMT("011001000aaaaaaa", "subc %A"), - FMT("0110010010mmn00n", "subc %M%N"), - FMT("011001010aaaaaaa", "zalh %A"), - FMT("0110010110mmn00n", "zalh %M%N"), - FMT("011001100aaaaaaa", "zals %A"), - FMT("0110011010mmn00n", "zals %M%N"), - FMT("011001110aaaaaaa", "tblr %A"), - FMT("0110011110mmn00n", "tblr %M%N"), - FMT("011010001000000k", "larp %K"), - FMT("011010000aaaaaaa", "mar %A"), /* Actually this is executed as a NOP */ -/* FMT("0110100010mmn00n", "mar %M%N"), */ +const char *const tms32010_disassembler::TMS32010Formats[] = { + "0000ssss0aaaaaaa", "add %A%S", + "0000ssss10mmn00n", "add %M%S%N", + "0001ssss0aaaaaaa", "sub %A%S", + "0001ssss10mmn00n", "sub %M%S%N", + "0010ssss0aaaaaaa", "lac %A%S", + "0010ssss10mmn00n", "lac %M%S%N", + "0011000r0aaaaaaa", "sar %R,%A", + "0011000r10mmn00n", "sar %R%M%N", + "0011100r0aaaaaaa", "lar %R,%A", + "0011100r10mmn00n", "lar %R%M%N", + "01000ppp0aaaaaaa", "in %A,%P", + "01000ppp10mmn00n", "in %M,%P%N", + "01001ppp0aaaaaaa", "out %A,%P", + "01001ppp10mmn00n", "out %M,%P%N", + "01010sss0aaaaaaa", "sacl %A", /* This instruction has a shift but */ + "01010sss10mmn00n", "sacl %M%N", /* is documented as not performed */ + "01011sss0aaaaaaa", "sach %A%S", + "01011sss10mmn00n", "sach %M%S%N", + "011000000aaaaaaa", "addh %A", + "0110000010mmn00n", "addh %M%N", + "011000010aaaaaaa", "adds %A", + "0110000110mmn00n", "adds %M%N", + "011000100aaaaaaa", "subh %A", + "0110001010mmn00n", "subh %M%N", + "011000110aaaaaaa", "subs %A", + "0110001110mmn00n", "subs %M%N", + "011001000aaaaaaa", "subc %A", + "0110010010mmn00n", "subc %M%N", + "011001010aaaaaaa", "zalh %A", + "0110010110mmn00n", "zalh %M%N", + "011001100aaaaaaa", "zals %A", + "0110011010mmn00n", "zals %M%N", + "011001110aaaaaaa", "tblr %A", + "0110011110mmn00n", "tblr %M%N", + "011010001000000k", "larp %K", + "011010000aaaaaaa", "mar %A", /* Actually this is executed as a NOP */ +/* "0110100010mmn00n", "mar %M%N", */ /* MAR indirect has been expanded out to all its variations because one of */ /* its opcodes is the same as LARP (actually performs the same function) */ - FMT("0110100010001000", "mar *"), - FMT("0110100010001001", "mar *"), - FMT("0110100010010000", "mar *-,AR0"), - FMT("0110100010010001", "mar *-,AR1"), - FMT("0110100010011000", "mar *-"), - FMT("0110100010011001", "mar *-"), - FMT("0110100010100000", "mar *+,AR0"), - FMT("0110100010100001", "mar *+,AR1"), - FMT("0110100010101000", "mar *+"), - FMT("0110100010101001", "mar *+"), - FMT("0110100010110000", "mar ??,AR0"), - FMT("0110100010110001", "mar ??,AR1"), - FMT("0110100010111000", "mar ??"), - FMT("0110100010111001", "mar ??"), + "0110100010001000", "mar *", + "0110100010001001", "mar *", + "0110100010010000", "mar *-,AR0", + "0110100010010001", "mar *-,AR1", + "0110100010011000", "mar *-", + "0110100010011001", "mar *-", + "0110100010100000", "mar *+,AR0", + "0110100010100001", "mar *+,AR1", + "0110100010101000", "mar *+", + "0110100010101001", "mar *+", + "0110100010110000", "mar ??,AR0", + "0110100010110001", "mar ??,AR1", + "0110100010111000", "mar ??", + "0110100010111001", "mar ??", - FMT("011010010aaaaaaa", "dmov %A"), - FMT("0110100110mmn00n", "dmov %M%N"), - FMT("011010100aaaaaaa", "lt %A"), - FMT("0110101010mmn00n", "lt %M%N"), - FMT("011010110aaaaaaa", "ltd %A"), - FMT("0110101110mmn00n", "ltd %M%N"), - FMT("011011000aaaaaaa", "lta %A"), - FMT("0110110010mmn00n", "lta %M%N"), - FMT("011011010aaaaaaa", "mpy %A"), - FMT("0110110110mmn00n", "mpy %M%N"), - FMT("011011100000000k", "ldpk %K"), - FMT("011011110aaaaaaa", "ldp %A"), - FMT("0110111110mmn00n", "ldp %M%N"), - FMT("0111000rdddddddd", "lark %R,%D"), - FMT("011110000aaaaaaa", "xor %A"), - FMT("0111100010mmn00n", "xor %M%N"), - FMT("011110010aaaaaaa", "and %A"), - FMT("0111100110mmn00n", "and %M%N"), - FMT("011110100aaaaaaa", "or %A"), - FMT("0111101010mmn00n", "or %M%N"), - FMT("011110110aaaaaaa", "lst %A"), - FMT("0111101110mmn00n", "lst %M%N"), - FMT("011111000aaaaaaa", "sst %A"), - FMT("0111110010mmn00n", "sst %M%N"), - FMT("011111010aaaaaaa", "tblw %A"), - FMT("0111110110mmn00n", "tblw %M%N"), - FMT("01111110dddddddd", "lack %D"), - FMT("0111111110000000", "nop"), /* 7F80 */ - FMT("0111111110000001", "dint"), - FMT("0111111110000010", "eint"), - FMT("0111111110001000", "abs"), /* 7F88 */ - FMT("0111111110001001", "zac"), - FMT("0111111110001010", "rovm"), - FMT("0111111110001011", "sovm"), - FMT("0111111110001100", "cala"), - FMT("0111111110001101", "ret"), - FMT("0111111110001110", "pac"), - FMT("0111111110001111", "apac"), - FMT("0111111110010000", "spac"), - FMT("0111111110011100", "push"), - FMT("0111111110011101", "pop"), /* 7F9D */ - FMT("100wwwwwwwwwwwww", "mpyk %W"), - FMT("1111010000000000bbbbbbbbbbbbbbbb", "banz %B"), - FMT("1111010100000000bbbbbbbbbbbbbbbb", "bv %B"), - FMT("1111011000000000bbbbbbbbbbbbbbbb", "bioz %B"), - FMT("1111100000000000bbbbbbbbbbbbbbbb", "call %B"), - FMT("1111100100000000bbbbbbbbbbbbbbbb", "b %B"), - FMT("1111101000000000bbbbbbbbbbbbbbbb", "blz %B"), - FMT("1111101100000000bbbbbbbbbbbbbbbb", "blez %B"), - FMT("1111110000000000bbbbbbbbbbbbbbbb", "bgz %B"), - FMT("1111110100000000bbbbbbbbbbbbbbbb", "bgez %B"), - FMT("1111111000000000bbbbbbbbbbbbbbbb", "bnz %B"), - FMT("1111111100000000bbbbbbbbbbbbbbbb", "bz %B"), + "011010010aaaaaaa", "dmov %A", + "0110100110mmn00n", "dmov %M%N", + "011010100aaaaaaa", "lt %A", + "0110101010mmn00n", "lt %M%N", + "011010110aaaaaaa", "ltd %A", + "0110101110mmn00n", "ltd %M%N", + "011011000aaaaaaa", "lta %A", + "0110110010mmn00n", "lta %M%N", + "011011010aaaaaaa", "mpy %A", + "0110110110mmn00n", "mpy %M%N", + "011011100000000k", "ldpk %K", + "011011110aaaaaaa", "ldp %A", + "0110111110mmn00n", "ldp %M%N", + "0111000rdddddddd", "lark %R,%D", + "011110000aaaaaaa", "xor %A", + "0111100010mmn00n", "xor %M%N", + "011110010aaaaaaa", "and %A", + "0111100110mmn00n", "and %M%N", + "011110100aaaaaaa", "or %A", + "0111101010mmn00n", "or %M%N", + "011110110aaaaaaa", "lst %A", + "0111101110mmn00n", "lst %M%N", + "011111000aaaaaaa", "sst %A", + "0111110010mmn00n", "sst %M%N", + "011111010aaaaaaa", "tblw %A", + "0111110110mmn00n", "tblw %M%N", + "01111110dddddddd", "lack %D", + "0111111110000000", "nop", /* 7F80 */ + "0111111110000001", "dint", + "0111111110000010", "eint", + "0111111110001000", "abs", /* 7F88 */ + "0111111110001001", "zac", + "0111111110001010", "rovm", + "0111111110001011", "sovm", + "0111111110001100", "cala", + "0111111110001101", "ret", + "0111111110001110", "pac", + "0111111110001111", "apac", + "0111111110010000", "spac", + "0111111110011100", "push", + "0111111110011101", "pop", /* 7F9D */ + "100wwwwwwwwwwwww", "mpyk %W", + "1111010000000000bbbbbbbbbbbbbbbb", "banz %B", + "1111010100000000bbbbbbbbbbbbbbbb", "bv %B", + "1111011000000000bbbbbbbbbbbbbbbb", "bioz %B", + "1111100000000000bbbbbbbbbbbbbbbb", "call %B", + "1111100100000000bbbbbbbbbbbbbbbb", "b %B", + "1111101000000000bbbbbbbbbbbbbbbb", "blz %B", + "1111101100000000bbbbbbbbbbbbbbbb", "blez %B", + "1111110000000000bbbbbbbbbbbbbbbb", "bgz %B", + "1111110100000000bbbbbbbbbbbbbbbb", "bgez %B", + "1111111000000000bbbbbbbbbbbbbbbb", "bnz %B", + "1111111100000000bbbbbbbbbbbbbbbb", "bz %B", nullptr }; -#define MAX_OPS ((ARRAY_LENGTH(TMS32010Formats) - 1) / PTRS_PER_FORMAT) - -struct TMS32010Opcode { - word mask; /* instruction mask */ - word bits; /* constant bits */ - word extcode; /* value that gets extension code */ - const char *parse; /* how to parse bits */ - const char *fmt; /* instruction format */ -}; - -static TMS32010Opcode Op[MAX_OPS+1]; -static int OpInizialized = 0; - -static void InitDasm32010(void) +tms32010_disassembler::tms32010_disassembler() { const char *p; const char *const *ops; - word mask, bits; + u16 mask, bits; int bit; int i; @@ -209,20 +186,14 @@ static void InitDasm32010(void) ops[0],ops[1],bit); } while (isspace((uint8_t)*p)) p++; - if (*p) Op[i].extcode = *p; - Op[i].bits = bits; - Op[i].mask = mask; - Op[i].fmt = ops[1]; - Op[i].parse = ops[0]; + Op.emplace_back(bits, mask, *p, ops[0], ops[1]); - ops += PTRS_PER_FORMAT; + ops += 2; i++; } - - OpInizialized = 1; } -CPU_DISASSEMBLE(tms32010) +offs_t tms32010_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { uint32_t flags = 0; int a, b, d, k, m, n, p, r, s, w; /* these can all be filled in by parsing an instruction */ @@ -234,11 +205,9 @@ CPU_DISASSEMBLE(tms32010) //char *buffertmp; const char *cp; /* character pointer in OpFormats */ - if (!OpInizialized) InitDasm32010(); - op = -1; /* no matching opcode */ - code = (oprom[0] << 8) | oprom[1]; - for ( i = 0; i < MAX_OPS; i++) + code = opcodes.r16(pc); + for ( i = 0; i < int(Op.size()); i++) { if ((code & Op[i].mask) == Op[i].bits) { @@ -253,14 +222,14 @@ CPU_DISASSEMBLE(tms32010) if (op == -1) { util::stream_format(stream, "dw %04Xh *(invalid op)", code); - return cnt | DASMFLAG_SUPPORTED; + return cnt | SUPPORTED; } //buffertmp = buffer; if (Op[op].extcode) { bit = 31; code <<= 16; - code |= (opram[2] << 8) | opram[3]; + code |= opcodes.r16(pc+1); cnt++; } else @@ -298,9 +267,9 @@ CPU_DISASSEMBLE(tms32010) cp = Op[op].fmt; if (!strncmp(cp, "cal", 3)) - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; else if (!strncmp(cp, "ret", 3)) - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; while (*cp) { @@ -330,5 +299,11 @@ CPU_DISASSEMBLE(tms32010) stream << *cp++; } } - return cnt | flags | DASMFLAG_SUPPORTED; + return cnt | flags | SUPPORTED; } + +u32 tms32010_disassembler::opcode_alignment() const +{ + return 1; +} + diff --git a/src/devices/cpu/tms32010/32010dsm.h b/src/devices/cpu/tms32010/32010dsm.h new file mode 100644 index 00000000000..d2b93d5f5a4 --- /dev/null +++ b/src/devices/cpu/tms32010/32010dsm.h @@ -0,0 +1,59 @@ +// license:BSD-3-Clause +// copyright-holders:Tony La Porta + /**************************************************************************\ + * Texas Instruments TMS32010 DSP Disassembler * + * * + * Copyright Tony La Porta * + * To be used with TMS32010 DSP Emulator engine. * + * * + * Many thanks to those involved in the i8039 Disassembler * + * as this was based on it. * + * * + * * + * * + * A Memory address * + * B Branch Address for Branch instructions (Requires next opcode read) * + * D Immediate byte load * + * K Immediate bit load * + * W Immediate word load (Actually 13 bit) * + * M AR[x] register modification type (for indirect addressing) * + * N ARP register to change ARP pointer to (for indirect addressing) * + * P I/O port address number * + * R AR[R] register to use * + * S Shift ALU left * + * * + \**************************************************************************/ + +#ifndef MAME_CPU_TMS32010_DIS32010_H +#define MAME_CPU_TMS32010_DIS32010_H + +#pragma once + +class tms32010_disassembler : public util::disasm_interface +{ +public: + tms32010_disassembler(); + virtual ~tms32010_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + struct TMS32010Opcode { + u16 mask; /* instruction mask */ + u16 bits; /* constant bits */ + u16 extcode; /* value that gets extension code */ + const char *parse; /* how to parse bits */ + const char *fmt; /* instruction format */ + + TMS32010Opcode(u16 m, u16 b, u16 e, const char *p, const char *f) : mask(m), bits(b), extcode(e), parse(p), fmt(f) {} + }; + + static const char *const arith[4]; + static const char *const nextar[4]; + static const char *const TMS32010Formats[]; + + std::vector Op; +}; + +#endif diff --git a/src/devices/cpu/tms32010/tms32010.cpp b/src/devices/cpu/tms32010/tms32010.cpp index 007cac7b0fc..c5b203f74cf 100644 --- a/src/devices/cpu/tms32010/tms32010.cpp +++ b/src/devices/cpu/tms32010/tms32010.cpp @@ -59,6 +59,7 @@ #include "emu.h" #include "tms32010.h" +#include "32010dsm.h" #include "debugger.h" @@ -134,10 +135,9 @@ device_memory_interface::space_config_vector tms32010_device::memory_space_confi }; } -offs_t tms32010_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *tms32010_device::create_disassembler() { - extern CPU_DISASSEMBLE( tms32010 ); - return CPU_DISASSEMBLE_NAME(tms32010)(this, stream, pc, oprom, opram, options); + return new tms32010_disassembler; } diff --git a/src/devices/cpu/tms32010/tms32010.h b/src/devices/cpu/tms32010/tms32010.h index 2f2469330e5..e3f955e6a05 100644 --- a/src/devices/cpu/tms32010/tms32010.h +++ b/src/devices/cpu/tms32010/tms32010.h @@ -70,9 +70,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/tms32025/32025dsm.cpp b/src/devices/cpu/tms32025/32025dsm.cpp index cf9a61571b5..9bc8f90812f 100644 --- a/src/devices/cpu/tms32025/32025dsm.cpp +++ b/src/devices/cpu/tms32025/32025dsm.cpp @@ -31,309 +31,286 @@ \**************************************************************************/ #include "emu.h" -#include "debugger.h" +#include "32025dsm.h" #include -#include "tms32025.h" +const char *const tms32025_disassembler::arith[8] = { "*", "*-", "*+", "??", "BR0-", "*0-", "*0+", "*BR0+" } ; +const char *const tms32025_disassembler::nextar[16] = { "", "", "", "", "", "", "", "", ",AR0", ",AR1", ",AR2", ",AR3", ",AR4", ",AR5", ",AR6", ",AR7" } ; +const char *const tms32025_disassembler::cmpmode[4] = { "0 (ARx = AR0)" , "1 (ARx < AR0)" , "2 (ARx > AR0)" , "3 (ARx <> AR0)" } ; +const char *const tms32025_disassembler::TMS32025Formats[] = { + "0000tttt0aaaaaaa", "add %A,%T", /* 0xxx */ + "0000tttt1mmmnnnn", "add %M,%T%N", + "0001tttt0aaaaaaa", "sub %A,%T", /* 1xxx */ + "0001tttt1mmmnnnn", "sub %M,%T%N", + "0010tttt0aaaaaaa", "lac %A,%T", /* 2xxx */ + "0010tttt1mmmnnnn", "lac %M,%T%N", + "00110rrr0aaaaaaa", "lar %R,%A", /* 3xxx */ + "00110rrr1mmmnnnn", "lar %R%M%N", + "001110000aaaaaaa", "mpy %A", /* 38xx */ + "001110001mmmnnnn", "mpy %M%N", + "001110010aaaaaaa", "sqra %A", /* 39xx */ + "001110011mmmnnnn", "sqra %M%N", + "001110100aaaaaaa", "mpya %A", /* 3Axx */ + "001110101mmmnnnn", "mpya %M%N", + "001110110aaaaaaa", "mpys %A", /* 3Bxx */ + "001110111mmmnnnn", "mpys %M%N", + "001111000aaaaaaa", "lt %A", /* 3Cxx */ + "001111001mmmnnnn", "lt %M%N", + "001111010aaaaaaa", "lta %A", /* 3Dxx */ + "001111011mmmnnnn", "lta %M%N", + "001111100aaaaaaa", "ltp %A", /* 3Exx */ + "001111101mmmnnnn", "ltp %M%N", + "001111110aaaaaaa", "ltd %A", /* 3Fxx */ + "001111111mmmnnnn", "ltd %M%N", + "010000000aaaaaaa", "zalh %A", /* 40xx */ + "010000001mmmnnnn", "zalh %M%N", + "010000010aaaaaaa", "zals %A", /* 41xx */ + "010000011mmmnnnn", "zals %M%N", + "010000100aaaaaaa", "lact %A", /* 42xx */ + "010000101mmmnnnn", "lact %M%N", + "010000110aaaaaaa", "addc %A%S", /* 43xx */ + "010000111mmmnnnn", "addc %M%S%N", + "010001000aaaaaaa", "subh %A", /* 44xx */ + "010001001mmmnnnn", "subh %M%N", + "010001010aaaaaaa", "subs %A", /* 45xx */ + "010001011mmmnnnn", "subs %M%N", + "010001100aaaaaaa", "subt %A", /* 46xx */ + "010001101mmmnnnn", "subt %M%N", + "010001110aaaaaaa", "subc %A", /* 47xx */ + "010001111mmmnnnn", "subc %M%N", + "010010000aaaaaaa", "addh %A", /* 48xx */ + "010010001mmmnnnn", "addh %M%N", + "010010010aaaaaaa", "adds %A", /* 49xx */ + "010010011mmmnnnn", "adds %M%N", + "010010100aaaaaaa", "addt %A", /* 4Axx */ + "010010101mmmnnnn", "addt %M%N", + "010010110aaaaaaa", "rpt %A", /* 4Bxx */ + "010010111mmmnnnn", "rpt %M%N", + "010011000aaaaaaa", "xor %A", /* 4Cxx */ + "010011001mmmnnnn", "xor %M%N", + "010011010aaaaaaa", "or %A", /* 4Dxx */ + "010011011mmmnnnn", "or %M%N", + "010011100aaaaaaa", "and %A", /* 4Exx */ + "010011101mmmnnnn", "and %M%N", + "010011110aaaaaaa", "subb %A", /* 4Fxx */ + "010011111mmmnnnn", "subb %M%N", + "010100000aaaaaaa", "lst %A", /* 50xx */ + "010100001mmmnnnn", "lst %M%N", + "010100010aaaaaaa", "lst1 %A", /* 51xx */ + "010100011mmmnnnn", "lst1 %M%N", + "010100100aaaaaaa", "ldp %A", /* 52xx */ + "010100101mmmnnnn", "ldp %M%N", + "010100110aaaaaaa", "lph %A", /* 53xx */ + "010100111mmmnnnn", "lph %M%N", + "010101000aaaaaaa", "pshd %A", /* 54xx */ + "010101001mmmnnnn", "pshd %M%N", -typedef unsigned char byte; -typedef unsigned short int word; - -#define FMT(a,b) a, b -#define PTRS_PER_FORMAT 2 - -static const char *const arith[8] = { "*", "*-", "*+", "??", "BR0-", "*0-", "*0+", "*BR0+" } ; -static const char *const nextar[16] = { "", "", "", "", "", "", "", "", ",AR0", ",AR1", ",AR2", ",AR3", ",AR4", ",AR5", ",AR6", ",AR7" } ; -static const char *const cmpmode[4] = { "0 (ARx = AR0)" , "1 (ARx < AR0)" , "2 (ARx > AR0)" , "3 (ARx <> AR0)" } ; - - -static const char *const TMS32025Formats[] = { - FMT("0000tttt0aaaaaaa", "add %A,%T"), /* 0xxx */ - FMT("0000tttt1mmmnnnn", "add %M,%T%N"), - FMT("0001tttt0aaaaaaa", "sub %A,%T"), /* 1xxx */ - FMT("0001tttt1mmmnnnn", "sub %M,%T%N"), - FMT("0010tttt0aaaaaaa", "lac %A,%T"), /* 2xxx */ - FMT("0010tttt1mmmnnnn", "lac %M,%T%N"), - FMT("00110rrr0aaaaaaa", "lar %R,%A"), /* 3xxx */ - FMT("00110rrr1mmmnnnn", "lar %R%M%N"), - FMT("001110000aaaaaaa", "mpy %A"), /* 38xx */ - FMT("001110001mmmnnnn", "mpy %M%N"), - FMT("001110010aaaaaaa", "sqra %A"), /* 39xx */ - FMT("001110011mmmnnnn", "sqra %M%N"), - FMT("001110100aaaaaaa", "mpya %A"), /* 3Axx */ - FMT("001110101mmmnnnn", "mpya %M%N"), - FMT("001110110aaaaaaa", "mpys %A"), /* 3Bxx */ - FMT("001110111mmmnnnn", "mpys %M%N"), - FMT("001111000aaaaaaa", "lt %A"), /* 3Cxx */ - FMT("001111001mmmnnnn", "lt %M%N"), - FMT("001111010aaaaaaa", "lta %A"), /* 3Dxx */ - FMT("001111011mmmnnnn", "lta %M%N"), - FMT("001111100aaaaaaa", "ltp %A"), /* 3Exx */ - FMT("001111101mmmnnnn", "ltp %M%N"), - FMT("001111110aaaaaaa", "ltd %A"), /* 3Fxx */ - FMT("001111111mmmnnnn", "ltd %M%N"), - FMT("010000000aaaaaaa", "zalh %A"), /* 40xx */ - FMT("010000001mmmnnnn", "zalh %M%N"), - FMT("010000010aaaaaaa", "zals %A"), /* 41xx */ - FMT("010000011mmmnnnn", "zals %M%N"), - FMT("010000100aaaaaaa", "lact %A"), /* 42xx */ - FMT("010000101mmmnnnn", "lact %M%N"), - FMT("010000110aaaaaaa", "addc %A%S"), /* 43xx */ - FMT("010000111mmmnnnn", "addc %M%S%N"), - FMT("010001000aaaaaaa", "subh %A"), /* 44xx */ - FMT("010001001mmmnnnn", "subh %M%N"), - FMT("010001010aaaaaaa", "subs %A"), /* 45xx */ - FMT("010001011mmmnnnn", "subs %M%N"), - FMT("010001100aaaaaaa", "subt %A"), /* 46xx */ - FMT("010001101mmmnnnn", "subt %M%N"), - FMT("010001110aaaaaaa", "subc %A"), /* 47xx */ - FMT("010001111mmmnnnn", "subc %M%N"), - FMT("010010000aaaaaaa", "addh %A"), /* 48xx */ - FMT("010010001mmmnnnn", "addh %M%N"), - FMT("010010010aaaaaaa", "adds %A"), /* 49xx */ - FMT("010010011mmmnnnn", "adds %M%N"), - FMT("010010100aaaaaaa", "addt %A"), /* 4Axx */ - FMT("010010101mmmnnnn", "addt %M%N"), - FMT("010010110aaaaaaa", "rpt %A"), /* 4Bxx */ - FMT("010010111mmmnnnn", "rpt %M%N"), - FMT("010011000aaaaaaa", "xor %A"), /* 4Cxx */ - FMT("010011001mmmnnnn", "xor %M%N"), - FMT("010011010aaaaaaa", "or %A"), /* 4Dxx */ - FMT("010011011mmmnnnn", "or %M%N"), - FMT("010011100aaaaaaa", "and %A"), /* 4Exx */ - FMT("010011101mmmnnnn", "and %M%N"), - FMT("010011110aaaaaaa", "subb %A"), /* 4Fxx */ - FMT("010011111mmmnnnn", "subb %M%N"), - FMT("010100000aaaaaaa", "lst %A"), /* 50xx */ - FMT("010100001mmmnnnn", "lst %M%N"), - FMT("010100010aaaaaaa", "lst1 %A"), /* 51xx */ - FMT("010100011mmmnnnn", "lst1 %M%N"), - FMT("010100100aaaaaaa", "ldp %A"), /* 52xx */ - FMT("010100101mmmnnnn", "ldp %M%N"), - FMT("010100110aaaaaaa", "lph %A"), /* 53xx */ - FMT("010100111mmmnnnn", "lph %M%N"), - FMT("010101000aaaaaaa", "pshd %A"), /* 54xx */ - FMT("010101001mmmnnnn", "pshd %M%N"), - -/* FMT("010101010aaaaaaa", "mar %A"), 55xx */ +/* "010101010aaaaaaa", "mar %A", 55xx */ /* MAR direct has been expanded out to all its variations because one of its */ /* its opcodes is the same as NOP. Actually MAR direct just performs a NOP */ - FMT("0101010100000000", "nop"), /* 5500 */ - FMT("0101010100000001", "mar $01"), - FMT("0101010100000010", "mar $02"), - FMT("0101010100000011", "mar $03"), - FMT("0101010100000100", "mar $04"), - FMT("0101010100000101", "mar $05"), - FMT("0101010100000110", "mar $06"), - FMT("0101010100000111", "mar $07"), - FMT("0101010100001000", "mar $08"), - FMT("0101010100001001", "mar $09"), - FMT("0101010100001010", "mar $0A"), - FMT("0101010100001011", "mar $0B"), - FMT("0101010100001100", "mar $0C"), - FMT("0101010100001101", "mar $0D"), - FMT("0101010100001110", "mar $0E"), - FMT("0101010100001111", "mar $0F"), - FMT("010101010001tttt", "mar $1%T"), - FMT("010101010010tttt", "mar $2%T"), - FMT("010101010011tttt", "mar $3%T"), - FMT("010101010100tttt", "mar $4%T"), - FMT("010101010101tttt", "mar $5%T"), - FMT("010101010110tttt", "mar $6%T"), - FMT("010101010111tttt", "mar $7%T"), + "0101010100000000", "nop", /* 5500 */ + "0101010100000001", "mar $01", + "0101010100000010", "mar $02", + "0101010100000011", "mar $03", + "0101010100000100", "mar $04", + "0101010100000101", "mar $05", + "0101010100000110", "mar $06", + "0101010100000111", "mar $07", + "0101010100001000", "mar $08", + "0101010100001001", "mar $09", + "0101010100001010", "mar $0A", + "0101010100001011", "mar $0B", + "0101010100001100", "mar $0C", + "0101010100001101", "mar $0D", + "0101010100001110", "mar $0E", + "0101010100001111", "mar $0F", + "010101010001tttt", "mar $1%T", + "010101010010tttt", "mar $2%T", + "010101010011tttt", "mar $3%T", + "010101010100tttt", "mar $4%T", + "010101010101tttt", "mar $5%T", + "010101010110tttt", "mar $6%T", + "010101010111tttt", "mar $7%T", -/* FMT("010101011mmmnnnn", "mar %M%N"), 55xx */ +/* "010101011mmmnnnn", "mar %M%N", 55xx */ /* MAR indirect has been expanded out to all its variations because one of */ /* its opcodes, is the same as LARP (actually performs the same function) */ - FMT("0101010110000xxx", "mar *"), /* 558x */ - FMT("0101010110001kkk", "larp %K"), /* 558x */ - FMT("010101011001nnnn", "mar *-%N"), /* 558x */ - FMT("010101011010nnnn", "mar *+%N"), - FMT("010101011011nnnn", "mar ??%N"), - FMT("010101011100nnnn", "mar *BR0-%N"), - FMT("010101011101nnnn", "mar *0-%N"), - FMT("010101011110nnnn", "mar *0+%N"), - FMT("010101011111nnnn", "mar *BR0+%N"), + "0101010110000xxx", "mar *", /* 558x */ + "0101010110001kkk", "larp %K", /* 558x */ + "010101011001nnnn", "mar *-%N", /* 558x */ + "010101011010nnnn", "mar *+%N", + "010101011011nnnn", "mar ??%N", + "010101011100nnnn", "mar *BR0-%N", + "010101011101nnnn", "mar *0-%N", + "010101011110nnnn", "mar *0+%N", + "010101011111nnnn", "mar *BR0+%N", - FMT("010101100aaaaaaa", "dmov %A"), /* 56xx */ - FMT("010101101mmmnnnn", "dmov %M%N"), - FMT("010101110aaaaaaa", "bitt %A"), /* 57xx */ - FMT("010101111mmmnnnn", "bitt %M%N"), - FMT("010110000aaaaaaa", "tblr %A"), /* 58xx */ - FMT("010110001mmmnnnn", "tblr %M%N"), - FMT("010110010aaaaaaa", "tblw %A"), /* 59xx */ - FMT("010110011mmmnnnn", "tblw %M%N"), - FMT("010110100aaaaaaa", "sqrs %A"), /* 5Axx */ - FMT("010110101mmmnnnn", "sqrs %M%N"), - FMT("010110110aaaaaaa", "lts %A"), /* 5Bxx */ - FMT("010110111mmmnnnn", "lts %M%N"), - FMT("010111000aaaaaaabbbbbbbbbbbbbbbb", "macd %B,%A"), /* 5Cxx */ - FMT("010111001mmmnnnnbbbbbbbbbbbbbbbb", "macd %B,%M%N"), - FMT("010111010aaaaaaabbbbbbbbbbbbbbbb", "mac %B,%A"), /* 5Dxx */ - FMT("010111011mmmnnnnbbbbbbbbbbbbbbbb", "mac %B,%M%N"), - FMT("010111101mmmnnnnbbbbbbbbbbbbbbbb", "bc %B %M%N"), /* 5Exx */ - FMT("010111111mmmnnnnbbbbbbbbbbbbbbbb", "bnc %B %M%N"), /* 5Fxx */ - FMT("01100sss0aaaaaaa", "sacl %A%S"), /* 6xxx */ - FMT("01100sss1mmmnnnn", "sacl %M%S%N"), - FMT("01101sss0aaaaaaa", "sach %A%S"), /* 6Xxx */ - FMT("01101sss1mmmnnnn", "sach %M%S%N"), - FMT("01110rrr0aaaaaaa", "sar %R,%A"), /* 7xxx */ - FMT("01110rrr1mmmnnnn", "sar %R%M%N"), - FMT("011110000aaaaaaa", "sst %A"), /* 78xx */ - FMT("011110001mmmnnnn", "sst %M%N"), - FMT("011110010aaaaaaa", "sst1 %A"), /* 79xx */ - FMT("011110011mmmnnnn", "sst1 %M%N"), - FMT("011110100aaaaaaa", "popd %A"), /* 7Axx */ - FMT("011110101mmmnnnn", "popd %M%N"), - FMT("011110110aaaaaaa", "zalr %A"), /* 7Bxx */ - FMT("011110111mmmnnnn", "zalr %M%N"), - FMT("011111000aaaaaaa", "spl %A"), /* 7Cxx */ - FMT("011111001mmmnnnn", "spl %M%N"), - FMT("011111010aaaaaaa", "sph %A"), /* 7Dxx */ - FMT("011111011mmmnnnn", "sph %M%N"), - FMT("011111100aaaaaaa", "adrk %A"), /* 7Exx */ - FMT("011111101mmmnnnn", "adrk %M%N"), - FMT("011111110aaaaaaa", "sbrk %A"), /* 7Fxx */ - FMT("011111111mmmnnnn", "sbrk %M%N"), - FMT("1000pppp0aaaaaaa", "in %A,%P"), /* 8xxx */ - FMT("1000pppp1mmmnnnn", "in %M,%P%N"), - FMT("1001tttt0aaaaaaa", "bit %A,%T"), /* 9xxx */ - FMT("1001tttt1mmmnnnn", "bit %M,%T%N"), - FMT("101wwwwwwwwwwwww", "mpyk %W"), /* Axxx-Bxxx */ - FMT("11000rrrdddddddd", "lark %R,%D"), /* Cxxx */ - FMT("1100100kdddddddd", "ldpk %K%D"), /* Cxxx */ -/* FMT("11001010dddddddd", "lack %D"), CAxx */ + "010101100aaaaaaa", "dmov %A", /* 56xx */ + "010101101mmmnnnn", "dmov %M%N", + "010101110aaaaaaa", "bitt %A", /* 57xx */ + "010101111mmmnnnn", "bitt %M%N", + "010110000aaaaaaa", "tblr %A", /* 58xx */ + "010110001mmmnnnn", "tblr %M%N", + "010110010aaaaaaa", "tblw %A", /* 59xx */ + "010110011mmmnnnn", "tblw %M%N", + "010110100aaaaaaa", "sqrs %A", /* 5Axx */ + "010110101mmmnnnn", "sqrs %M%N", + "010110110aaaaaaa", "lts %A", /* 5Bxx */ + "010110111mmmnnnn", "lts %M%N", + "010111000aaaaaaabbbbbbbbbbbbbbbb", "macd %B,%A", /* 5Cxx */ + "010111001mmmnnnnbbbbbbbbbbbbbbbb", "macd %B,%M%N", + "010111010aaaaaaabbbbbbbbbbbbbbbb", "mac %B,%A", /* 5Dxx */ + "010111011mmmnnnnbbbbbbbbbbbbbbbb", "mac %B,%M%N", + "010111101mmmnnnnbbbbbbbbbbbbbbbb", "bc %B %M%N", /* 5Exx */ + "010111111mmmnnnnbbbbbbbbbbbbbbbb", "bnc %B %M%N", /* 5Fxx */ + "01100sss0aaaaaaa", "sacl %A%S", /* 6xxx */ + "01100sss1mmmnnnn", "sacl %M%S%N", + "01101sss0aaaaaaa", "sach %A%S", /* 6Xxx */ + "01101sss1mmmnnnn", "sach %M%S%N", + "01110rrr0aaaaaaa", "sar %R,%A", /* 7xxx */ + "01110rrr1mmmnnnn", "sar %R%M%N", + "011110000aaaaaaa", "sst %A", /* 78xx */ + "011110001mmmnnnn", "sst %M%N", + "011110010aaaaaaa", "sst1 %A", /* 79xx */ + "011110011mmmnnnn", "sst1 %M%N", + "011110100aaaaaaa", "popd %A", /* 7Axx */ + "011110101mmmnnnn", "popd %M%N", + "011110110aaaaaaa", "zalr %A", /* 7Bxx */ + "011110111mmmnnnn", "zalr %M%N", + "011111000aaaaaaa", "spl %A", /* 7Cxx */ + "011111001mmmnnnn", "spl %M%N", + "011111010aaaaaaa", "sph %A", /* 7Dxx */ + "011111011mmmnnnn", "sph %M%N", + "011111100aaaaaaa", "adrk %A", /* 7Exx */ + "011111101mmmnnnn", "adrk %M%N", + "011111110aaaaaaa", "sbrk %A", /* 7Fxx */ + "011111111mmmnnnn", "sbrk %M%N", + "1000pppp0aaaaaaa", "in %A,%P", /* 8xxx */ + "1000pppp1mmmnnnn", "in %M,%P%N", + "1001tttt0aaaaaaa", "bit %A,%T", /* 9xxx */ + "1001tttt1mmmnnnn", "bit %M,%T%N", + "101wwwwwwwwwwwww", "mpyk %W", /* Axxx-Bxxx */ + "11000rrrdddddddd", "lark %R,%D", /* Cxxx */ + "1100100kdddddddd", "ldpk %K%D", /* Cxxx */ +/* "11001010dddddddd", "lack %D", CAxx */ /* LACK has been expanded out to all its variations because one of its */ /* its opcodes is the same as ZAC. Actually, it performs the same function */ - FMT("1100101000000000", "zac"), /* CA00 */ - FMT("1100101000000001", "lack 01h"), /* CAxx */ - FMT("1100101000000010", "lack 02h"), - FMT("1100101000000011", "lack 03h"), - FMT("1100101000000100", "lack 04h"), - FMT("1100101000000101", "lack 05h"), - FMT("1100101000000110", "lack 06h"), - FMT("1100101000000111", "lack 07h"), - FMT("1100101000001000", "lack 08h"), - FMT("1100101000001001", "lack 09h"), - FMT("1100101000001010", "lack 0Ah"), - FMT("1100101000001011", "lack 0Bh"), - FMT("1100101000001100", "lack 0Ch"), - FMT("1100101000001101", "lack 0Dh"), - FMT("1100101000001110", "lack 0Eh"), - FMT("1100101000001111", "lack 0Fh"), - FMT("110010100001tttt", "lack 1%T"), - FMT("110010100010tttt", "lack 2%T"), - FMT("110010100011tttt", "lack 3%T"), - FMT("110010100100tttt", "lack 4%T"), - FMT("110010100101tttt", "lack 5%T"), - FMT("110010100110tttt", "lack 6%T"), - FMT("110010100111tttt", "lack 7%T"), - FMT("110010101000tttt", "lack 8%T"), - FMT("110010101001tttt", "lack 9%T"), - FMT("110010101010tttt", "lack A%T"), - FMT("110010101011tttt", "lack B%T"), - FMT("110010101100tttt", "lack C%T"), - FMT("110010101101tttt", "lack D%T"), - FMT("110010101110tttt", "lack E%T"), - FMT("110010101111tttt", "lack F%T"), + "1100101000000000", "zac", /* CA00 */ + "1100101000000001", "lack 01h", /* CAxx */ + "1100101000000010", "lack 02h", + "1100101000000011", "lack 03h", + "1100101000000100", "lack 04h", + "1100101000000101", "lack 05h", + "1100101000000110", "lack 06h", + "1100101000000111", "lack 07h", + "1100101000001000", "lack 08h", + "1100101000001001", "lack 09h", + "1100101000001010", "lack 0Ah", + "1100101000001011", "lack 0Bh", + "1100101000001100", "lack 0Ch", + "1100101000001101", "lack 0Dh", + "1100101000001110", "lack 0Eh", + "1100101000001111", "lack 0Fh", + "110010100001tttt", "lack 1%T", + "110010100010tttt", "lack 2%T", + "110010100011tttt", "lack 3%T", + "110010100100tttt", "lack 4%T", + "110010100101tttt", "lack 5%T", + "110010100110tttt", "lack 6%T", + "110010100111tttt", "lack 7%T", + "110010101000tttt", "lack 8%T", + "110010101001tttt", "lack 9%T", + "110010101010tttt", "lack A%T", + "110010101011tttt", "lack B%T", + "110010101100tttt", "lack C%T", + "110010101101tttt", "lack D%T", + "110010101110tttt", "lack E%T", + "110010101111tttt", "lack F%T", - FMT("11001011dddddddd", "rptk %D"), /* CBxx */ - FMT("11001100dddddddd", "addk %D"), /* CCxx */ - FMT("11001101dddddddd", "subk %D"), /* CDxx */ - FMT("1100111000000000", "eint"), /* CE00 */ - FMT("1100111000000001", "dint"), /* CE01 */ - FMT("1100111000000010", "rovm"), /* CE02 */ - FMT("1100111000000011", "sovm"), /* CE03 */ - FMT("1100111000000100", "cnfd"), /* CE04 */ - FMT("1100111000000101", "cnfp"), /* CE05 */ - FMT("1100111000000110", "rsxm"), /* CE06 */ - FMT("1100111000000111", "ssxm"), /* CE07 */ - FMT("11001110000010kk", "spm %K"), /* CE0x */ - FMT("1100111000001100", "rxf"), /* CE0C */ - FMT("1100111000001101", "sxf"), /* CE0D */ - FMT("110011100000111k", "fort %K"), /* CE0x */ - FMT("1100111000010100", "pac"), /* CE14 */ - FMT("1100111000010101", "apac"), /* CE15 */ - FMT("1100111000010110", "spac"), /* CE16 */ - FMT("1100111000011000", "sfl"), /* CE18 */ - FMT("1100111000011001", "sfr"), /* CE19 */ - FMT("1100111000011011", "abs"), /* CE1B */ - FMT("1100111000011100", "push"), /* CE1C */ - FMT("1100111000011101", "pop"), /* CE1D */ - FMT("1100111000011110", "trap"), /* CE1E */ - FMT("1100111000011111", "idle"), /* CE1F */ - FMT("1100111000100000", "rtxm"), /* CE20 */ - FMT("1100111000100001", "stxm"), /* CE21 */ - FMT("1100111000100011", "neg"), /* CE23 */ - FMT("1100111000100100", "cala"), /* CE24 */ - FMT("1100111000100101", "bacc"), /* CE25 */ - FMT("1100111000100110", "ret"), /* CE26 */ - FMT("1100111000100111", "cmpl"), /* CE27 */ - FMT("1100111000110000", "rc"), /* CE30 */ - FMT("1100111000110001", "sc"), /* CE31 */ - FMT("1100111000110010", "rtc"), /* CE32 */ - FMT("1100111000110011", "stc"), /* CE33 */ - FMT("1100111000110100", "rol"), /* CE34 */ - FMT("1100111000110101", "ror"), /* CE35 */ - FMT("1100111000110110", "rfsm"), /* CE36 */ - FMT("1100111000110111", "sfsm"), /* CE37 */ - FMT("1100111000111000", "rhm"), /* CE38 */ - FMT("1100111000111001", "shm"), /* CE39 */ - FMT("11001110001111kk", "conf %K"), /* CE3x */ - FMT("11001110010100cc", "cmpr %C"), /* CE5x */ - FMT("110011101mmm0010", "norm %M"), /* CEx2 */ - FMT("110011110aaaaaaa", "mpys %A"), /* CFxx */ - FMT("110011111mmmnnnn", "mpys %M%N"), - FMT("11010rrr00000000wwwwwwwwwwwwwwww", "lrlk %R,%W"), /* Dx00 */ - FMT("1101tttt00000001wwwwwwwwwwwwwwww", "lalk %W,%T"), /* Dx01 */ - FMT("1101tttt00000010wwwwwwwwwwwwwwww", "adlk %W,%T"), /* Dx02 */ - FMT("1101tttt00000011wwwwwwwwwwwwwwww", "sblk %W,%T"), /* Dx03 */ - FMT("1101tttt00000100wwwwwwwwwwwwwwww", "andk %W,%T"), /* Dx04 */ - FMT("1101tttt00000101wwwwwwwwwwwwwwww", "ork %W,%T"), /* Dx05 */ - FMT("1101tttt00000110wwwwwwwwwwwwwwww", "xork %W,%T"), /* Dx06 */ - FMT("1110pppp0aaaaaaa", "out %A,%P"), /* Exxx */ - FMT("1110pppp1mmmnnnn", "out %M,%P%N"), - FMT("111100001mmmnnnnbbbbbbbbbbbbbbbb", "bv %B %M%N"), /* F0xx */ - FMT("111100011mmmnnnnbbbbbbbbbbbbbbbb", "bgz %B %M%N"), /* F1xx */ - FMT("111100101mmmnnnnbbbbbbbbbbbbbbbb", "blez %B %M%N"), /* F2xx */ - FMT("111100111mmmnnnnbbbbbbbbbbbbbbbb", "blz %B %M%N"), /* F3xx */ - FMT("111101001mmmnnnnbbbbbbbbbbbbbbbb", "bgez %B %M%N"), /* F4xx */ - FMT("111101011mmmnnnnbbbbbbbbbbbbbbbb", "bnz %B %M%N"), /* F5xx */ - FMT("111101101mmmnnnnbbbbbbbbbbbbbbbb", "bz %B %M%N"), /* F6xx */ - FMT("111101111mmmnnnnbbbbbbbbbbbbbbbb", "bnv %B %M%N"), /* F7xx */ - FMT("111110001mmmnnnnbbbbbbbbbbbbbbbb", "bbz %B %M%N"), /* F8xx */ - FMT("111110011mmmnnnnbbbbbbbbbbbbbbbb", "bbnz %B %M%N"), /* F9xx */ - FMT("111110101mmmnnnnbbbbbbbbbbbbbbbb", "bioz %B %M%N"), /* FAxx */ - FMT("111110111mmmnnnnbbbbbbbbbbbbbbbb", "banz %B %M%N"), /* FBxx */ - FMT("111111000aaaaaaabbbbbbbbbbbbbbbb", "blkp %B,%A"), /* FCxx */ - FMT("111111001mmmnnnnbbbbbbbbbbbbbbbb", "blkp %B,%M%N"), - FMT("111111010aaaaaaabbbbbbbbbbbbbbbb", "blkd %B,%A"), /* FDxx */ - FMT("111111011mmmnnnnbbbbbbbbbbbbbbbb", "blkd %B,%M%N"), - FMT("111111101mmmnnnnbbbbbbbbbbbbbbbb", "call %B %M%N"), /* FExx */ - FMT("111111111mmmnnnnbbbbbbbbbbbbbbbb", "b %B %M%N"), /* FFxx */ + "11001011dddddddd", "rptk %D", /* CBxx */ + "11001100dddddddd", "addk %D", /* CCxx */ + "11001101dddddddd", "subk %D", /* CDxx */ + "1100111000000000", "eint", /* CE00 */ + "1100111000000001", "dint", /* CE01 */ + "1100111000000010", "rovm", /* CE02 */ + "1100111000000011", "sovm", /* CE03 */ + "1100111000000100", "cnfd", /* CE04 */ + "1100111000000101", "cnfp", /* CE05 */ + "1100111000000110", "rsxm", /* CE06 */ + "1100111000000111", "ssxm", /* CE07 */ + "11001110000010kk", "spm %K", /* CE0x */ + "1100111000001100", "rxf", /* CE0C */ + "1100111000001101", "sxf", /* CE0D */ + "110011100000111k", "fort %K", /* CE0x */ + "1100111000010100", "pac", /* CE14 */ + "1100111000010101", "apac", /* CE15 */ + "1100111000010110", "spac", /* CE16 */ + "1100111000011000", "sfl", /* CE18 */ + "1100111000011001", "sfr", /* CE19 */ + "1100111000011011", "abs", /* CE1B */ + "1100111000011100", "push", /* CE1C */ + "1100111000011101", "pop", /* CE1D */ + "1100111000011110", "trap", /* CE1E */ + "1100111000011111", "idle", /* CE1F */ + "1100111000100000", "rtxm", /* CE20 */ + "1100111000100001", "stxm", /* CE21 */ + "1100111000100011", "neg", /* CE23 */ + "1100111000100100", "cala", /* CE24 */ + "1100111000100101", "bacc", /* CE25 */ + "1100111000100110", "ret", /* CE26 */ + "1100111000100111", "cmpl", /* CE27 */ + "1100111000110000", "rc", /* CE30 */ + "1100111000110001", "sc", /* CE31 */ + "1100111000110010", "rtc", /* CE32 */ + "1100111000110011", "stc", /* CE33 */ + "1100111000110100", "rol", /* CE34 */ + "1100111000110101", "ror", /* CE35 */ + "1100111000110110", "rfsm", /* CE36 */ + "1100111000110111", "sfsm", /* CE37 */ + "1100111000111000", "rhm", /* CE38 */ + "1100111000111001", "shm", /* CE39 */ + "11001110001111kk", "conf %K", /* CE3x */ + "11001110010100cc", "cmpr %C", /* CE5x */ + "110011101mmm0010", "norm %M", /* CEx2 */ + "110011110aaaaaaa", "mpys %A", /* CFxx */ + "110011111mmmnnnn", "mpys %M%N", + "11010rrr00000000wwwwwwwwwwwwwwww", "lrlk %R,%W", /* Dx00 */ + "1101tttt00000001wwwwwwwwwwwwwwww", "lalk %W,%T", /* Dx01 */ + "1101tttt00000010wwwwwwwwwwwwwwww", "adlk %W,%T", /* Dx02 */ + "1101tttt00000011wwwwwwwwwwwwwwww", "sblk %W,%T", /* Dx03 */ + "1101tttt00000100wwwwwwwwwwwwwwww", "andk %W,%T", /* Dx04 */ + "1101tttt00000101wwwwwwwwwwwwwwww", "ork %W,%T", /* Dx05 */ + "1101tttt00000110wwwwwwwwwwwwwwww", "xork %W,%T", /* Dx06 */ + "1110pppp0aaaaaaa", "out %A,%P", /* Exxx */ + "1110pppp1mmmnnnn", "out %M,%P%N", + "111100001mmmnnnnbbbbbbbbbbbbbbbb", "bv %B %M%N", /* F0xx */ + "111100011mmmnnnnbbbbbbbbbbbbbbbb", "bgz %B %M%N", /* F1xx */ + "111100101mmmnnnnbbbbbbbbbbbbbbbb", "blez %B %M%N", /* F2xx */ + "111100111mmmnnnnbbbbbbbbbbbbbbbb", "blz %B %M%N", /* F3xx */ + "111101001mmmnnnnbbbbbbbbbbbbbbbb", "bgez %B %M%N", /* F4xx */ + "111101011mmmnnnnbbbbbbbbbbbbbbbb", "bnz %B %M%N", /* F5xx */ + "111101101mmmnnnnbbbbbbbbbbbbbbbb", "bz %B %M%N", /* F6xx */ + "111101111mmmnnnnbbbbbbbbbbbbbbbb", "bnv %B %M%N", /* F7xx */ + "111110001mmmnnnnbbbbbbbbbbbbbbbb", "bbz %B %M%N", /* F8xx */ + "111110011mmmnnnnbbbbbbbbbbbbbbbb", "bbnz %B %M%N", /* F9xx */ + "111110101mmmnnnnbbbbbbbbbbbbbbbb", "bioz %B %M%N", /* FAxx */ + "111110111mmmnnnnbbbbbbbbbbbbbbbb", "banz %B %M%N", /* FBxx */ + "111111000aaaaaaabbbbbbbbbbbbbbbb", "blkp %B,%A", /* FCxx */ + "111111001mmmnnnnbbbbbbbbbbbbbbbb", "blkp %B,%M%N", + "111111010aaaaaaabbbbbbbbbbbbbbbb", "blkd %B,%A", /* FDxx */ + "111111011mmmnnnnbbbbbbbbbbbbbbbb", "blkd %B,%M%N", + "111111101mmmnnnnbbbbbbbbbbbbbbbb", "call %B %M%N", /* FExx */ + "111111111mmmnnnnbbbbbbbbbbbbbbbb", "b %B %M%N", /* FFxx */ nullptr }; -#define MAX_OPS ((ARRAY_LENGTH(TMS32025Formats) - 1) / PTRS_PER_FORMAT) - -struct TMS32025Opcode { - word mask; /* instruction mask */ - word bits; /* constant bits */ - word extcode; /* value that gets extension code */ - const char *parse; /* how to parse bits */ - const char *fmt; /* instruction format */ -}; - -static TMS32025Opcode Op[MAX_OPS+1]; -static int OpInizialized = 0; - -static void InitDasm32025(void) +tms32025_disassembler::tms32025_disassembler() { const char *p; const char *const *ops; - word mask, bits; + u16 mask, bits; int bit; int i; @@ -374,20 +351,14 @@ static void InitDasm32025(void) ops[0],ops[1],bit); } while (isspace((uint8_t)*p)) p++; - if (*p) Op[i].extcode = *p; - Op[i].bits = bits; - Op[i].mask = mask; - Op[i].fmt = ops[1]; - Op[i].parse = ops[0]; + Op.emplace_back(bits, mask, *p, ops[0], ops[1]); - ops += PTRS_PER_FORMAT; + ops += 2; i++; } - - OpInizialized = 1; } -CPU_DISASSEMBLE(tms32025) +offs_t tms32025_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { uint32_t flags = 0; int a, b, c, d, k, m, n, p, r, s, t, w; /* these can all be filled in by parsing an instruction */ @@ -399,11 +370,9 @@ CPU_DISASSEMBLE(tms32025) //char *buffertmp; const char *cp; /* character pointer in OpFormats */ - if (!OpInizialized) InitDasm32025(); - op = -1; /* no matching opcode */ - code = (oprom[0] << 8) | oprom[1]; - for ( i = 0; i < MAX_OPS; i++) + code = opcodes.r16(pc); + for ( i = 0; i < int(Op.size()); i++) { if ((code & Op[i].mask) == Op[i].bits) { @@ -418,14 +387,14 @@ CPU_DISASSEMBLE(tms32025) if (op == -1) { util::stream_format(stream, "???? dw %04Xh",code); - return cnt | DASMFLAG_SUPPORTED; + return cnt | SUPPORTED; } //buffertmp = buffer; if (Op[op].extcode) { bit = 31; code <<= 16; - code |= (opram[2] << 8) | opram[3]; + code |= opcodes.r16(pc+1); cnt++; } else @@ -466,9 +435,9 @@ CPU_DISASSEMBLE(tms32025) cp = Op[op].fmt; if (!strncmp(cp, "cal", 3)) - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; else if (!strncmp(cp, "ret", 3)) - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; while (*cp) { @@ -501,5 +470,10 @@ CPU_DISASSEMBLE(tms32025) stream << *cp++; } } - return cnt | flags | DASMFLAG_SUPPORTED; + return cnt | flags | SUPPORTED; +} + +u32 tms32025_disassembler::opcode_alignment() const +{ + return 1; } diff --git a/src/devices/cpu/tms32025/32025dsm.h b/src/devices/cpu/tms32025/32025dsm.h new file mode 100644 index 00000000000..187628b09de --- /dev/null +++ b/src/devices/cpu/tms32025/32025dsm.h @@ -0,0 +1,66 @@ +// license:BSD-3-Clause +// copyright-holders:Tony La Porta, hap + /**************************************************************************\ + * Texas Instruments TMS320x25 DSP Disassembler * + * * + * Copyright Tony La Porta * + * To be used with TMS320x25 DSP Emulator engine. * + * Written for the MAME project. * + * * + * Many thanks to those involved in the i8039 Disassembler * + * as the structure here was borrowed from it. * + * * + * Note : This is a word based microcontroller, with addressing * + * architecture based on the Harvard addressing scheme. * + * * + * * + * A Memory Address * + * B Opcode Address Argument (Requires next opcode read) * + * C Compare mode * + * D Immediate byte load * + * K Immediate bit load * + * W Immediate word load * + * M AR[x] register modification type (for indirect addressing) * + * N ARP register to change ARP pointer to (for indirect addressing) * + * P I/O port address number * + * R AR[R] register to use * + * S Shift ALU left * + * T Shift ALU left (Hex) / Nibble data * + * X Don't care bit * + * * + \**************************************************************************/ + +#ifndef MAME_CPU_TMS32025_32025DSM_H +#define MAME_CPU_TMS32025_32025DSM_H + +#pragma once + +class tms32025_disassembler : public util::disasm_interface +{ +public: + tms32025_disassembler(); + virtual ~tms32025_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + struct TMS32025Opcode { + u16 mask; /* instruction mask */ + u16 bits; /* constant bits */ + u16 extcode; /* value that gets extension code */ + const char *parse; /* how to parse bits */ + const char *fmt; /* instruction format */ + + TMS32025Opcode(u16 m, u16 b, u16 e, const char *p, const char *f) : mask(m), bits(b), extcode(e), parse(p), fmt(f) {} + }; + + static const char *const arith[8]; + static const char *const nextar[16]; + static const char *const cmpmode[4]; + static const char *const TMS32025Formats[]; + + std::vector Op; +}; + +#endif diff --git a/src/devices/cpu/tms32025/dis32025.cpp b/src/devices/cpu/tms32025/dis32025.cpp deleted file mode 100644 index 6df4b92707a..00000000000 --- a/src/devices/cpu/tms32025/dis32025.cpp +++ /dev/null @@ -1,137 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:Tony La Porta, hap - /**************************************************************************\ - * Texas Instruments TMS320x25 DSP Disassembler * - * * - * Copyright Tony La Porta * - * Written for the MAME project. * - * * - * Notes : Data is expected to be read from source file as MSB first. * - * This is a word based microcontroller, with addressing * - * architecture based on the Harvard addressing scheme. * - * * - \**************************************************************************/ - -#include -#include - -#include "32025dsm.c" - - -unsigned char *Buffer; - - -int main(int argc,char *argv[]) -{ - int length=0, length_to_dump=0, offset=0, disasm_words=0; - int filelength=0, bytes_read; - int Counter=0; - - FILE *F; - char *String_Output; - - if(argc<2) - { - printf("\n"); - printf("TMS32025 Disassembler 1.1 by Tony La Porta (C)2001-2002+\n\n"); - printf("Usage: dis32025 [ [ ] ]\n"); - printf(" source file data must be MSB first\n"); - printf(" starting address to disassemble from (decimal)\n"); - printf(" number of addresses to disassemble (decimal)\n"); - printf(" Precede values with 0x if HEX values preffered\n"); - exit(1); - } - - if(!(F=fopen(argv[1],"rb"))) - { - printf("\n%s: Can't open file %s\n",argv[0],argv[1]); - exit(2); - } - argv++; argc--; - if (argv[1]) - { - offset = strtol(argv[1],nullptr,0); - argv++; argc--; - } - if (argv[1]) - { - length = strtol(argv[1],nullptr,0); - argv++; argc--; - } - - fseek(F,0, SEEK_END); - filelength = ftell(F); - - length *= 2; - - if ((length > (filelength - (offset*2))) || (length == 0)) length = filelength - (offset*2); - printf("Length=%04Xh(words) Offset=$%04Xh filelength=%04Xh(words) %04Xh(bytes)\n",length/2,offset,filelength/2,filelength); - length_to_dump = length; - printf("Starting from %d, dumping %d opcodes (word size)\n",offset,length/2); - Buffer = calloc((filelength+1),sizeof(char)); - if (Buffer==nullptr) - { - printf("Out of Memory !!!"); - fclose(F); - exit(3); - } - String_Output = calloc(80,sizeof(char)); - if (String_Output==nullptr) - { - printf("Out of Memory !!!"); - free(Buffer); - fclose(F); - exit(4); - } - - if (fseek(F,0,SEEK_SET) != 0) - { - printf("Error seeking to beginning of file\n"); - free(String_Output); - free(Buffer); - fclose(F); - exit(5); - } - - Counter = offset; - bytes_read = fread(Buffer,sizeof(char),filelength,F); - if (bytes_read >= length) - { - for (; length > 0; length -= (disasm_words*2)) - { - int ii; - disasm_words = Dasm32025(String_Output,Counter); - printf("$%04lX: ",Counter); - for (ii = 0; ii < disasm_words; ii++) - { - if (((Counter*2) + ii) > filelength) /* Past end of length to dump ? */ - { - sprintf(String_Output,"???? dw %02.2X%02.2Xh (Past end of disassembly !)",Buffer[((Counter-1)*2)],Buffer[((Counter-1)*2)+1]); - } - else - { - printf("%02.2x%02.2x ",Buffer[(Counter*2)],Buffer[(Counter*2) + 1]); - } - Counter++ ; - } - for (; ii < 4; ii++) - { - printf(" "); - } - printf("\t%s\n",String_Output); - } - } - else - { - printf("ERROR length to dump was %d ", length_to_dump/2); - printf(", but bytes read from file were %d\n", bytes_read/2); - free(String_Output); - free(Buffer); - fclose(F); - exit(7); - } - free(String_Output); - free(Buffer); - fclose(F); - return(0); -} diff --git a/src/devices/cpu/tms32025/tms32025.cpp b/src/devices/cpu/tms32025/tms32025.cpp index a9405d72f3d..08a2dfbe180 100644 --- a/src/devices/cpu/tms32025/tms32025.cpp +++ b/src/devices/cpu/tms32025/tms32025.cpp @@ -120,6 +120,7 @@ Table 3-2. TMS32025/26 Memory Blocks #include "emu.h" #include "tms32025.h" +#include "32025dsm.h" #include "debugger.h" @@ -253,11 +254,9 @@ device_memory_interface::space_config_vector tms32025_device::memory_space_confi }; } - -offs_t tms32025_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *tms32025_device::create_disassembler() { - extern CPU_DISASSEMBLE( tms32025 ); - return CPU_DISASSEMBLE_NAME(tms32025)(this, stream, pc, oprom, opram, options); + return new tms32025_disassembler; } READ16_MEMBER( tms32025_device::drr_r) diff --git a/src/devices/cpu/tms32025/tms32025.h b/src/devices/cpu/tms32025/tms32025.h index a9ae17576c4..6e8c2ab627a 100644 --- a/src/devices/cpu/tms32025/tms32025.h +++ b/src/devices/cpu/tms32025/tms32025.h @@ -125,9 +125,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; void common_reset(); diff --git a/src/devices/cpu/tms32031/dis32031.cpp b/src/devices/cpu/tms32031/dis32031.cpp index b6012827611..6bb468e164a 100644 --- a/src/devices/cpu/tms32031/dis32031.cpp +++ b/src/devices/cpu/tms32031/dis32031.cpp @@ -9,40 +9,13 @@ ***************************************************************************/ #include "emu.h" -#include "tms32031.h" - - -/*************************************************************************** - MEMORY ACCESSORS -***************************************************************************/ - -#define INTEGER 0 -#define FLOAT 1 -#define NODEST 2 -#define NOSOURCE 4 -#define NOSOURCE1 NOSOURCE -#define NOSOURCE2 8 -#define SWAPSRCDST 16 -#define UNSIGNED 32 - +#include "dis32031.h" /*************************************************************************** CODE CODE ***************************************************************************/ -#if 0 -static inline char *signed_16bit(int16_t val) -{ - static char temp[10]; - if (val < 0) - sprintf(temp, "-$%x", -val & 0xffff); - else - sprintf(temp, "$%x", val); - return temp; -} -#endif - -static const char *const regname[32] = +const char *const tms32031_disassembler::regname[32] = { "R0", "R1", "R2", "R3", "R4", "R5", "R6", "R7", "AR0", "AR1", "AR2", "AR3", "AR4", "AR5", "AR6", "AR7", @@ -50,7 +23,7 @@ static const char *const regname[32] = "IOF", "RS", "RE", "RC", "??", "??", "??", "??" }; -static const char *const condition[32] = +const char *const tms32031_disassembler::condition[32] = { "U", "LO", "LS", "HI", "HS", "EQ", "NE", "LT", "LE", "GT", "GE", "??", "NV", "V", "NUF", "UF", @@ -122,7 +95,7 @@ static const char *const condition[32] = // 19 = LUF (LUF) // 20 = ZUF (Z | UF) -static void append_indirect(uint8_t ma, int8_t disp, std::ostream &stream) +void tms32031_disassembler::append_indirect(uint8_t ma, int8_t disp, std::ostream &stream) { std::string dispstr; int mode = (ma >> 3) & 0x1f; @@ -172,14 +145,14 @@ static void append_indirect(uint8_t ma, int8_t disp, std::ostream &stream) } } -static std::string get_indirect(uint8_t ma, int8_t disp) +std::string tms32031_disassembler::get_indirect(uint8_t ma, int8_t disp) { std::ostringstream stream; append_indirect(ma, disp, stream); return stream.str(); } -static void append_immediate(uint16_t data, int is_float, int is_unsigned, std::ostream &stream) +void tms32031_disassembler::append_immediate(uint16_t data, int is_float, int is_unsigned, std::ostream &stream) { if (is_float) { @@ -203,7 +176,7 @@ static void append_immediate(uint16_t data, int is_float, int is_unsigned, std:: util::stream_format(stream, "$%04X", data); } -static void disasm_general(const char *opstring, uint32_t op, int flags, std::ostream &stream) +void tms32031_disassembler::disasm_general(const char *opstring, uint32_t op, int flags, std::ostream &stream) { util::stream_format(stream, "%-6s", opstring); @@ -244,7 +217,7 @@ static void disasm_general(const char *opstring, uint32_t op, int flags, std::os } } -static void disasm_3op(const char *opstring, uint32_t op, int flags, std::ostream &stream) +void tms32031_disassembler::disasm_3op(const char *opstring, uint32_t op, int flags, std::ostream &stream) { util::stream_format(stream, "%-6s", opstring); @@ -289,7 +262,7 @@ static void disasm_3op(const char *opstring, uint32_t op, int flags, std::ostrea } } -static void disasm_conditional(const char *opstring, uint32_t op, int flags, std::ostream &stream) +void tms32031_disassembler::disasm_conditional(const char *opstring, uint32_t op, int flags, std::ostream &stream) { char temp[10]; sprintf(temp, "%s%s", opstring, condition[(op >> 23) & 31]); @@ -297,7 +270,7 @@ static void disasm_conditional(const char *opstring, uint32_t op, int flags, std } -static void disasm_parallel_3op3op(const char *opstring1, const char *opstring2, uint32_t op, int flags, const uint8_t *srctable, std::ostream &stream) +void tms32031_disassembler::disasm_parallel_3op3op(const char *opstring1, const char *opstring2, uint32_t op, int flags, const uint8_t *srctable, std::ostream &stream) { const uint8_t *s = &srctable[((op >> 24) & 3) * 4]; int d1 = (op >> 23) & 1; @@ -315,7 +288,7 @@ static void disasm_parallel_3op3op(const char *opstring1, const char *opstring2, } -static void disasm_parallel_3opstore(const char *opstring1, const char *opstring2, uint32_t op, int flags, std::ostream &stream) +void tms32031_disassembler::disasm_parallel_3opstore(const char *opstring1, const char *opstring2, uint32_t op, int flags, std::ostream &stream) { int d1 = (op >> 22) & 7; int s1 = (op >> 19) & 7; @@ -335,7 +308,7 @@ static void disasm_parallel_3opstore(const char *opstring1, const char *opstring } -static void disasm_parallel_loadload(const char *opstring1, const char *opstring2, uint32_t op, int flags, std::ostream &stream) +void tms32031_disassembler::disasm_parallel_loadload(const char *opstring1, const char *opstring2, uint32_t op, int flags, std::ostream &stream) { int d2 = (op >> 22) & 7; int d1 = (op >> 19) & 7; @@ -349,7 +322,7 @@ static void disasm_parallel_loadload(const char *opstring1, const char *opstring } -static void disasm_parallel_storestore(const char *opstring1, const char *opstring2, uint32_t op, int flags, std::ostream &stream) +void tms32031_disassembler::disasm_parallel_storestore(const char *opstring1, const char *opstring2, uint32_t op, int flags, std::ostream &stream) { int s2 = (op >> 22) & 7; int s1 = (op >> 16) & 7; @@ -364,9 +337,10 @@ static void disasm_parallel_storestore(const char *opstring1, const char *opstri -static unsigned dasm_tms3203x(std::ostream &stream, unsigned pc, uint32_t op) +offs_t tms32031_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { uint32_t flags = 0; + uint32_t op = opcodes.r32(pc); switch (op >> 23) { @@ -485,7 +459,7 @@ static unsigned dasm_tms3203x(std::ostream &stream, unsigned pc, uint32_t op) case 0x0c4: case 0x0c5: util::stream_format(stream, "CALL $%06X", op & 0xffffff); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; @@ -537,7 +511,7 @@ static unsigned dasm_tms3203x(std::ostream &stream, unsigned pc, uint32_t op) char temp[10]; sprintf(temp, "CALL%s", condition[(op >> 16) & 31]); util::stream_format(stream, "%-6s%s", temp, regname[op & 31]); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; } @@ -546,7 +520,7 @@ static unsigned dasm_tms3203x(std::ostream &stream, unsigned pc, uint32_t op) char temp[10]; sprintf(temp, "CALL%s", condition[(op >> 16) & 31]); util::stream_format(stream, "%-6s$%06X", temp, (pc + 1 + (int16_t)op) & 0xffffff); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; } @@ -556,19 +530,19 @@ static unsigned dasm_tms3203x(std::ostream &stream, unsigned pc, uint32_t op) char temp[10]; sprintf(temp, "TRAP%s", condition[(op >> 16) & 31]); util::stream_format(stream, "%-6s$%02X", temp, op & 31); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; } case 0x0f0: util::stream_format(stream, "RETI%s", condition[(op >> 16) & 31]); - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; case 0x0f1: util::stream_format(stream, "RETS%s", condition[(op >> 16) & 31]); - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; @@ -720,12 +694,11 @@ static unsigned dasm_tms3203x(std::ostream &stream, unsigned pc, uint32_t op) break; } - return 1 | flags | DASMFLAG_SUPPORTED; + return 1 | flags | SUPPORTED; } - -CPU_DISASSEMBLE( tms3203x ) +u32 tms32031_disassembler::opcode_alignment() const { - uint32_t op = oprom[0] | (oprom[1] << 8) | (oprom[2] << 16) | (oprom[3] << 24); - return dasm_tms3203x(stream, pc, op); + return 1; } + diff --git a/src/devices/cpu/tms32031/dis32031.h b/src/devices/cpu/tms32031/dis32031.h new file mode 100644 index 00000000000..b6e03e4f31a --- /dev/null +++ b/src/devices/cpu/tms32031/dis32031.h @@ -0,0 +1,51 @@ +// license:BSD-3-Clause +// copyright-holders:Aaron Giles +/*************************************************************************** + + dis32031.c + Disassembler for the portable TMS32C031 emulator. + Written by Aaron Giles + +***************************************************************************/ + +#ifndef MAME_CPU_TMS32031_DIS32031_H +#define MAME_CPU_TMS32031_DIS32031_H + +#pragma once + +class tms32031_disassembler : public util::disasm_interface +{ +public: + tms32031_disassembler() = default; + virtual ~tms32031_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum { + INTEGER = 0, + FLOAT = 1, + NODEST = 2, + NOSOURCE = 4, + NOSOURCE1 = NOSOURCE, + NOSOURCE2 = 8, + SWAPSRCDST = 16, + UNSIGNED = 32 + }; + + static const char *const regname[32]; + static const char *const condition[32]; + void append_indirect(uint8_t ma, int8_t disp, std::ostream &stream); + std::string get_indirect(uint8_t ma, int8_t disp); + void append_immediate(uint16_t data, int is_float, int is_unsigned, std::ostream &stream); + void disasm_general(const char *opstring, uint32_t op, int flags, std::ostream &stream); + void disasm_3op(const char *opstring, uint32_t op, int flags, std::ostream &stream); + void disasm_conditional(const char *opstring, uint32_t op, int flags, std::ostream &stream); + void disasm_parallel_3op3op(const char *opstring1, const char *opstring2, uint32_t op, int flags, const uint8_t *srctable, std::ostream &stream); + void disasm_parallel_3opstore(const char *opstring1, const char *opstring2, uint32_t op, int flags, std::ostream &stream); + void disasm_parallel_loadload(const char *opstring1, const char *opstring2, uint32_t op, int flags, std::ostream &stream); + void disasm_parallel_storestore(const char *opstring1, const char *opstring2, uint32_t op, int flags, std::ostream &stream); +}; + +#endif diff --git a/src/devices/cpu/tms32031/tms32031.cpp b/src/devices/cpu/tms32031/tms32031.cpp index a924791cb71..fd8c92af63e 100644 --- a/src/devices/cpu/tms32031/tms32031.cpp +++ b/src/devices/cpu/tms32031/tms32031.cpp @@ -10,6 +10,7 @@ #include "emu.h" #include "tms32031.h" +#include "dis32031.h" #include "debugger.h" @@ -553,36 +554,13 @@ void tms3203x_device::state_string_export(const device_state_entry &entry, std:: //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t tms3203x_device::disasm_min_opcode_bytes() const -{ - return 4; -} - - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t tms3203x_device::disasm_max_opcode_bytes() const -{ - return 4; -} - - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t tms3203x_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *tms3203x_device::create_disassembler() { - extern CPU_DISASSEMBLE( tms3203x ); - return CPU_DISASSEMBLE_NAME(tms3203x)(this, stream, pc, oprom, opram, options); + return new tms32031_disassembler; } diff --git a/src/devices/cpu/tms32031/tms32031.h b/src/devices/cpu/tms32031/tms32031.h index e654d4f2f5e..fcc05db55bc 100644 --- a/src/devices/cpu/tms32031/tms32031.h +++ b/src/devices/cpu/tms32031/tms32031.h @@ -182,9 +182,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // memory helpers uint32_t ROPCODE(offs_t pc); diff --git a/src/devices/cpu/tms32051/dis32051.cpp b/src/devices/cpu/tms32051/dis32051.cpp index b963781beeb..d634ebd37c4 100644 --- a/src/devices/cpu/tms32051/dis32051.cpp +++ b/src/devices/cpu/tms32051/dis32051.cpp @@ -1,10 +1,11 @@ // license:BSD-3-Clause // copyright-holders:Ville Linde -#include "emu.h" +#include "emu.h" +#include "dis32051.h" -static const char *const zl_condition_codes[] = +const char *const tms32051_disassembler::zl_condition_codes[] = { // bit 3, 2 (ZL), bit 1, 0 (MASK) "", // Z=0, L=0, ZM=0, ZL=0 @@ -25,7 +26,7 @@ static const char *const zl_condition_codes[] = "leq", // Z=1, L=1, ZM=1, ZL=1 }; -static const char *const cv_condition_codes[16] = +const char *const tms32051_disassembler::cv_condition_codes[16] = { "", // V=0, C=0, VM=0, CM=0 "nc", // V=0, C=0, VM=0, CM=1 @@ -45,7 +46,7 @@ static const char *const cv_condition_codes[16] = "c ov", // V=1, C=1, VM=1, CM=1 }; -static const char *const tp_condition_codes[4] = +const char *const tms32051_disassembler::tp_condition_codes[4] = { "bio", "tc", @@ -53,24 +54,13 @@ static const char *const tp_condition_codes[4] = "" }; - -static offs_t npc; -static const uint8_t *rombase; -static offs_t pcbase; - -static std::ostream *output; - -static uint16_t FETCH(void) +uint16_t tms32051_disassembler::FETCH(offs_t &npc, const data_buffer &opcodes) { - uint16_t result = rombase[(npc - pcbase) * 2 + 0] | (rombase[(npc - pcbase) * 2 + 1] << 8); - npc++; - return result; + return opcodes.r16(npc++); } -static char *GET_ADDRESS(int addr_mode, int address) +std::string tms32051_disassembler::GET_ADDRESS(int addr_mode, int address) { - static char buffer[100]; - if (addr_mode) // Indirect addressing { int nar = address & 0x7; @@ -78,48 +68,43 @@ static char *GET_ADDRESS(int addr_mode, int address) switch ((address >> 3) & 0xf) { - case 0x0: sprintf(buffer, "*"); break; - case 0x1: sprintf(buffer, "*, ar%d", nar); break; - case 0x2: sprintf(buffer, "*-"); break; - case 0x3: sprintf(buffer, "*-, ar%d", nar); break; - case 0x4: sprintf(buffer, "*+"); break; - case 0x5: sprintf(buffer, "*+, ar%d", nar); break; - case 0x8: sprintf(buffer, "*br0-"); break; - case 0x9: sprintf(buffer, "*br0-, ar%d", nar); break; - case 0xa: sprintf(buffer, "*0-"); break; - case 0xb: sprintf(buffer, "*0-, ar%d", nar); break; - case 0xc: sprintf(buffer, "*0+"); break; - case 0xd: sprintf(buffer, "*0+, ar%d", nar); break; - case 0xe: sprintf(buffer, "*br0+"); break; - case 0xf: sprintf(buffer, "*br0+, ar%d", nar); break; - - default: sprintf(buffer, "??? (indirect)"); break; + case 0x0: return util::string_format("*"); + case 0x1: return util::string_format("*, ar%d", nar); + case 0x2: return util::string_format("*-"); + case 0x3: return util::string_format("*-, ar%d", nar); + case 0x4: return util::string_format("*+"); + case 0x5: return util::string_format("*+, ar%d", nar); + case 0x8: return util::string_format("*br0-"); + case 0x9: return util::string_format("*br0-, ar%d", nar); + case 0xa: return util::string_format("*0-"); + case 0xb: return util::string_format("*0-, ar%d", nar); + case 0xc: return util::string_format("*0+"); + case 0xd: return util::string_format("*0+, ar%d", nar); + case 0xe: return util::string_format("*br0+"); + case 0xf: return util::string_format("*br0+, ar%d", nar); + + default: return util::string_format("??? (indirect)"); } } else // Direct addressing { - sprintf(buffer, "#%02X", address); + return util::string_format("#%02X", address); } - return buffer; } -static char *GET_SHIFT(int shift) +std::string tms32051_disassembler::GET_SHIFT(int shift) { - static char buffer[100]; - if (shift > 0) { - sprintf(buffer, ", %d", shift); + return util::string_format(", %d", shift); } else { - memset(buffer, 0, sizeof(buffer)); + return ""; } - - return buffer; } -static void print_condition_codes(bool pp, int zl, int cv, int tp) +void tms32051_disassembler::print_condition_codes(bool pp, int zl, int cv, int tp) { if (*(zl_condition_codes[zl]) != 0) { @@ -143,7 +128,7 @@ static void print_condition_codes(bool pp, int zl, int cv, int tp) } } -static void dasm_group_be(uint16_t opcode) +void tms32051_disassembler::dasm_group_be(uint16_t opcode, offs_t &npc, const data_buffer &opcodes) { int subop = opcode & 0xff; @@ -217,19 +202,19 @@ static void dasm_group_be(uint16_t opcode) case 0x7c: case 0x7d: case 0x7e: case 0x7f: util::stream_format(*output, "intr %d", opcode & 0x1f); break; - case 0x80: util::stream_format(*output, "mpy #%04X", FETCH()); break; - case 0x81: util::stream_format(*output, "and #%04X", FETCH() << 16); break; - case 0x82: util::stream_format(*output, "or #%04X", FETCH() << 16); break; - case 0x83: util::stream_format(*output, "xor #%04X", FETCH() << 16); break; - case 0xc4: util::stream_format(*output, "rpt #%04X", FETCH()); break; - case 0xc5: util::stream_format(*output, "rptz #%04X", FETCH()); break; - case 0xc6: util::stream_format(*output, "rptb #%04X", FETCH()); break; + case 0x80: util::stream_format(*output, "mpy #%04X", FETCH(npc, opcodes)); break; + case 0x81: util::stream_format(*output, "and #%04X", FETCH(npc, opcodes) << 16); break; + case 0x82: util::stream_format(*output, "or #%04X", FETCH(npc, opcodes) << 16); break; + case 0x83: util::stream_format(*output, "xor #%04X", FETCH(npc, opcodes) << 16); break; + case 0xc4: util::stream_format(*output, "rpt #%04X", FETCH(npc, opcodes)); break; + case 0xc5: util::stream_format(*output, "rptz #%04X", FETCH(npc, opcodes)); break; + case 0xc6: util::stream_format(*output, "rptb #%04X", FETCH(npc, opcodes)); break; default: util::stream_format(*output, "??? (group be)"); break; } } -static void dasm_group_bf(uint16_t opcode) +void tms32051_disassembler::dasm_group_bf(uint16_t opcode, offs_t &npc, const data_buffer &opcodes) { int subop = (opcode >> 4) & 0xf; int shift = opcode & 0xf; @@ -240,7 +225,7 @@ static void dasm_group_bf(uint16_t opcode) { if (opcode & 0x8) { - util::stream_format(*output, "lar ar%d, #%04X", opcode & 0x7, FETCH()); + util::stream_format(*output, "lar ar%d, #%04X", opcode & 0x7, FETCH(npc, opcodes)); } else { @@ -261,31 +246,34 @@ static void dasm_group_bf(uint16_t opcode) break; } - case 0x8: util::stream_format(*output, "lacc #%04X", FETCH() << shift); break; - case 0x9: util::stream_format(*output, "add #%04X", FETCH() << shift); break; - case 0xa: util::stream_format(*output, "sub #%04X", FETCH() << shift); break; - case 0xb: util::stream_format(*output, "and #%04X", FETCH() << shift); break; - case 0xc: util::stream_format(*output, "or #%04X", FETCH() << shift); break; - case 0xd: util::stream_format(*output, "xor #%04X", FETCH() << shift); break; + case 0x8: util::stream_format(*output, "lacc #%04X", FETCH(npc, opcodes) << shift); break; + case 0x9: util::stream_format(*output, "add #%04X", FETCH(npc, opcodes) << shift); break; + case 0xa: util::stream_format(*output, "sub #%04X", FETCH(npc, opcodes) << shift); break; + case 0xb: util::stream_format(*output, "and #%04X", FETCH(npc, opcodes) << shift); break; + case 0xc: util::stream_format(*output, "or #%04X", FETCH(npc, opcodes) << shift); break; + case 0xd: util::stream_format(*output, "xor #%04X", FETCH(npc, opcodes) << shift); break; case 0xe: util::stream_format(*output, "bsar %d", shift+1); break; default: util::stream_format(*output, "??? (group bf)"); break; } } -CPU_DISASSEMBLE(tms32051) +u32 tms32051_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t tms32051_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { uint32_t flags = 0; uint16_t opcode; int baseop; int address, addr_mode; - pcbase = pc; - rombase = oprom; - npc = pc; + offs_t npc = pc; output = &stream; - opcode = FETCH(); + opcode = FETCH(npc, opcodes); baseop = (opcode >> 8) & 0xff; addr_mode = (opcode >> 7) & 0x1; @@ -300,10 +288,10 @@ CPU_DISASSEMBLE(tms32051) break; } case 0x08: util::stream_format(*output, "lamm %s", GET_ADDRESS(addr_mode, address)); break; - case 0x09: util::stream_format(*output, "smmr %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH()); break; + case 0x09: util::stream_format(*output, "smmr %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH(npc, opcodes)); break; case 0x0a: util::stream_format(*output, "subc %s", GET_ADDRESS(addr_mode, address)); break; case 0x0b: util::stream_format(*output, "rpt %s", GET_ADDRESS(addr_mode, address)); break; - case 0x0c: util::stream_format(*output, "out %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH()); break; + case 0x0c: util::stream_format(*output, "out %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH(npc, opcodes)); break; case 0x0d: util::stream_format(*output, "ldp %s", GET_ADDRESS(addr_mode, address)); break; case 0x0e: util::stream_format(*output, "lst 0, %s", GET_ADDRESS(addr_mode, address)); break; case 0x0f: util::stream_format(*output, "lst 1, %s", GET_ADDRESS(addr_mode, address)); break; @@ -355,10 +343,10 @@ CPU_DISASSEMBLE(tms32051) case 0x59: util::stream_format(*output, "opl %s", GET_ADDRESS(addr_mode, address)); break; case 0x5a: util::stream_format(*output, "apl %s", GET_ADDRESS(addr_mode, address)); break; case 0x5b: util::stream_format(*output, "cpl %s", GET_ADDRESS(addr_mode, address)); break; - case 0x5c: util::stream_format(*output, "xpl %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH()); break; - case 0x5d: util::stream_format(*output, "opl %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH()); break; - case 0x5e: util::stream_format(*output, "apl %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH()); break; - case 0x5f: util::stream_format(*output, "cpl %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH()); break; + case 0x5c: util::stream_format(*output, "xpl %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH(npc, opcodes)); break; + case 0x5d: util::stream_format(*output, "opl %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH(npc, opcodes)); break; + case 0x5e: util::stream_format(*output, "apl %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH(npc, opcodes)); break; + case 0x5f: util::stream_format(*output, "cpl %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH(npc, opcodes)); break; case 0x60: util::stream_format(*output, "addc %s", GET_ADDRESS(addr_mode, address)); break; case 0x61: util::stream_format(*output, "add %s << 16", GET_ADDRESS(addr_mode, address)); break; @@ -386,13 +374,13 @@ CPU_DISASSEMBLE(tms32051) case 0x76: util::stream_format(*output, "pshd %s", GET_ADDRESS(addr_mode, address)); break; case 0x77: util::stream_format(*output, "dmov %s", GET_ADDRESS(addr_mode, address)); break; case 0x78: util::stream_format(*output, "adrk #%02X", opcode & 0xff); break; - case 0x79: util::stream_format(*output, "b %04X, %s", FETCH(), GET_ADDRESS(1, address)); break; - case 0x7a: util::stream_format(*output, "call %04X, %s", FETCH(), GET_ADDRESS(1, address)); flags = DASMFLAG_STEP_OVER; break; - case 0x7b: util::stream_format(*output, "banz %04X, %s", FETCH(), GET_ADDRESS(1, address)); break; + case 0x79: util::stream_format(*output, "b %04X, %s", FETCH(npc, opcodes), GET_ADDRESS(1, address)); break; + case 0x7a: util::stream_format(*output, "call %04X, %s", FETCH(npc, opcodes), GET_ADDRESS(1, address)); flags = STEP_OVER; break; + case 0x7b: util::stream_format(*output, "banz %04X, %s", FETCH(npc, opcodes), GET_ADDRESS(1, address)); break; case 0x7c: util::stream_format(*output, "sbrk #%02X", opcode & 0xff); break; - case 0x7d: util::stream_format(*output, "bd %04X, %s", FETCH(), GET_ADDRESS(1, address)); break; - case 0x7e: util::stream_format(*output, "calld %04X, %s", FETCH(), GET_ADDRESS(1, address)); flags = DASMFLAG_STEP_OVER; break; - case 0x7f: util::stream_format(*output, "banzd %04X, %s", FETCH(), GET_ADDRESS(1, address)); break; + case 0x7d: util::stream_format(*output, "bd %04X, %s", FETCH(npc, opcodes), GET_ADDRESS(1, address)); break; + case 0x7e: util::stream_format(*output, "calld %04X, %s", FETCH(npc, opcodes), GET_ADDRESS(1, address)); flags = STEP_OVER; break; + case 0x7f: util::stream_format(*output, "banzd %04X, %s", FETCH(npc, opcodes), GET_ADDRESS(1, address)); break; case 0x80: case 0x81: case 0x82: case 0x83: case 0x84: case 0x85: case 0x86: case 0x87: @@ -401,7 +389,7 @@ CPU_DISASSEMBLE(tms32051) break; } case 0x88: util::stream_format(*output, "samm %s", GET_ADDRESS(addr_mode, address)); break; - case 0x89: util::stream_format(*output, "lmmr %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH()); break; + case 0x89: util::stream_format(*output, "lmmr %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH(npc, opcodes)); break; case 0x8a: util::stream_format(*output, "popd %s", GET_ADDRESS(addr_mode, address)); break; case 0x8b: { @@ -433,21 +421,21 @@ CPU_DISASSEMBLE(tms32051) break; } - case 0xa0: util::stream_format(*output, "norm %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH()); break; - case 0xa2: util::stream_format(*output, "mac %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH()); break; + case 0xa0: util::stream_format(*output, "norm %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH(npc, opcodes)); break; + case 0xa2: util::stream_format(*output, "mac %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH(npc, opcodes)); break; case 0xa3: util::stream_format(*output, "macd %s", GET_ADDRESS(addr_mode, address)); break; case 0xa4: util::stream_format(*output, "blpd %s", GET_ADDRESS(addr_mode, address)); break; - case 0xa5: util::stream_format(*output, "blpd %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH()); break; + case 0xa5: util::stream_format(*output, "blpd %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH(npc, opcodes)); break; case 0xa6: util::stream_format(*output, "tblr %s", GET_ADDRESS(addr_mode, address)); break; case 0xa7: util::stream_format(*output, "tblw %s", GET_ADDRESS(addr_mode, address)); break; - case 0xa8: util::stream_format(*output, "bldd %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH()); break; - case 0xa9: util::stream_format(*output, "bldd %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH()); break; + case 0xa8: util::stream_format(*output, "bldd %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH(npc, opcodes)); break; + case 0xa9: util::stream_format(*output, "bldd %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH(npc, opcodes)); break; case 0xaa: util::stream_format(*output, "mads %s", GET_ADDRESS(addr_mode, address)); break; case 0xab: util::stream_format(*output, "madd %s", GET_ADDRESS(addr_mode, address)); break; case 0xac: util::stream_format(*output, "bldd %s", GET_ADDRESS(addr_mode, address)); break; case 0xad: util::stream_format(*output, "bldd %s", GET_ADDRESS(addr_mode, address)); break; - case 0xae: util::stream_format(*output, "splk %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH()); break; - case 0xaf: util::stream_format(*output, "in %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH()); break; + case 0xae: util::stream_format(*output, "splk %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH(npc, opcodes)); break; + case 0xaf: util::stream_format(*output, "in %s, #%04X", GET_ADDRESS(addr_mode, address), FETCH(npc, opcodes)); break; case 0xb0: case 0xb1: case 0xb2: case 0xb3: case 0xb4: case 0xb5: case 0xb6: case 0xb7: @@ -466,8 +454,8 @@ CPU_DISASSEMBLE(tms32051) util::stream_format(*output, "ldp #%03X", opcode & 0x1ff); break; } - case 0xbe: dasm_group_be(opcode); break; - case 0xbf: dasm_group_bf(opcode); break; + case 0xbe: dasm_group_be(opcode, npc, opcodes); break; + case 0xbf: dasm_group_bf(opcode, npc, opcodes); break; case 0xe0: case 0xe1: case 0xe2: case 0xe3: { @@ -477,7 +465,7 @@ CPU_DISASSEMBLE(tms32051) int cv = ((zlcv << 2) & 0xc) | (zlcvmask & 0x3); int tp = (opcode >> 8) & 0x3; - util::stream_format(*output, "bcnd %04X", FETCH()); + util::stream_format(*output, "bcnd %04X", FETCH(npc, opcodes)); print_condition_codes(true, zl, cv, tp); break; } @@ -505,7 +493,7 @@ CPU_DISASSEMBLE(tms32051) int cv = ((zlcv << 2) & 0xc) | (zlcvmask & 0x3); int tp = (opcode >> 8) & 0x3; - util::stream_format(*output, "cc %04X", FETCH()); + util::stream_format(*output, "cc %04X", FETCH(npc, opcodes)); print_condition_codes(true, zl, cv, tp); break; } @@ -527,7 +515,7 @@ CPU_DISASSEMBLE(tms32051) util::stream_format(*output, "retc "); print_condition_codes(false, zl, cv, tp); } - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; } @@ -539,7 +527,7 @@ CPU_DISASSEMBLE(tms32051) int cv = ((zlcv << 2) & 0xc) | (zlcvmask & 0x3); int tp = (opcode >> 8) & 0x3; - util::stream_format(*output, "bcndd %04X", FETCH()); + util::stream_format(*output, "bcndd %04X", FETCH(npc, opcodes)); print_condition_codes(true, zl, cv, tp); break; } @@ -552,7 +540,7 @@ CPU_DISASSEMBLE(tms32051) int cv = ((zlcv << 2) & 0xc) | (zlcvmask & 0x3); int tp = (opcode >> 8) & 0x3; - util::stream_format(*output, "ccd %04X", FETCH()); + util::stream_format(*output, "ccd %04X", FETCH(npc, opcodes)); print_condition_codes(true, zl, cv, tp); break; } @@ -574,12 +562,12 @@ CPU_DISASSEMBLE(tms32051) util::stream_format(*output, "retcd "); print_condition_codes(false, zl, cv, tp); } - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; } default: util::stream_format(*output, "??? ($%04X)", opcode); break; } - return (npc-pc) | flags | DASMFLAG_SUPPORTED; + return (npc-pc) | flags | SUPPORTED; } diff --git a/src/devices/cpu/tms32051/dis32051.h b/src/devices/cpu/tms32051/dis32051.h new file mode 100644 index 00000000000..dd170859bf3 --- /dev/null +++ b/src/devices/cpu/tms32051/dis32051.h @@ -0,0 +1,32 @@ +// license:BSD-3-Clause +// copyright-holders:Ville Linde + +#ifndef MAME_CPU_TMS32051_DIS32051_H +#define MAME_CPU_TMS32051_DIS32051_H + +#pragma once + +class tms32051_disassembler : public util::disasm_interface +{ +public: + tms32051_disassembler() = default; + virtual ~tms32051_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *const zl_condition_codes[]; + static const char *const cv_condition_codes[16]; + static const char *const tp_condition_codes[4]; + uint16_t FETCH(offs_t &npc, const data_buffer &opcodes); + std::string GET_ADDRESS(int addr_mode, int address); + std::string GET_SHIFT(int shift); + void print_condition_codes(bool pp, int zl, int cv, int tp); + void dasm_group_be(uint16_t opcode, offs_t &npc, const data_buffer &opcodes); + void dasm_group_bf(uint16_t opcode, offs_t &npc, const data_buffer &opcodes); + + std::ostream *output; +}; + +#endif diff --git a/src/devices/cpu/tms32051/tms32051.cpp b/src/devices/cpu/tms32051/tms32051.cpp index 22abad952ff..f1a38012f24 100644 --- a/src/devices/cpu/tms32051/tms32051.cpp +++ b/src/devices/cpu/tms32051/tms32051.cpp @@ -8,6 +8,7 @@ #include "emu.h" #include "tms32051.h" +#include "dis32051.h" #include "debugger.h" enum @@ -117,10 +118,9 @@ tms32053_device::tms32053_device(const machine_config &mconfig, const char *tag, } -offs_t tms32051_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *tms32051_device::create_disassembler() { - extern CPU_DISASSEMBLE( tms32051 ); - return CPU_DISASSEMBLE_NAME(tms32051)(this, stream, pc, oprom, opram, options); + return new tms32051_disassembler; } diff --git a/src/devices/cpu/tms32051/tms32051.h b/src/devices/cpu/tms32051/tms32051.h index 880741f5a66..bd365dc4da2 100644 --- a/src/devices/cpu/tms32051/tms32051.h +++ b/src/devices/cpu/tms32051/tms32051.h @@ -80,9 +80,7 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; address_space_config m_program_config; address_space_config m_data_config; diff --git a/src/devices/cpu/tms32082/dis_mp.cpp b/src/devices/cpu/tms32082/dis_mp.cpp index 0bb6e45d2c5..75c63543256 100644 --- a/src/devices/cpu/tms32082/dis_mp.cpp +++ b/src/devices/cpu/tms32082/dis_mp.cpp @@ -3,12 +3,12 @@ // TMS32082 MP Disassembler #include "emu.h" - +#include "dis_mp.h" #define SIMM15(v) (int32_t)((v & 0x4000) ? (v | 0xffffe000) : (v)) #define UIMM15(v) (v) -static const char *BCND_CONDITION[32] = +const char *tms32082_mp_disassembler::BCND_CONDITION[32] = { "nev.b", "gt0.b", "eq0.b", "ge0.b", "lt0.b", "ne0.b", "le0.b", "alw.b", "nev.h", "gt0.h", "eq0.h", "ge0.h", "lt0.h", "ne0.h", "le0.h", "alw.h", @@ -16,7 +16,7 @@ static const char *BCND_CONDITION[32] = "nev.d", "gt0.d", "eq0.d", "ge0.d", "lt0.d", "ne0.d", "le0.d", "alw.d", }; -static const char *BITNUM_CONDITION[32] = +const char *tms32082_mp_disassembler::BITNUM_CONDITION[32] = { "eq.b", "ne.b", "gt.b", "le.b", "lt.b", "ge.b", "hi.b", "ls.b", "lo.b", "hs.b", "eq.h", "ne.h", "gt.h", "le.h", "lt.h", "ge.h", @@ -24,87 +24,75 @@ static const char *BITNUM_CONDITION[32] = "lt.w", "ge.w", "hi.w", "ls.w", "lo.w", "hs.w", "?", "?", }; -static const char *MEMOP_S[2] = +const char *tms32082_mp_disassembler::MEMOP_S[2] = { ":s", "" }; -static const char *MEMOP_M[2] = +const char *tms32082_mp_disassembler::MEMOP_M[2] = { ":m", "" }; -static const char *FLOATOP_PRECISION[4] = +const char *tms32082_mp_disassembler::FLOATOP_PRECISION[4] = { "s", "d", "i", "u" }; -static const char *ACC_SEL[4] = +const char *tms32082_mp_disassembler::ACC_SEL[4] = { "A0", "A1", "A2", "A3" }; -static const char *FLOATOP_ROUND[4] = +const char *tms32082_mp_disassembler::FLOATOP_ROUND[4] = { "n", "z", "p", "m" }; -static std::ostream *output; -static const uint8_t *opdata; -static int opbytes; - -static uint32_t fetch(void) +uint32_t tms32082_mp_disassembler::fetch(offs_t &pos, const data_buffer &opcodes) { - uint32_t d = ((uint32_t)(opdata[0]) << 24) | ((uint32_t)(opdata[1]) << 16) | ((uint32_t)(opdata[2]) << 8) | opdata[3]; - opdata += 4; - opbytes += 4; + uint32_t d = opcodes.r32(pos); + pos += 4; return d; } -static char* get_creg_name(uint32_t reg) +std::string tms32082_mp_disassembler::get_creg_name(uint32_t reg) { - static char buffer[64]; - switch (reg) { - case 0x0000: sprintf(buffer, "EPC"); break; - case 0x0001: sprintf(buffer, "EIP"); break; - case 0x0002: sprintf(buffer, "CONFIG"); break; - case 0x0004: sprintf(buffer, "INTPEN"); break; - case 0x0006: sprintf(buffer, "IE"); break; - case 0x0008: sprintf(buffer, "FPST"); break; - case 0x000a: sprintf(buffer, "PPERROR"); break; - case 0x000d: sprintf(buffer, "PKTREQ"); break; - case 0x000e: sprintf(buffer, "TCOUNT"); break; - case 0x000f: sprintf(buffer, "TSCALE"); break; - case 0x0010: sprintf(buffer, "FLTOP"); break; - case 0x0011: sprintf(buffer, "FLTADR"); break; - case 0x0012: sprintf(buffer, "FLTTAG"); break; - case 0x0013: sprintf(buffer, "FLTDTL"); break; - case 0x0014: sprintf(buffer, "FLTDTH"); break; - case 0x0020: sprintf(buffer, "SYSSTK"); break; - case 0x0021: sprintf(buffer, "SYSTMP"); break; - case 0x0030: sprintf(buffer, "MPC"); break; - case 0x0031: sprintf(buffer, "MIP"); break; - case 0x0033: sprintf(buffer, "ECOMCNTL"); break; - case 0x0034: sprintf(buffer, "ANASTAT"); break; - case 0x0039: sprintf(buffer, "BRK1"); break; - case 0x003a: sprintf(buffer, "BRK2"); break; - case 0x4000: sprintf(buffer, "IN0P"); break; - case 0x4001: sprintf(buffer, "IN1P"); break; - case 0x4002: sprintf(buffer, "OUTP"); break; - default: sprintf(buffer, "CR %04X", reg); + case 0x0000: return "EPC"; + case 0x0001: return "EIP"; + case 0x0002: return "CONFIG"; + case 0x0004: return "INTPEN"; + case 0x0006: return "IE"; + case 0x0008: return "FPST"; + case 0x000a: return "PPERROR"; + case 0x000d: return "PKTREQ"; + case 0x000e: return "TCOUNT"; + case 0x000f: return "TSCALE"; + case 0x0010: return "FLTOP"; + case 0x0011: return "FLTADR"; + case 0x0012: return "FLTTAG"; + case 0x0013: return "FLTDTL"; + case 0x0014: return "FLTDTH"; + case 0x0020: return "SYSSTK"; + case 0x0021: return "SYSTMP"; + case 0x0030: return "MPC"; + case 0x0031: return "MIP"; + case 0x0033: return "ECOMCNTL"; + case 0x0034: return "ANASTAT"; + case 0x0039: return "BRK1"; + case 0x003a: return "BRK2"; + case 0x4000: return "IN0P"; + case 0x4001: return "IN1P"; + case 0x4002: return "OUTP"; + default: return util::string_format("CR %04X", reg); } - - return buffer; } -static char* format_vector_op(uint32_t op, uint32_t imm32) +std::string tms32082_mp_disassembler::format_vector_op(uint32_t op, uint32_t imm32) { - static char buffer[256]; - static char dest[64]; - char *b = buffer; - + std::string result; int rd = (op >> 27) & 0x1f; int rs = (op >> 22) & 0x1f; int src1 = (op & 0x1f); @@ -121,85 +109,87 @@ static char* format_vector_op(uint32_t op, uint32_t imm32) bool regdest = (op & (1 << 10)) == 0 && (op & (1 << 6)) == 0; // accumulator or register destination - if (regdest) - sprintf(dest, "R%d", rd); - else - sprintf(dest, "A%d", acc); + std::string dest = regdest ? util::string_format("R%d", rd) : util::string_format("A%d", acc); // base op switch (subop) { - case 0xc0: b += sprintf(b, "vadd.%s%s R%d, R%d, R%d", FLOATOP_PRECISION[p1], FLOATOP_PRECISION[pd2], src1, rs, rs); break; - case 0xc1: b += sprintf(b, "vadd.%s%s 0x%08X, R%d, R%d", FLOATOP_PRECISION[p1], FLOATOP_PRECISION[pd2], imm32, rs, rs); break; - case 0xc2: b += sprintf(b, "vsub.%s%s R%d, R%d, R%d", FLOATOP_PRECISION[p1], FLOATOP_PRECISION[pd2], rs, src1, rs); break; - case 0xc3: b += sprintf(b, "vsub.%s%s R%d, 0x%08X, R%d", FLOATOP_PRECISION[p1], FLOATOP_PRECISION[pd2], rs, imm32, rs); break; - case 0xc4: b += sprintf(b, "vmpy.%s%s R%d, R%d, R%d", FLOATOP_PRECISION[p1], FLOATOP_PRECISION[pd2], src1, rs, rs); break; - case 0xc5: b += sprintf(b, "vmpy.%s%s 0x%08X, R%d, R%d", FLOATOP_PRECISION[p1], FLOATOP_PRECISION[pd2], imm32, rs, rs); break; + case 0xc0: result += util::string_format("vadd.%s%s R%d, R%d, R%d", FLOATOP_PRECISION[p1], FLOATOP_PRECISION[pd2], src1, rs, rs); break; + case 0xc1: result += util::string_format("vadd.%s%s 0x%08X, R%d, R%d", FLOATOP_PRECISION[p1], FLOATOP_PRECISION[pd2], imm32, rs, rs); break; + case 0xc2: result += util::string_format("vsub.%s%s R%d, R%d, R%d", FLOATOP_PRECISION[p1], FLOATOP_PRECISION[pd2], rs, src1, rs); break; + case 0xc3: result += util::string_format("vsub.%s%s R%d, 0x%08X, R%d", FLOATOP_PRECISION[p1], FLOATOP_PRECISION[pd2], rs, imm32, rs); break; + case 0xc4: result += util::string_format("vmpy.%s%s R%d, R%d, R%d", FLOATOP_PRECISION[p1], FLOATOP_PRECISION[pd2], src1, rs, rs); break; + case 0xc5: result += util::string_format("vmpy.%s%s 0x%08X, R%d, R%d", FLOATOP_PRECISION[p1], FLOATOP_PRECISION[pd2], imm32, rs, rs); break; case 0xd6: case 0xc6: - b += sprintf(b, "vmsub.s%s R%d, %s, R%d", FLOATOP_PRECISION[pd2], src1, z ? "0" : ACC_SEL[acc], rs); + result += util::string_format("vmsub.s%s R%d, %s, R%d", FLOATOP_PRECISION[pd2], src1, z ? "0" : ACC_SEL[acc], rs); break; case 0xd7: case 0xc7: - b += sprintf(b, "vmsub.s%s 0x%08X, %s, R%d", FLOATOP_PRECISION[pd2], imm32, z ? "0" : ACC_SEL[acc], rs); + result += util::string_format("vmsub.s%s 0x%08X, %s, R%d", FLOATOP_PRECISION[pd2], imm32, z ? "0" : ACC_SEL[acc], rs); break; case 0xd8: case 0xc8: - b += sprintf(b, "vrnd.%s%s R%d, R%d", FLOATOP_PRECISION[p1], FLOATOP_PRECISION[pd4], src1, rs); + result += util::string_format("vrnd.%s%s R%d, R%d", FLOATOP_PRECISION[p1], FLOATOP_PRECISION[pd4], src1, rs); break; case 0xd9: case 0xc9: - b += sprintf(b, "vrnd.%s%s 0x%08X, R%d", FLOATOP_PRECISION[p1], FLOATOP_PRECISION[pd4], imm32, rs); + result += util::string_format("vrnd.%s%s 0x%08X, R%d", FLOATOP_PRECISION[p1], FLOATOP_PRECISION[pd4], imm32, rs); break; - case 0xca: b += sprintf(b, "vrnd.%s%s R%d, R%d", FLOATOP_PRECISION[2 + p1], FLOATOP_PRECISION[pd2],src1, rs); break; - case 0xcb: b += sprintf(b, "vrnd.%s%s 0x%08X, R%d", FLOATOP_PRECISION[2 + p1], FLOATOP_PRECISION[pd2], imm32, rs); break; + case 0xca: result += util::string_format("vrnd.%s%s R%d, R%d", FLOATOP_PRECISION[2 + p1], FLOATOP_PRECISION[pd2],src1, rs); break; + case 0xcb: result += util::string_format("vrnd.%s%s 0x%08X, R%d", FLOATOP_PRECISION[2 + p1], FLOATOP_PRECISION[pd2], imm32, rs); break; case 0xcc: case 0xdc: - b += sprintf(b, "vmac.ss%s R%d, R%d, %s, %s", FLOATOP_PRECISION[(op >> 9) & 1], src1, rs, z ? "0" : ACC_SEL[acc], (regdest && rd == 0) ? ACC_SEL[acc] : dest); + result += util::string_format("vmac.ss%s R%d, R%d, %s, %s", FLOATOP_PRECISION[(op >> 9) & 1], src1, rs, z ? "0" : ACC_SEL[acc], (regdest && rd == 0) ? ACC_SEL[acc] : dest); break; case 0xcd: case 0xdd: - b += sprintf(b, "vmac.ss%s 0x%08X, R%d, %s, %s", FLOATOP_PRECISION[(op >> 9) & 1], imm32, rs, z ? "0" : ACC_SEL[acc], (regdest && rd == 0) ? ACC_SEL[acc] : dest); + result += util::string_format("vmac.ss%s 0x%08X, R%d, %s, %s", FLOATOP_PRECISION[(op >> 9) & 1], imm32, rs, z ? "0" : ACC_SEL[acc], (regdest && rd == 0) ? ACC_SEL[acc] : dest); break; case 0xce: case 0xde: - b += sprintf(b, "vmsc.ss%s R%d, R%d, %s, %s", FLOATOP_PRECISION[(op >> 9) & 1], src1, rs, z ? "0" : ACC_SEL[acc], (regdest && rd == 0) ? ACC_SEL[acc] : dest); + result += util::string_format("vmsc.ss%s R%d, R%d, %s, %s", FLOATOP_PRECISION[(op >> 9) & 1], src1, rs, z ? "0" : ACC_SEL[acc], (regdest && rd == 0) ? ACC_SEL[acc] : dest); break; case 0xcf: case 0xdf: - b += sprintf(b, "vmsc.ss%s 0x%08X, R%d, %s, %s", FLOATOP_PRECISION[(op >> 9) & 1], imm32, rs, z ? "0" : ACC_SEL[acc], (regdest && rd == 0) ? ACC_SEL[acc] : dest); + result += util::string_format("vmsc.ss%s 0x%08X, R%d, %s, %s", FLOATOP_PRECISION[(op >> 9) & 1], imm32, rs, z ? "0" : ACC_SEL[acc], (regdest && rd == 0) ? ACC_SEL[acc] : dest); break; - default: b += sprintf(b, "?"); break; + default: result += '?'; break; } // align the line end - int len = strlen(buffer); + int len = result.size(); if (len < 30) { for (int i=0; i < (30-len); i++) { - b += sprintf(b, " "); + result += ' '; } } // optional load/store op switch (vector_ls_bits) { - case 0x01: b += sprintf(b, "|| vst.s R%d", rd); break; - case 0x03: b += sprintf(b, "|| vst.d R%d", rd); break; - case 0x04: b += sprintf(b, "|| vld0.s R%d", rd); break; - case 0x05: b += sprintf(b, "|| vld1.s R%d", rd); break; - case 0x06: b += sprintf(b, "|| vld0.d R%d", rd); break; - case 0x07: b += sprintf(b, "|| vld1.d R%d", rd); break; + case 0x01: result += util::string_format("|| vst.s R%d", rd); break; + case 0x03: result += util::string_format("|| vst.d R%d", rd); break; + case 0x04: result += util::string_format("|| vld0.s R%d", rd); break; + case 0x05: result += util::string_format("|| vld1.s R%d", rd); break; + case 0x06: result += util::string_format("|| vld0.d R%d", rd); break; + case 0x07: result += util::string_format("|| vld1.d R%d", rd); break; } - return buffer; + return result; +} + + +u32 tms32082_mp_disassembler::opcode_alignment() const +{ + return 4; } -static offs_t tms32082_disasm_mp(std::ostream &stream, offs_t pc, const uint8_t *oprom) +offs_t tms32082_mp_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { output = &stream; - opdata = oprom; - opbytes = 0; + offs_t pos = pc; uint32_t flags = 0; - uint32_t op = fetch(); + uint32_t op = fetch(pos, opcodes); int rd = (op >> 27) & 0x1f; int link = rd; @@ -310,7 +300,7 @@ static offs_t tms32082_disasm_mp(std::ostream &stream, offs_t pc, const uint8_t uint32_t imm32 = 0; if (op & (1 << 12)) // fetch 32-bit immediate if needed - imm32 = fetch(); + imm32 = fetch(pos, opcodes); int m = op & (1 << 15) ? 0 : 1; int s = op & (1 << 11) ? 0 : 1; @@ -502,10 +492,5 @@ static offs_t tms32082_disasm_mp(std::ostream &stream, offs_t pc, const uint8_t } } - return opbytes | flags | DASMFLAG_SUPPORTED; -} - -CPU_DISASSEMBLE(tms32082_mp) -{ - return tms32082_disasm_mp(stream, pc, oprom); + return (pos - pc) | flags | SUPPORTED; } diff --git a/src/devices/cpu/tms32082/dis_mp.h b/src/devices/cpu/tms32082/dis_mp.h new file mode 100644 index 00000000000..8c3a0721c1a --- /dev/null +++ b/src/devices/cpu/tms32082/dis_mp.h @@ -0,0 +1,35 @@ +// license:BSD-3-Clause +// copyright-holders:Ville Linde +// TMS32082 MP Disassembler + +#ifndef MAME_CPU_TMS32082_DIS_MP_H +#define MAME_CPU_TMS32082_DIS_MP_H + +#pragma once + +class tms32082_mp_disassembler : public util::disasm_interface +{ +public: + tms32082_mp_disassembler() = default; + virtual ~tms32082_mp_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *BCND_CONDITION[32]; + static const char *BITNUM_CONDITION[32]; + static const char *MEMOP_S[2]; + static const char *MEMOP_M[2]; + static const char *FLOATOP_PRECISION[4]; + static const char *ACC_SEL[4]; + static const char *FLOATOP_ROUND[4]; + + std::ostream *output; + + uint32_t fetch(offs_t &pos, const data_buffer &opcodes); + std::string get_creg_name(uint32_t reg); + std::string format_vector_op(uint32_t op, uint32_t imm32); +}; + +#endif diff --git a/src/devices/cpu/tms32082/dis_pp.cpp b/src/devices/cpu/tms32082/dis_pp.cpp index b685ab54b4f..8a3a6475ba0 100644 --- a/src/devices/cpu/tms32082/dis_pp.cpp +++ b/src/devices/cpu/tms32082/dis_pp.cpp @@ -3,9 +3,9 @@ // TMS32082 PP Disassembler #include "emu.h" +#include "dis_pp.h" - -static const char *REG_NAMES[128] = +const char *tms32082_pp_disassembler::REG_NAMES[128] = { // 0 - 15 "a0", "a1", "a2", "a3", "a4", "???", "a6", "a7", @@ -33,7 +33,7 @@ static const char *REG_NAMES[128] = "???", "???", "???", "???", "tag0", "tag1", "tag2", "tag3" }; -static const char *CONDITION_CODES[16] = +const char *tms32082_pp_disassembler::CONDITION_CODES[16] = { "", "[p] ", "[ls] ", "[hi] ", "[lt] ", "[le] ", "[ge] ", "[gt] ", @@ -41,50 +41,40 @@ static const char *CONDITION_CODES[16] = "[v] ", "[nv] ", "[n] ", "[nn] " }; -static const char *TRANSFER_SIZE[4] = +const char *tms32082_pp_disassembler::TRANSFER_SIZE[4] = { "b:", "h:", "w:", "" }; - -static std::ostream *output; - -static char *format_address_mode(int mode, int areg, int s, int limx) +std::string tms32082_pp_disassembler::format_address_mode(int mode, int areg, int s, int limx) { - static char buffer[64]; - - memset(buffer, 0, sizeof(char)*64); - switch (mode) { - case 0x4: sprintf(buffer, "*(a%d++=x%d)", areg, limx); break; - case 0x5: sprintf(buffer, "*(a%d--=x%d)", areg, limx); break; - case 0x6: sprintf(buffer, "*(a%d++0x%04X)", areg, limx); break; - case 0x7: sprintf(buffer, "*(a%d--0x%04X)", areg, limx); break; - case 0x8: sprintf(buffer, "*(a%d+x%d)", areg, limx); break; - case 0x9: sprintf(buffer, "*(a%d-x%d)", areg, limx); break; - case 0xa: sprintf(buffer, "*(a%d+0x%04X)", areg, limx); break; - case 0xb: sprintf(buffer, "*(a%d-0x%04X)", areg, limx); break; - case 0xc: sprintf(buffer, "*(a%d+=x%d)", areg, limx); break; - case 0xd: sprintf(buffer, "*(a%d-=x%d)", areg, limx); break; - case 0xe: sprintf(buffer, "*(a%d+=0x%04X)", areg, limx); break; - case 0xf: sprintf(buffer, "*(a%d-=0x%04X)", areg, limx); break; + case 0x4: return util::string_format("*(a%d++=x%d)", areg, limx); + case 0x5: return util::string_format("*(a%d--=x%d)", areg, limx); + case 0x6: return util::string_format("*(a%d++0x%04X)", areg, limx); + case 0x7: return util::string_format("*(a%d--0x%04X)", areg, limx); + case 0x8: return util::string_format("*(a%d+x%d)", areg, limx); + case 0x9: return util::string_format("*(a%d-x%d)", areg, limx); + case 0xa: return util::string_format("*(a%d+0x%04X)", areg, limx); + case 0xb: return util::string_format("*(a%d-0x%04X)", areg, limx); + case 0xc: return util::string_format("*(a%d+=x%d)", areg, limx); + case 0xd: return util::string_format("*(a%d-=x%d)", areg, limx); + case 0xe: return util::string_format("*(a%d+=0x%04X)", areg, limx); + case 0xf: return util::string_format("*(a%d-=0x%04X)", areg, limx); } - return buffer; + return ""; } -static void format_transfer(uint64_t op) +void tms32082_pp_disassembler::format_transfer(uint64_t op) { - char buffer[128]; - char *b = buffer; + std::string buffer; int lmode = (op >> 35) & 0xf; int gmode = (op >> 13) & 0xf; bool is_nop = false; - memset(buffer, 0, sizeof(char)*128); - switch (lmode) { case 0x0: @@ -106,8 +96,8 @@ static void format_transfer(uint64_t op) int dreg = (dstbank << 3) | dst; int sreg = (srcbank << 3) | src; - b += sprintf(b, "%s", CONDITION_CODES[cond]); - b += sprintf(b, "%s = %s", REG_NAMES[dreg], REG_NAMES[sreg]); + buffer += util::string_format("%s", CONDITION_CODES[cond]); + buffer += util::string_format("%s = %s", REG_NAMES[dreg], REG_NAMES[sreg]); break; } case 0x01: // Format 8: Conditional DU ||Conditional Field Move @@ -122,8 +112,8 @@ static void format_transfer(uint64_t op) int dreg = (dstbank << 3) | dst; int sreg = (4 << 3) | src; - b += sprintf(b, "%s", CONDITION_CODES[cond]); - b += sprintf(b, "%s = [%s%d]%s", REG_NAMES[dreg], TRANSFER_SIZE[size], itm, REG_NAMES[sreg]); + buffer += util::string_format("%s", CONDITION_CODES[cond]); + buffer += util::string_format("%s = [%s%d]%s", REG_NAMES[dreg], TRANSFER_SIZE[size], itm, REG_NAMES[sreg]); break; } case 0x02: case 0x03: // Format 10: Conditional Non-D Data Unit @@ -142,8 +132,8 @@ static void format_transfer(uint64_t op) } else { - b += sprintf(b, "%s", CONDITION_CODES[cond]); - b += sprintf(b, "%s = %s", REG_NAMES[dreg], REG_NAMES[sreg]); + buffer += util::string_format("%s", CONDITION_CODES[cond]); + buffer += util::string_format("%s = %s", REG_NAMES[dreg], REG_NAMES[sreg]); } break; } @@ -161,14 +151,14 @@ static void format_transfer(uint64_t op) int greg = (bank << 3) | reg; - b += sprintf(b, "%s", CONDITION_CODES[cond]); + buffer += util::string_format("%s", CONDITION_CODES[cond]); switch (le) { - case 0: b += sprintf(b, "&%s%s = %s", TRANSFER_SIZE[size], format_address_mode(gmode, ga, s, gimx), REG_NAMES[greg]); break; - case 1: b += sprintf(b, "%s = %s", REG_NAMES[greg], format_address_mode(gmode, ga, s, gimx)); break; - case 2: b += sprintf(b, "%s = &%s%s", REG_NAMES[greg], TRANSFER_SIZE[size], format_address_mode(gmode, ga, s, gimx)); break; - case 3: b += sprintf(b, "%s = &%s%s", REG_NAMES[greg], TRANSFER_SIZE[size], format_address_mode(gmode, ga, s, gimx)); break; + case 0: buffer += util::string_format("&%s%s = %s", TRANSFER_SIZE[size], format_address_mode(gmode, ga, s, gimx), REG_NAMES[greg]); break; + case 1: buffer += util::string_format("%s = %s", REG_NAMES[greg], format_address_mode(gmode, ga, s, gimx)); break; + case 2: buffer += util::string_format("%s = &%s%s", REG_NAMES[greg], TRANSFER_SIZE[size], format_address_mode(gmode, ga, s, gimx)); break; + case 3: buffer += util::string_format("%s = &%s%s", REG_NAMES[greg], TRANSFER_SIZE[size], format_address_mode(gmode, ga, s, gimx)); break; } } else // Format 5: Global (Long Offset) @@ -190,10 +180,10 @@ static void format_transfer(uint64_t op) switch (le) { - case 0: b += sprintf(b, "&%s%s = %s", TRANSFER_SIZE[size], format_address_mode(gmode, ga, s, offset), REG_NAMES[greg]); break; - case 1: b += sprintf(b, "%s = %s", REG_NAMES[greg], format_address_mode(gmode, ga, s, offset)); break; - case 2: b += sprintf(b, "%s = &%s%s", REG_NAMES[greg], TRANSFER_SIZE[size], format_address_mode(gmode, ga, s, offset)); break; - case 3: b += sprintf(b, "%s = &%s%s", REG_NAMES[greg], TRANSFER_SIZE[size], format_address_mode(gmode, ga, s, offset)); break; + case 0: buffer += util::string_format("&%s%s = %s", TRANSFER_SIZE[size], format_address_mode(gmode, ga, s, offset), REG_NAMES[greg]); break; + case 1: buffer += util::string_format("%s = %s", REG_NAMES[greg], format_address_mode(gmode, ga, s, offset)); break; + case 2: buffer += util::string_format("%s = &%s%s", REG_NAMES[greg], TRANSFER_SIZE[size], format_address_mode(gmode, ga, s, offset)); break; + case 3: buffer += util::string_format("%s = &%s%s", REG_NAMES[greg], TRANSFER_SIZE[size], format_address_mode(gmode, ga, s, offset)); break; } } break; @@ -210,12 +200,12 @@ static void format_transfer(uint64_t op) { case 0x00: // Format 2: Move || Local { - b += sprintf(b, "move||local "); + buffer += util::string_format("move||local "); break; } case 0x01: // Format 3: Field Move || Local { - b += sprintf(b, "field move||local "); + buffer += util::string_format("field move||local "); break; } case 0x02: case 0x03: // Format 6: Non-D DU || Local @@ -231,10 +221,10 @@ static void format_transfer(uint64_t op) switch (le) { - case 0: b += sprintf(b, "&%s%s = %s", TRANSFER_SIZE[size], format_address_mode(lmode, la, s, limx), REG_NAMES[reg]); break; - case 1: b += sprintf(b, "%s = %s", REG_NAMES[reg], format_address_mode(lmode, la, s, limx)); break; - case 2: b += sprintf(b, "%s = &%s%s", REG_NAMES[reg], TRANSFER_SIZE[size], format_address_mode(lmode, la, s, limx)); break; - case 3: b += sprintf(b, "%s = &%s%s", REG_NAMES[reg], TRANSFER_SIZE[size], format_address_mode(lmode, la, s, limx)); break; + case 0: buffer += util::string_format("&%s%s = %s", TRANSFER_SIZE[size], format_address_mode(lmode, la, s, limx), REG_NAMES[reg]); break; + case 1: buffer += util::string_format("%s = %s", REG_NAMES[reg], format_address_mode(lmode, la, s, limx)); break; + case 2: buffer += util::string_format("%s = &%s%s", REG_NAMES[reg], TRANSFER_SIZE[size], format_address_mode(lmode, la, s, limx)); break; + case 3: buffer += util::string_format("%s = &%s%s", REG_NAMES[reg], TRANSFER_SIZE[size], format_address_mode(lmode, la, s, limx)); break; } break; } @@ -263,10 +253,10 @@ static void format_transfer(uint64_t op) switch (le) { - case 0: b += sprintf(b, "&%s%s = %s", TRANSFER_SIZE[size], format_address_mode(lmode, la, s, offset), REG_NAMES[reg]); break; - case 1: b += sprintf(b, "%s = %s", REG_NAMES[reg], format_address_mode(lmode, la, s, offset)); break; - case 2: b += sprintf(b, "%s = &%s%s", REG_NAMES[reg], TRANSFER_SIZE[size], format_address_mode(lmode, la, s, offset)); break; - case 3: b += sprintf(b, "%s = &%s%s", REG_NAMES[reg], TRANSFER_SIZE[size], format_address_mode(lmode, la, s, offset)); break; + case 0: buffer += util::string_format("&%s%s = %s", TRANSFER_SIZE[size], format_address_mode(lmode, la, s, offset), REG_NAMES[reg]); break; + case 1: buffer += util::string_format("%s = %s", REG_NAMES[reg], format_address_mode(lmode, la, s, offset)); break; + case 2: buffer += util::string_format("%s = &%s%s", REG_NAMES[reg], TRANSFER_SIZE[size], format_address_mode(lmode, la, s, offset)); break; + case 3: buffer += util::string_format("%s = &%s%s", REG_NAMES[reg], TRANSFER_SIZE[size], format_address_mode(lmode, la, s, offset)); break; } break; } @@ -294,10 +284,10 @@ static void format_transfer(uint64_t op) // local transfer switch (local_le) { - case 0: b += sprintf(b, "&%s%s = %s", TRANSFER_SIZE[local_size], format_address_mode(lmode, la, local_s, local_imx), REG_NAMES[lreg]); break; - case 1: b += sprintf(b, "%s = %s", REG_NAMES[lreg], format_address_mode(lmode, la, local_s, local_imx)); break; - case 2: b += sprintf(b, "%s = &%s%s", REG_NAMES[lreg], TRANSFER_SIZE[local_size], format_address_mode(lmode, la, local_s, local_imx)); break; - case 3: b += sprintf(b, "%s = &%s%s", REG_NAMES[lreg], TRANSFER_SIZE[local_size], format_address_mode(lmode, la, local_s, local_imx)); break; + case 0: buffer += util::string_format("&%s%s = %s", TRANSFER_SIZE[local_size], format_address_mode(lmode, la, local_s, local_imx), REG_NAMES[lreg]); break; + case 1: buffer += util::string_format("%s = %s", REG_NAMES[lreg], format_address_mode(lmode, la, local_s, local_imx)); break; + case 2: buffer += util::string_format("%s = &%s%s", REG_NAMES[lreg], TRANSFER_SIZE[local_size], format_address_mode(lmode, la, local_s, local_imx)); break; + case 3: buffer += util::string_format("%s = &%s%s", REG_NAMES[lreg], TRANSFER_SIZE[local_size], format_address_mode(lmode, la, local_s, local_imx)); break; } util::stream_format(*output, ", "); @@ -305,10 +295,10 @@ static void format_transfer(uint64_t op) // global transfer switch (global_le) { - case 0: b += sprintf(b, "&%s%s = %s", TRANSFER_SIZE[global_size], format_address_mode(gmode, ga, global_s, global_imx), REG_NAMES[greg]); break; - case 1: b += sprintf(b, "%s = %s", REG_NAMES[greg], format_address_mode(gmode, ga, global_s, global_imx)); break; - case 2: b += sprintf(b, "%s = &%s%s", REG_NAMES[greg], TRANSFER_SIZE[global_size], format_address_mode(gmode, ga, global_s, global_imx)); break; - case 3: b += sprintf(b, "%s = &%s%s", REG_NAMES[greg], TRANSFER_SIZE[global_size], format_address_mode(gmode, ga, global_s, global_imx)); break; + case 0: buffer += util::string_format("&%s%s = %s", TRANSFER_SIZE[global_size], format_address_mode(gmode, ga, global_s, global_imx), REG_NAMES[greg]); break; + case 1: buffer += util::string_format("%s = %s", REG_NAMES[greg], format_address_mode(gmode, ga, global_s, global_imx)); break; + case 2: buffer += util::string_format("%s = &%s%s", REG_NAMES[greg], TRANSFER_SIZE[global_size], format_address_mode(gmode, ga, global_s, global_imx)); break; + case 3: buffer += util::string_format("%s = &%s%s", REG_NAMES[greg], TRANSFER_SIZE[global_size], format_address_mode(gmode, ga, global_s, global_imx)); break; } break; } @@ -320,7 +310,7 @@ static void format_transfer(uint64_t op) util::stream_format(*output, " || %s", buffer); } -static void format_alu_op(int aluop, int a, const char *dst_text, const char *a_text, const char *b_text, const char *c_text) +void tms32082_pp_disassembler::format_alu_op(int aluop, int a, const char *dst_text, const char *a_text, const char *b_text, const char *c_text) { if (a) // arithmetic { @@ -409,13 +399,17 @@ static void format_alu_op(int aluop, int a, const char *dst_text, const char *a_ } } -static offs_t tms32082_disasm_pp(std::ostream &stream, offs_t pc, const uint8_t *oprom) +u32 tms32082_pp_disassembler::opcode_alignment() const +{ + return 8; +} + +offs_t tms32082_pp_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { output = &stream; uint32_t flags = 0; - uint64_t op = ((uint64_t)(oprom[0]) << 56) | ((uint64_t)(oprom[1]) << 48) | ((uint64_t)(oprom[2]) << 40) | ((uint64_t)(oprom[3]) << 32) | - ((uint64_t)(oprom[4]) << 24) | ((uint64_t)(oprom[5]) << 16) | ((uint64_t)(oprom[6]) << 8) | ((uint64_t)(oprom[7])); + uint64_t op = opcodes.r64(pc); switch (op >> 60) { @@ -695,10 +689,5 @@ static offs_t tms32082_disasm_pp(std::ostream &stream, offs_t pc, const uint8_t break; } - return 8 | flags | DASMFLAG_SUPPORTED; -} - -CPU_DISASSEMBLE(tms32082_pp) -{ - return tms32082_disasm_pp(stream, pc, oprom); + return 8 | flags | SUPPORTED; } diff --git a/src/devices/cpu/tms32082/dis_pp.h b/src/devices/cpu/tms32082/dis_pp.h new file mode 100644 index 00000000000..6541eeccb70 --- /dev/null +++ b/src/devices/cpu/tms32082/dis_pp.h @@ -0,0 +1,33 @@ +// license:BSD-3-Clause +// copyright-holders:Ville Linde +// TMS32082 PP Disassembler + +#ifndef MAME_CPU_TMS32082_DIS_PP_H +#define MAME_CPU_TMS32082_DIS_PP_H + +#pragma once + +class tms32082_pp_disassembler : public util::disasm_interface +{ +public: + tms32082_pp_disassembler() = default; + virtual ~tms32082_pp_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *REG_NAMES[128]; + static const char *CONDITION_CODES[16]; + static const char *TRANSFER_SIZE[4]; + + + std::ostream *output; + + + std::string format_address_mode(int mode, int areg, int s, int limx); + void format_transfer(uint64_t op); + void format_alu_op(int aluop, int a, const char *dst_text, const char *a_text, const char *b_text, const char *c_text); +}; + +#endif diff --git a/src/devices/cpu/tms32082/tms32082.cpp b/src/devices/cpu/tms32082/tms32082.cpp index e2a975ea995..baf7289fe4b 100644 --- a/src/devices/cpu/tms32082/tms32082.cpp +++ b/src/devices/cpu/tms32082/tms32082.cpp @@ -9,11 +9,10 @@ #include "emu.h" #include "tms32082.h" +#include "dis_pp.h" +#include "dis_mp.h" #include "debugger.h" -extern CPU_DISASSEMBLE(tms32082_mp); -extern CPU_DISASSEMBLE(tms32082_pp); - DEFINE_DEVICE_TYPE(TMS32082_MP, tms32082_mp_device, "tms32082_mp", "TMS32082 MP") DEFINE_DEVICE_TYPE(TMS32082_PP, tms32082_pp_device, "tms32082_pp", "TMS32082 PP") @@ -64,13 +63,12 @@ device_memory_interface::space_config_vector tms32082_pp_device::memory_space_co }; } -offs_t tms32082_mp_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) + +util::disasm_interface *tms32082_mp_device::create_disassembler() { - return CPU_DISASSEMBLE_NAME(tms32082_mp)(this, stream, pc, oprom, opram, options); + return new tms32082_mp_disassembler; } - - void tms32082_mp_device::set_command_callback(write32_delegate callback) { m_cmd_callback = callback; @@ -502,9 +500,9 @@ tms32082_pp_device::tms32082_pp_device(const machine_config &mconfig, const char } -offs_t tms32082_pp_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *tms32082_pp_device::create_disassembler() { - return CPU_DISASSEMBLE_NAME(tms32082_pp)(this, stream, pc, oprom, opram, options); + return new tms32082_pp_disassembler; } void tms32082_pp_device::device_start() diff --git a/src/devices/cpu/tms32082/tms32082.h b/src/devices/cpu/tms32082/tms32082.h index c1d4674dbeb..de7949ec29f 100644 --- a/src/devices/cpu/tms32082/tms32082.h +++ b/src/devices/cpu/tms32082/tms32082.h @@ -93,9 +93,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 4; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 8; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; address_space_config m_program_config; @@ -181,9 +179,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 8; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 8; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; address_space_config m_program_config; diff --git a/src/devices/cpu/tms34010/34010dsm.cpp b/src/devices/cpu/tms34010/34010dsm.cpp index f4bad3089ee..cb2fd0ffe4e 100644 --- a/src/devices/cpu/tms34010/34010dsm.cpp +++ b/src/devices/cpu/tms34010/34010dsm.cpp @@ -8,30 +8,23 @@ */ #include "emu.h" +#include "34010dsm.h" -#ifdef STANDALONE -#define PC __pc + (offset << 3) -#define OP_WORD(v) { v = filebuf[_pc>>3]; _pc += 8; v = v | (filebuf[_pc>>3] << 8); _pc += 8;} -#define PARAM_WORD(v) { v = filebuf[_pc>>3]; _pc += 8; v = v | (filebuf[_pc>>3] << 8); _pc += 8;} -#define PARAM_LONG(v) { int v1, v2; PARAM_WORD(v1); PARAM_WORD(v2); v = v1 | (v2 << 16); } -#else -#define PC __pc -#define OP_WORD(v) { v = rombase[(__pc - pcbase) >> 3] | (rombase[(__pc + 8 - pcbase) >> 3] << 8); _pc += 16; } -#define PARAM_WORD(v) { v = rambase[(__pc + 16 - pcbase) >> 3] | (rambase[(__pc + 24 - pcbase) >> 3] << 8); _pc += 16; } -#define PARAM_LONG(v) { v = rambase[(__pc + 16 - pcbase) >> 3] | (rambase[(__pc + 24 - pcbase) >> 3] << 8) | (rambase[(__pc + 32 - pcbase) >> 3] << 16) | (rambase[(__pc + 40 - pcbase) >> 3] << 24); _pc += 32; } -#define PARM2_LONG(v) { v = rambase[(__pc + 48 - pcbase) >> 3] | (rambase[(__pc + 56 - pcbase) >> 3] << 8) | (rambase[(__pc + 64 - pcbase) >> 3] << 16) | (rambase[(__pc + 72 - pcbase) >> 3] << 24); _pc += 32; } -#endif - -static uint8_t rf; -static uint32_t __pc, _pc; -static uint16_t op,rs,rd; - -static const uint8_t *rombase; -static const uint8_t *rambase; -static offs_t pcbase; - - -static void print_reg(std::ostream &stream, uint8_t reg) +uint16_t tms34010_disassembler::r16(offs_t &pos, const data_buffer &opcodes) +{ + uint16_t r = opcodes.r16(pos); + pos += 16; + return r; +} + +uint32_t tms34010_disassembler::r32(offs_t &pos, const data_buffer &opcodes) +{ + uint32_t r = opcodes.r32(pos); + pos += 32; + return r; +} + +void tms34010_disassembler::print_reg(std::ostream &stream, uint8_t reg) { if (reg != 0x0f) { @@ -43,73 +36,51 @@ static void print_reg(std::ostream &stream, uint8_t reg) } } -static void print_src_reg(std::ostream &stream) +void tms34010_disassembler::print_src_reg(std::ostream &stream) { print_reg(stream, rs); } -static void print_des_reg(std::ostream &stream) +void tms34010_disassembler::print_des_reg(std::ostream &stream) { print_reg(stream, rd); } -static void print_src_des_reg(std::ostream &stream) +void tms34010_disassembler::print_src_des_reg(std::ostream &stream) { print_src_reg(stream); stream << ","; print_des_reg(stream); } -static void print_word_parm(std::ostream &stream) +void tms34010_disassembler::print_word_parm(std::ostream &stream, offs_t &pos, const data_buffer ¶ms) { - uint16_t w; - - PARAM_WORD(w); - - util::stream_format(stream, "%Xh", w); + util::stream_format(stream, "%Xh", r16(pos, params)); } -static void print_word_parm_1s_comp(std::ostream &stream) +void tms34010_disassembler::print_word_parm_1s_comp(std::ostream &stream, offs_t &pos, const data_buffer ¶ms) { - uint16_t w; - - PARAM_WORD(w); - w = ~w; - util::stream_format(stream, "%Xh", w); + util::stream_format(stream, "%Xh", u16(~r16(pos, params))); } -static void print_long_parm(std::ostream &stream) +void tms34010_disassembler::print_long_parm(std::ostream &stream, offs_t &pos, const data_buffer ¶ms) { - uint32_t l; - - PARAM_LONG(l); - util::stream_format(stream, "%Xh", l); -} - -static void print_long_parm2(std::ostream &stream) -{ - uint32_t l; - - PARM2_LONG(l); - util::stream_format(stream, "%Xh", l); + util::stream_format(stream, "%Xh", r32(pos, params)); } -static void print_long_parm_1s_comp(std::ostream &stream) +void tms34010_disassembler::print_long_parm_1s_comp(std::ostream &stream, offs_t &pos, const data_buffer ¶ms) { - uint32_t l; - - PARAM_LONG(l); - util::stream_format(stream, "%Xh", ~l); + util::stream_format(stream, "%Xh", u32(~r32(pos, params))); } -static void print_constant(std::ostream &stream) +void tms34010_disassembler::print_constant(std::ostream &stream) { uint8_t constant = (op >> 5) & 0x1f; util::stream_format(stream, "%Xh", constant); } -static void print_constant_1_32(std::ostream &stream) +void tms34010_disassembler::print_constant_1_32(std::ostream &stream) { uint8_t constant = (op >> 5) & 0x1f; if (!constant) constant = 0x20; @@ -117,52 +88,48 @@ static void print_constant_1_32(std::ostream &stream) util::stream_format(stream, "%Xh", constant); } -static void print_constant_1s_comp(std::ostream &stream) +void tms34010_disassembler::print_constant_1s_comp(std::ostream &stream) { uint8_t constant = (~op >> 5) & 0x1f; util::stream_format(stream, "%Xh", constant); } -static void print_constant_2s_comp(std::ostream &stream) +void tms34010_disassembler::print_constant_2s_comp(std::ostream &stream) { uint8_t constant = 32 - ((op >> 5) & 0x1f); util::stream_format(stream, "%Xh", constant); } -static void print_relative(std::ostream &stream) +void tms34010_disassembler::print_relative(std::ostream &stream, offs_t pc, offs_t &pos, const data_buffer ¶ms) { - uint16_t l; - int16_t ls; + int16_t ls = (int16_t)r16(pos, params); - PARAM_WORD(l); - ls = (int16_t)l; - - util::stream_format(stream, "%Xh", PC + 32 + (ls << 4)); + util::stream_format(stream, "%Xh", pc + 32 + (ls << 4)); } -static void print_relative_8bit(std::ostream &stream) +void tms34010_disassembler::print_relative_8bit(std::ostream &stream, offs_t pc) { int8_t ls = (int8_t)op; - util::stream_format(stream, "%Xh", PC + 16 + (ls << 4)); + util::stream_format(stream, "%Xh", pc + 16 + (ls << 4)); } -static void print_relative_5bit(std::ostream &stream) +void tms34010_disassembler::print_relative_5bit(std::ostream &stream, offs_t pc) { int8_t ls = (int8_t)((op >> 5) & 0x1f); if (op & 0x0400) ls = -ls; - util::stream_format(stream, "%Xh", PC + 16 + (ls << 4)); + util::stream_format(stream, "%Xh", pc + 16 + (ls << 4)); } -static void print_field(std::ostream &stream) +void tms34010_disassembler::print_field(std::ostream &stream) { util::stream_format(stream, "%c", (op & 0x200) ? '1' : '0'); } -static void print_condition_code(std::ostream &stream) +void tms34010_disassembler::print_condition_code(std::ostream &stream) { switch (op & 0x0f00) { @@ -185,7 +152,7 @@ static void print_condition_code(std::ostream &stream) } } -static void print_reg_list_range(std::ostream &stream, int8_t first, int8_t last) +void tms34010_disassembler::print_reg_list_range(std::ostream &stream, int8_t first, int8_t last) { if ((first != -1 ) && (first != last)) { @@ -197,13 +164,12 @@ static void print_reg_list_range(std::ostream &stream, int8_t first, int8_t last } } -static void print_reg_list(std::ostream &stream, uint16_t rev) +void tms34010_disassembler::print_reg_list(std::ostream &stream, uint16_t rev, offs_t &pos, const data_buffer ¶ms) { - uint16_t l; uint8_t i; int8_t first = -1, last = 0; - PARAM_WORD(l); + uint16_t l = r16(pos, params); for (i = 0; i < 16; i++) { @@ -241,15 +207,14 @@ static void print_reg_list(std::ostream &stream, uint16_t rev) } -static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) +offs_t tms34010_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { int flags = 0; uint8_t bad = 0; uint16_t subop; + offs_t pos = pc; - __pc = _pc = pc; - - OP_WORD(op); + op = r16(pos, opcodes); subop = (op & 0x01e0); rs = (op >> 5) & 0x0f; /* Source register */ @@ -267,21 +232,21 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) break; case 0x0040: - if (is_34020) + if (m_is_34020) util::stream_format(stream, "IDLE "); else bad = 1; break; case 0x0080: - if (is_34020) + if (m_is_34020) util::stream_format(stream, "MWAIT "); else bad = 1; break; case 0x00e0: - if (is_34020) + if (m_is_34020) util::stream_format(stream, "BLMOVE %d,%d", (op >> 1) & 1, op & 1); else bad = 1; @@ -334,21 +299,21 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) switch (subop) { case 0x0040: - if (is_34020) + if (m_is_34020) util::stream_format(stream, "SETCSP "); else bad = 1; break; case 0x0060: - if (is_34020) + if (m_is_34020) util::stream_format(stream, "SETCDP "); else bad = 1; break; case 0x0080: - if (is_34020) + if (m_is_34020) { util::stream_format(stream, "RPIX "); print_des_reg(stream); @@ -358,7 +323,7 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) break; case 0x00a0: - if (is_34020) + if (m_is_34020) { util::stream_format(stream, "EXGPS "); print_des_reg(stream); @@ -368,7 +333,7 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) break; case 0x00c0: - if (is_34020) + if (m_is_34020) { util::stream_format(stream, "GETPS "); print_des_reg(stream); @@ -378,7 +343,7 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) break; case 0x00e0: - if (is_34020) + if (m_is_34020) util::stream_format(stream, "SETCMP "); else bad = 1; @@ -394,9 +359,9 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) case 0x0140: util::stream_format(stream, "MOVB @"); - print_long_parm(stream); + print_long_parm(stream, pos, params); stream << ",@"; - print_long_parm2(stream); + print_long_parm(stream, pos, params); break; case 0x0160: @@ -434,10 +399,9 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) switch (subop) { case 0x0000: - if (is_34020 && (op & 0xfe00) == 0x0600) + if (m_is_34020 && (op & 0xfe00) == 0x0600) { - uint32_t x; - PARAM_LONG(x); + uint32_t x = r32(pos, params); util::stream_format(stream, "CEXEC %d,%06X,%d", (x >> 7) & 1, (x >> 8) & 0x1fffff, (x >> 29) & 7); } else @@ -445,10 +409,9 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) break; case 0x0020: - if (is_34020 && (op & 0xfe00) == 0x0600) + if (m_is_34020 && (op & 0xfe00) == 0x0600) { - uint32_t x; - PARAM_LONG(x); + uint32_t x = r32(pos, params); util::stream_format(stream, "CMOVGC "); print_des_reg(stream); util::stream_format(stream, ",%06X,%d", (x >> 8) & 0x1fffff, (x >> 29) & 7); @@ -458,10 +421,9 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) break; case 0x0040: - if (is_34020 && (op & 0xfe00) == 0x0600) + if (m_is_34020 && (op & 0xfe00) == 0x0600) { - uint32_t x; - PARAM_LONG(x); + uint32_t x = r32(pos, params); util::stream_format(stream, "CMOVGC "); print_des_reg(stream); stream << ","; @@ -474,10 +436,9 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) break; case 0x0060: - if (is_34020 && (op & 0xfe00) == 0x0600) + if (m_is_34020 && (op & 0xfe00) == 0x0600) { - uint32_t x; - PARAM_LONG(x); + uint32_t x = r32(pos, params); if (op == 0x0660 && (x & 0xff) == 0x01) { @@ -499,10 +460,9 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) break; case 0x0080: - if (is_34020 && (op & 0xfe00) == 0x0600) + if (m_is_34020 && (op & 0xfe00) == 0x0600) { - uint32_t x; - PARAM_LONG(x); + uint32_t x = r32(pos, params); util::stream_format(stream, "CMOVMC *"); rf = (x & 0x10) ? 'B' : 'A'; print_reg(stream, x & 0x0f); @@ -513,10 +473,9 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) break; case 0x00a0: - if (is_34020 && (op & 0xfe00) == 0x0600) + if (m_is_34020 && (op & 0xfe00) == 0x0600) { - uint32_t x; - PARAM_LONG(x); + uint32_t x = r32(pos, params); util::stream_format(stream, "CMOVCM *"); print_des_reg(stream); util::stream_format(stream, "+,%d,%d,%06X,%d", x & 0x1f, (x >> 7) & 1, (x >> 8) & 0x1fffff, (x >> 29) & 7); @@ -526,10 +485,9 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) break; case 0x00c0: - if (is_34020 && (op & 0xfe00) == 0x0600) + if (m_is_34020 && (op & 0xfe00) == 0x0600) { - uint32_t x; - PARAM_LONG(x); + uint32_t x = r32(pos, params); util::stream_format(stream, "CMOVCM *-"); print_des_reg(stream); util::stream_format(stream, ",%d,%d,%06X,%d", x & 0x1f, (x >> 7) & 1, (x >> 8) & 0x1fffff, (x >> 29) & 7); @@ -539,10 +497,9 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) break; case 0x00e0: - if (is_34020 && (op & 0xfe00) == 0x0600) + if (m_is_34020 && (op & 0xfe00) == 0x0600) { - uint32_t x; - PARAM_LONG(x); + uint32_t x = r32(pos, params); util::stream_format(stream, "CMOVMC *"); rf = (x & 0x10) ? 'B' : 'A'; print_reg(stream, x & 0x0f); @@ -581,14 +538,14 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) util::stream_format(stream, "MOVE "); print_des_reg(stream); stream << ",@"; - print_long_parm(stream); + print_long_parm(stream, pos, params); stream << ","; print_field(stream); break; case 0x01a0: util::stream_format(stream, "MOVE @"); - print_long_parm(stream); + print_long_parm(stream, pos, params); stream << ","; print_des_reg(stream); stream << ","; @@ -597,9 +554,9 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) case 0x01c0: util::stream_format(stream, "MOVE @"); - print_long_parm(stream); + print_long_parm(stream, pos, params); stream << ",@"; - print_long_parm2(stream); + print_long_parm(stream, pos, params); stream << ","; print_field(stream); break; @@ -608,7 +565,7 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) if (op & 0x200) { util::stream_format(stream, "MOVE @"); - print_long_parm(stream); + print_long_parm(stream, pos, params); stream << ","; print_des_reg(stream); } @@ -617,7 +574,7 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) util::stream_format(stream, "MOVB "); print_des_reg(stream); stream << ",@"; - print_long_parm(stream); + print_long_parm(stream, pos, params); } break; @@ -631,20 +588,19 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) switch (subop) { case 0x0000: - if (is_34020) + if (m_is_34020) { util::stream_format(stream, "TRAPL "); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; } else bad = 1; break; case 0x0020: - if (is_34020) + if (m_is_34020) { - uint32_t x; - PARAM_LONG(x); + uint32_t x = r32(pos, params); util::stream_format(stream, "CMOVMC *-"); rf = (x & 0x10) ? 'B' : 'A'; print_reg(stream, x & 0x0f); @@ -655,24 +611,24 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) break; case 0x0040: - if (is_34020) + if (m_is_34020) util::stream_format(stream, "VBLT B,L"); else bad = 1; break; case 0x0060: - if (is_34020) + if (m_is_34020) { util::stream_format(stream, "RETM "); - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; } else bad = 1; break; case 0x00e0: - if (is_34020) + if (m_is_34020) util::stream_format(stream, "CLIP "); else bad = 1; @@ -680,23 +636,23 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) case 0x0100: util::stream_format(stream, "TRAP %Xh", op & 0x1f); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case 0x0120: util::stream_format(stream, "CALL "); print_des_reg(stream); - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; break; case 0x0140: util::stream_format(stream, "RETI "); - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; break; case 0x0160: util::stream_format(stream, "RETS "); - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; if (op & 0x1f) { util::stream_format(stream, "%Xh", op & 0x1f); @@ -706,25 +662,25 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) case 0x0180: util::stream_format(stream, "MMTM "); print_des_reg(stream); - print_reg_list(stream, 1); + print_reg_list(stream, 1, pos, params); break; case 0x01a0: util::stream_format(stream, "MMFM "); print_des_reg(stream); - print_reg_list(stream, 0); + print_reg_list(stream, 0, pos, params); break; case 0x01c0: util::stream_format(stream, "MOVI "); - print_word_parm(stream); + print_word_parm(stream, pos, params); stream << ","; print_des_reg(stream); break; case 0x01e0: util::stream_format(stream, "MOVI "); - print_long_parm(stream); + print_long_parm(stream, pos, params); stream << ","; print_des_reg(stream); break; @@ -739,28 +695,28 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) switch (subop) { case 0x0000: - if (is_34020) + if (m_is_34020) util::stream_format(stream, "VLCOL "); else bad = 1; break; case 0x0020: - if (is_34020) + if (m_is_34020) util::stream_format(stream, "PFILL XY"); else bad = 1; break; case 0x0040: - if (is_34020) + if (m_is_34020) util::stream_format(stream, "VFILL L"); else bad = 1; break; case 0x0060: - if (is_34020) + if (m_is_34020) { util::stream_format(stream, "CVMXYL "); print_des_reg(stream); @@ -770,7 +726,7 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) break; case 0x0080: - if (is_34020) + if (m_is_34020) { util::stream_format(stream, "CVDXYL "); print_des_reg(stream); @@ -780,14 +736,14 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) break; case 0x00a0: - if (is_34020) + if (m_is_34020) util::stream_format(stream, "FPIXEQ "); else bad = 1; break; case 0x00c0: - if (is_34020) + if (m_is_34020) util::stream_format(stream, "FPIXNE "); else bad = 1; @@ -795,56 +751,56 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) case 0x0100: util::stream_format(stream, "ADDI "); - print_word_parm(stream); + print_word_parm(stream, pos, params); stream << ","; print_des_reg(stream); break; case 0x0120: util::stream_format(stream, "ADDI "); - print_long_parm(stream); + print_long_parm(stream, pos, params); stream << ","; print_des_reg(stream); break; case 0x0140: util::stream_format(stream, "CMPI "); - print_word_parm_1s_comp(stream); + print_word_parm_1s_comp(stream, pos, params); stream << ","; print_des_reg(stream); break; case 0x0160: util::stream_format(stream, "CMPI "); - print_long_parm_1s_comp(stream); + print_long_parm_1s_comp(stream, pos, params); stream << ","; print_des_reg(stream); break; case 0x0180: util::stream_format(stream, "ANDI "); - print_long_parm_1s_comp(stream); + print_long_parm_1s_comp(stream, pos, params); stream << ","; print_des_reg(stream); break; case 0x01a0: util::stream_format(stream, "ORI "); - print_long_parm(stream); + print_long_parm(stream, pos, params); stream << ","; print_des_reg(stream); break; case 0x01c0: util::stream_format(stream, "XORI "); - print_long_parm(stream); + print_long_parm(stream, pos, params); stream << ","; print_des_reg(stream); break; case 0x01e0: util::stream_format(stream, "SUBI "); - print_word_parm_1s_comp(stream); + print_word_parm_1s_comp(stream, pos, params); stream << ","; print_des_reg(stream); break; @@ -859,10 +815,10 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) switch (subop) { case 0x0000: - if (is_34020) + if (m_is_34020) { util::stream_format(stream, "ADDXYI "); - print_long_parm(stream); + print_long_parm(stream, pos, params); stream << ","; print_des_reg(stream); } @@ -871,7 +827,7 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) break; case 0x0040: - if (is_34020) + if (m_is_34020) util::stream_format(stream, "LINIT "); else bad = 1; @@ -879,21 +835,21 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) case 0x0100: util::stream_format(stream, "SUBI "); - print_long_parm_1s_comp(stream); + print_long_parm_1s_comp(stream, pos, params); stream << ","; print_des_reg(stream); break; case 0x0120: util::stream_format(stream, "CALLR "); - print_relative(stream); - flags = DASMFLAG_STEP_OVER; + print_relative(stream, pc, pos, params); + flags = STEP_OVER; break; case 0x0140: util::stream_format(stream, "CALLA "); - print_long_parm(stream); - flags = DASMFLAG_STEP_OVER; + print_long_parm(stream, pos, params); + flags = STEP_OVER; break; case 0x0160: @@ -904,24 +860,24 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) util::stream_format(stream, "DSJ "); print_des_reg(stream); stream << ","; - print_relative(stream); - flags = DASMFLAG_STEP_OVER; + print_relative(stream, pc, pos, params); + flags = STEP_OVER; break; case 0x01a0: util::stream_format(stream, "DSJEQ "); print_des_reg(stream); stream << ","; - print_relative(stream); - flags = DASMFLAG_STEP_OVER; + print_relative(stream, pc, pos, params); + flags = STEP_OVER; break; case 0x01c0: util::stream_format(stream, "DSJNE "); print_des_reg(stream); stream << ","; - print_relative(stream); - flags = DASMFLAG_STEP_OVER; + print_relative(stream, pc, pos, params); + flags = STEP_OVER; break; case 0x01e0: @@ -935,18 +891,18 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) case 0x0e00: - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; switch (subop) { case 0x0000: - if (is_34020) + if (m_is_34020) util::stream_format(stream, "PIXBLT L,M,L"); else bad = 1; break; case 0x00e0: - if (is_34020) + if (m_is_34020) util::stream_format(stream, "TFILL XY"); else bad = 1; @@ -1088,7 +1044,7 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) case 0x3400: case 0x3600: - if (is_34020) + if (m_is_34020) { util::stream_format(stream, "CMPK "); print_constant_1_32(stream); @@ -1106,8 +1062,8 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) util::stream_format(stream, "DSJS "); print_des_reg(stream); stream << ","; - print_relative_5bit(stream); - flags = DASMFLAG_STEP_OVER; + print_relative_5bit(stream, pc); + flags = STEP_OVER; break; @@ -1279,7 +1235,7 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) case 0x7a00: - if (is_34020) + if (m_is_34020) { util::stream_format(stream, "RMO "); print_src_des_reg(stream); @@ -1289,7 +1245,7 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) break; case 0x7e00: - if (is_34020) + if (m_is_34020) { util::stream_format(stream, "SWAPF *"); print_src_des_reg(stream); @@ -1423,7 +1379,7 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) stream << ",*"; print_des_reg(stream); stream << "("; - print_word_parm(stream); + print_word_parm(stream, pos, params); stream << ")"; break; @@ -1432,7 +1388,7 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) util::stream_format(stream, "MOVB *"); print_src_reg(stream); stream << "("; - print_word_parm(stream); + print_word_parm(stream, pos, params); stream << "),"; print_des_reg(stream); break; @@ -1445,7 +1401,7 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) stream << ",*"; print_des_reg(stream); stream << "("; - print_word_parm(stream); + print_word_parm(stream, pos, params); stream << "),"; print_field(stream); break; @@ -1456,7 +1412,7 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) util::stream_format(stream, "MOVE *"); print_src_reg(stream); stream << "("; - print_word_parm(stream); + print_word_parm(stream, pos, params); stream << "),"; print_des_reg(stream); stream << ","; @@ -1469,11 +1425,11 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) util::stream_format(stream, "MOVE *"); print_src_reg(stream); stream << "("; - print_word_parm(stream); + print_word_parm(stream, pos, params); stream << "),*"; print_des_reg(stream); stream << "("; - print_word_parm(stream); + print_word_parm(stream, pos, params); stream << "),"; print_field(stream); break; @@ -1483,11 +1439,11 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) util::stream_format(stream, "MOVB *"); print_src_reg(stream); stream << "("; - print_word_parm(stream); + print_word_parm(stream, pos, params); stream << "),*"; print_des_reg(stream); stream << "("; - print_word_parm(stream); + print_word_parm(stream, pos, params); stream << ")"; break; @@ -1515,15 +1471,15 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) switch (op & 0x00ff) { case 0x00: - print_relative(stream); + print_relative(stream, pc, pos, params); break; case 0x80: - print_long_parm(stream); + print_long_parm(stream, pos, params); break; default: - print_relative_8bit(stream); + print_relative_8bit(stream, pc); } break; @@ -1533,7 +1489,7 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) util::stream_format(stream, "MOVE *"); print_src_reg(stream); stream << "("; - print_word_parm(stream); + print_word_parm(stream, pos, params); stream << "),*"; print_des_reg(stream); stream << "+,"; @@ -1547,7 +1503,7 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) { case 0x0000: util::stream_format(stream, "MOVE @"); - print_long_parm(stream); + print_long_parm(stream, pos, params); stream << ",*"; print_des_reg(stream); stream << "+,"; @@ -1567,10 +1523,9 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) break; case 0xd800: - if (is_34020) + if (m_is_34020) { - uint32_t x; - PARAM_WORD(x); + uint32_t x = r16(pos, params); util::stream_format(stream, "CEXEC %d,%06X,%d", op & 1, ((x << 5) & 0x1fffe0) | ((op >> 1) & 0x1f), (x >> 13) & 7); } else @@ -1582,14 +1537,14 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) switch (subop) { case 0x0000: - if (is_34020) + if (m_is_34020) util::stream_format(stream, "FLINE 0"); else bad = 1; break; case 0x0080: - if (is_34020) + if (m_is_34020) util::stream_format(stream, "FLINE 1"); else bad = 1; @@ -1639,7 +1594,7 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) case 0xea00: - if (is_34020) + if (m_is_34020) { util::stream_format(stream, "CVSXYL "); print_src_des_reg(stream); @@ -1723,21 +1678,14 @@ static unsigned Dasm340x0(std::ostream &stream, uint32_t pc, bool is_34020) util::stream_format(stream, "DW %04Xh", op & 0xffff); } - return (_pc - __pc) | flags | DASMFLAG_SUPPORTED; + return (pos - pc) | flags | SUPPORTED; } -CPU_DISASSEMBLE( tms34010 ) +uint32_t tms34010_disassembler::opcode_alignment() const { - rombase = oprom; - rambase = opram; - pcbase = pc; - return Dasm340x0(stream, pc, false); + return 16; } -CPU_DISASSEMBLE( tms34020 ) +tms34010_disassembler::tms34010_disassembler(bool is_34020) : m_is_34020(is_34020) { - rombase = oprom; - rambase = opram; - pcbase = pc; - return Dasm340x0(stream, pc, true); } diff --git a/src/devices/cpu/tms34010/34010dsm.h b/src/devices/cpu/tms34010/34010dsm.h new file mode 100644 index 00000000000..2e8e72ee191 --- /dev/null +++ b/src/devices/cpu/tms34010/34010dsm.h @@ -0,0 +1,52 @@ +// license:BSD-3-Clause +// copyright-holders:Zsolt Vasvari +/* + * A TMS34010 disassembler + * + * This code written by Zsolt Vasvari for the MAME project + * + */ + +#ifndef MAME_CPU_TMS34010_34010DSM_H +#define MAME_CPU_TMS34010_34010DSM_H + +#pragma once + +class tms34010_disassembler : public util::disasm_interface +{ +public: + tms34010_disassembler(bool is_34020); + virtual ~tms34010_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + bool m_is_34020; + uint8_t rf; + uint16_t op,rs,rd; + + uint16_t r16(offs_t &pos, const data_buffer &opcodes); + uint32_t r32(offs_t &pos, const data_buffer &opcodes); + void print_reg(std::ostream &stream, uint8_t reg); + void print_src_reg(std::ostream &stream); + void print_des_reg(std::ostream &stream); + void print_src_des_reg(std::ostream &stream); + void print_word_parm(std::ostream &stream, offs_t &pos, const data_buffer ¶ms); + void print_word_parm_1s_comp(std::ostream &stream, offs_t &pos, const data_buffer ¶ms); + void print_long_parm(std::ostream &stream, offs_t &pos, const data_buffer ¶ms); + void print_long_parm_1s_comp(std::ostream &stream, offs_t &pos, const data_buffer ¶ms); + void print_constant(std::ostream &stream); + void print_constant_1_32(std::ostream &stream); + void print_constant_1s_comp(std::ostream &stream); + void print_constant_2s_comp(std::ostream &stream); + void print_relative(std::ostream &stream, offs_t pc, offs_t &pos, const data_buffer ¶ms); + void print_relative_8bit(std::ostream &stream, offs_t pc); + void print_relative_5bit(std::ostream &stream, offs_t pc); + void print_field(std::ostream &stream); + void print_condition_code(std::ostream &stream); + void print_reg_list_range(std::ostream &stream, int8_t first, int8_t last); + void print_reg_list(std::ostream &stream, uint16_t rev, offs_t &pos, const data_buffer ¶ms); +}; + +#endif diff --git a/src/devices/cpu/tms34010/34010gfx.hxx b/src/devices/cpu/tms34010/34010gfx.hxx index 5c92ad36b6b..72c32b8a227 100644 --- a/src/devices/cpu/tms34010/34010gfx.hxx +++ b/src/devices/cpu/tms34010/34010gfx.hxx @@ -207,6 +207,11 @@ int tms340x0_device::compute_pixblt_b_cycles(int left_partials, int right_partia /* Shift register handling */ void tms340x0_device::memory_w(address_space &space, offs_t offset,uint16_t data) { + logerror("memory_w %08x %04x\n", offset << 3, data); + if((offset << 3) == 0x02005010 && data == 0x0000) { + machine().debug_break(); + // abort(); + } space.write_word(offset, data); } @@ -217,6 +222,7 @@ uint16_t tms340x0_device::memory_r(address_space &space, offs_t offset) void tms340x0_device::shiftreg_w(address_space &space, offs_t offset,uint16_t data) { + logerror("shiftreg_w %08x %04x\n", offset << 3, data); if (!m_from_shiftreg_cb.isnull()) m_from_shiftreg_cb(space, (uint32_t)(offset << 3) & ~15, &m_shiftreg[0]); else diff --git a/src/devices/cpu/tms34010/dis34010.cpp b/src/devices/cpu/tms34010/dis34010.cpp deleted file mode 100644 index 01aebd4a6f1..00000000000 --- a/src/devices/cpu/tms34010/dis34010.cpp +++ /dev/null @@ -1,115 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:Zsolt Vasvari -/* This program is based on DIS68k by Aaron Giles */ - -#include "emu.h" - -static uint8_t *filebuf; -static uint32_t offset; - -#define STANDALONE -#include "34010dsm.c" - - -static const char *const Options[]= -{ - "begin","end","offset",0 -}; - -static void usage (void) -{ - printf ("Usage: DIS34010 [options] \n" - "Available options are:\n" - " -begin - Specify begin offset in file to disassemble in bits [0]\n" - " -end - Specify end offset in file to disassemble in bits [none]\n" - " -offset - Specify address to load program in bits [0]\n" - "All values should be entered in hexadecimal\n"); - exit (1); -} - -int main (int argc,char *argv[]) -{ - uint8_t i,j,n; - char *filename=0,buf[80]; - FILE *f; - uint32_t begin=0,end=(uint32_t)-1,filelen,len,pc; - printf ("DIS34010\n" - "Copyright Zsolt Vasvari/Aaron Giles\n"); - - for (i=1,n=0;iargc) usage(); - begin=strtoul(argv[i],0,16) >> 3; - break; - case 1: ++i; if (i>argc) usage(); - end=strtoul(argv[i],0,16) >> 3; - break; - case 2: ++i; if (i>argc) usage(); - offset=strtoul(argv[i],0,16) >> 3; - break; - default: usage(); - } - } - } - - if (!filename) - { - usage(); - return 1; - } - f=fopen (filename,"rb"); - if (!f) - { - printf ("Unable to open %s\n",filename); - return 2; - } - fseek (f,0,SEEK_END); - filelen=ftell (f); - fseek (f,begin,SEEK_SET); - len=(filelen>end)? (end-begin+1):(filelen-begin); - filebuf=malloc(len+16); - if (!filebuf) - { - printf ("Memory allocation error\n"); - fclose (f); - return 3; - } - memset (filebuf,0,len+16); - if (fread(filebuf,1,len,f)!=len) - { - printf ("Read error\n"); - fclose (f); - free (filebuf); - return 4; - } - fclose (f); - pc=0; - while (pc>3; - - printf ("%08X: ",(pc+offset) << 3); - for (j=0;j> 3) #define TOWORD(bitaddr) ((offs_t)(bitaddr) >> 4) - -CPU_DISASSEMBLE( tms34010 ); -CPU_DISASSEMBLE( tms34020 ); - #endif // MAME_CPU_TMS34010_TMS34010_H diff --git a/src/devices/cpu/tms57002/57002dsm.cpp b/src/devices/cpu/tms57002/57002dsm.cpp index 0f92c9af145..b8d03ab8172 100644 --- a/src/devices/cpu/tms57002/57002dsm.cpp +++ b/src/devices/cpu/tms57002/57002dsm.cpp @@ -9,10 +9,13 @@ ***************************************************************************/ #include "emu.h" -#include "debugger.h" -#include "tms57002.h" +#include "57002dsm.h" -static std::string get_memadr(uint32_t opcode, char type) +tms57002_disassembler::tms57002_disassembler() +{ +} + +std::string tms57002_disassembler::get_memadr(uint32_t opcode, char type) { std::string buf; @@ -30,11 +33,15 @@ static std::string get_memadr(uint32_t opcode, char type) return buf; } +u32 tms57002_disassembler::opcode_alignment() const +{ + return 1; +} -CPU_DISASSEMBLE(tms57002) +offs_t tms57002_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { std::streampos original_pos = stream.tellp(); - uint32_t opcode = opram[0] | (opram[1] << 8) | (opram[2] << 16); + uint32_t opcode = opcodes.r32(pc); uint8_t fa = opcode >> 18; if(fa == 0x3f) { switch((opcode >> 11) & 0x7f) { // category 3 diff --git a/src/devices/cpu/tms57002/57002dsm.h b/src/devices/cpu/tms57002/57002dsm.h new file mode 100644 index 00000000000..56ed3d0ea25 --- /dev/null +++ b/src/devices/cpu/tms57002/57002dsm.h @@ -0,0 +1,30 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + 57002dsm.c + + TMS57002 "DASP" emulator. + +***************************************************************************/ + +#ifndef MAME_CPU_TMS57002_57002DSM_H +#define MAME_CPU_TMS57002_57002DSM_H + +#pragma once + +class tms57002_disassembler : public util::disasm_interface +{ +public: + tms57002_disassembler(); + virtual ~tms57002_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static std::string get_memadr(uint32_t opcode, char type); + +}; + +#endif diff --git a/src/devices/cpu/tms57002/tms57002.cpp b/src/devices/cpu/tms57002/tms57002.cpp index 4b88669298b..0d4aea34c14 100644 --- a/src/devices/cpu/tms57002/tms57002.cpp +++ b/src/devices/cpu/tms57002/tms57002.cpp @@ -11,6 +11,7 @@ #include "emu.h" #include "tms57002.h" #include "debugger.h" +#include "57002dsm.h" DEFINE_DEVICE_TYPE(TMS57002, tms57002_device, "tms57002", "TMS57002") @@ -29,6 +30,10 @@ tms57002_device::tms57002_device(const machine_config &mconfig, const char *tag, { } +util::disasm_interface *tms57002_device::create_disassembler() +{ + return new tms57002_disassembler; +} WRITE_LINE_MEMBER(tms57002_device::pload_w) { @@ -892,22 +897,6 @@ uint32_t tms57002_device::execute_input_lines() const return 0; } -uint32_t tms57002_device::disasm_min_opcode_bytes() const -{ - return 4; -} - -uint32_t tms57002_device::disasm_max_opcode_bytes() const -{ - return 4; -} - -offs_t tms57002_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) -{ - extern CPU_DISASSEMBLE( tms57002 ); - return CPU_DISASSEMBLE_NAME(tms57002)(this, stream, pc, oprom, opram, options); -} - device_memory_interface::space_config_vector tms57002_device::memory_space_config() const { return space_config_vector { diff --git a/src/devices/cpu/tms57002/tms57002.h b/src/devices/cpu/tms57002/tms57002.h index 361c0b8a7d8..120af046362 100644 --- a/src/devices/cpu/tms57002/tms57002.h +++ b/src/devices/cpu/tms57002/tms57002.h @@ -35,9 +35,7 @@ protected: virtual uint32_t execute_max_cycles() const override; virtual uint32_t execute_input_lines() const override; virtual void execute_run() override; - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: enum { diff --git a/src/devices/cpu/tms57002/tms57kdec.cpp b/src/devices/cpu/tms57002/tms57kdec.cpp index b3b71cb58e4..8cca7ba825f 100644 --- a/src/devices/cpu/tms57002/tms57kdec.cpp +++ b/src/devices/cpu/tms57002/tms57kdec.cpp @@ -72,18 +72,11 @@ inline int tms57002_device::sfma(uint32_t st1) void tms57002_device::decode_error(uint32_t opcode) { - uint8_t opr[3]; if(unsupported_inst_warning) return; unsupported_inst_warning = 1; - opr[0] = opcode; - opr[1] = opcode >> 8; - opr[2] = opcode >> 16; - - std::stringstream stream; - disasm_disassemble(stream, pc, opr, opr, 0); - popmessage("tms57002: %s - Contact Mamedev", stream.str()); + popmessage("tms57002: %06x - Contact Mamedev", opcode); } void tms57002_device::decode_cat1(uint32_t opcode, unsigned short *op, cstate *cs) diff --git a/src/devices/cpu/tms7000/7000dasm.cpp b/src/devices/cpu/tms7000/7000dasm.cpp index 1f7f8549852..000c7ea2ea3 100644 --- a/src/devices/cpu/tms7000/7000dasm.cpp +++ b/src/devices/cpu/tms7000/7000dasm.cpp @@ -7,24 +7,9 @@ */ #include "emu.h" -#include "debugger.h" -#include "tms7000.h" +#include "7000dasm.h" -enum operandtype { DONE, NONE, UI8, I8, UI16, I16, PCREL, PCABS, TRAP }; - -struct oprandinfo { - char opstr[4][12]; - operandtype decode[4]; -}; - -struct tms7000_opcodeinfo { - int opcode; - char name[8]; - int operand; - uint32_t s_flag; -}; - -static const oprandinfo of[] = { +const tms7000_disassembler::oprandinfo tms7000_disassembler::of[] = { /* 00 */ { {" B,A", "", "", ""}, {NONE, DONE, DONE, DONE} }, /* 01 */ { {" R%u", ",A", "", ""}, {UI8, NONE, DONE, DONE} }, /* 02 */ { {" R%u", ",B", "", ""}, {UI8, NONE, DONE, DONE} }, @@ -84,7 +69,7 @@ static const oprandinfo of[] = { /* 45 */ { {" *R%u", "", "", ""}, {UI8, DONE, DONE, DONE} } }; -static const tms7000_opcodeinfo opcodes[] = { +const tms7000_disassembler::tms7000_opcodeinfo tms7000_disassembler::opcs[] = { {0x69, "ADC", 0, 0 }, {0x19, "ADC", 1, 0 }, {0x39, "ADC", 2, 0 }, @@ -141,9 +126,9 @@ static const tms7000_opcodeinfo opcodes[] = { {0x97, "BTJZP", 21, 0 }, {0xA7, "BTJZP", 22, 0 }, - {0x8E, "CALL", 43, DASMFLAG_STEP_OVER }, - {0x9E, "CALL", 45, DASMFLAG_STEP_OVER }, - {0xAE, "CALL", 12, DASMFLAG_STEP_OVER }, + {0x8E, "CALL", 43, STEP_OVER }, + {0x9E, "CALL", 45, STEP_OVER }, + {0xAE, "CALL", 12, STEP_OVER }, {0xB5, "CLR A", 23, 0 }, {0xC5, "CLR B", 23, 0 }, @@ -273,8 +258,8 @@ static const tms7000_opcodeinfo opcodes[] = { {0xD8, "PUSH", 24, 0 }, {0x0E, "PUSH ST", 23, 0 }, - {0x0B, "RETI", 23, DASMFLAG_STEP_OUT }, - {0x0A, "RETS", 23, DASMFLAG_STEP_OUT }, + {0x0B, "RETI", 23, STEP_OUT }, + {0x0A, "RETS", 23, STEP_OUT }, {0xBE, "RL A", 23, 0 }, {0xCE, "RL B", 23, 0 }, @@ -316,30 +301,30 @@ static const tms7000_opcodeinfo opcodes[] = { {0x5A, "SUB", 5, 0 }, {0x7A, "SUB", 6, 0 }, - {0xFF, "TRAP 0", 44, DASMFLAG_STEP_OVER }, - {0xFE, "TRAP 1", 44, DASMFLAG_STEP_OVER }, - {0xFD, "TRAP 2", 44, DASMFLAG_STEP_OVER }, - {0xFC, "TRAP 3", 44, DASMFLAG_STEP_OVER }, - {0xFB, "TRAP 4", 44, DASMFLAG_STEP_OVER }, - {0xFA, "TRAP 5", 44, DASMFLAG_STEP_OVER }, - {0xF9, "TRAP 6", 44, DASMFLAG_STEP_OVER }, - {0xF8, "TRAP 7", 44, DASMFLAG_STEP_OVER }, - {0xF7, "TRAP 8", 44, DASMFLAG_STEP_OVER }, - {0xF6, "TRAP 9", 44, DASMFLAG_STEP_OVER }, - {0xF5, "TRAP 10", 44, DASMFLAG_STEP_OVER }, - {0xF4, "TRAP 11", 44, DASMFLAG_STEP_OVER }, - {0xF3, "TRAP 12", 44, DASMFLAG_STEP_OVER }, - {0xF2, "TRAP 13", 44, DASMFLAG_STEP_OVER }, - {0xF1, "TRAP 14", 44, DASMFLAG_STEP_OVER }, - {0xF0, "TRAP 15", 44, DASMFLAG_STEP_OVER }, - {0xEF, "TRAP 16", 44, DASMFLAG_STEP_OVER }, - {0xEE, "TRAP 17", 44, DASMFLAG_STEP_OVER }, - {0xED, "TRAP 18", 44, DASMFLAG_STEP_OVER }, - {0xEC, "TRAP 19", 44, DASMFLAG_STEP_OVER }, - {0xEB, "TRAP 20", 44, DASMFLAG_STEP_OVER }, - {0xEA, "TRAP 21", 44, DASMFLAG_STEP_OVER }, - {0xE9, "TRAP 22", 44, DASMFLAG_STEP_OVER }, - {0xE8, "TRAP 23", 44, DASMFLAG_STEP_OVER }, + {0xFF, "TRAP 0", 44, STEP_OVER }, + {0xFE, "TRAP 1", 44, STEP_OVER }, + {0xFD, "TRAP 2", 44, STEP_OVER }, + {0xFC, "TRAP 3", 44, STEP_OVER }, + {0xFB, "TRAP 4", 44, STEP_OVER }, + {0xFA, "TRAP 5", 44, STEP_OVER }, + {0xF9, "TRAP 6", 44, STEP_OVER }, + {0xF8, "TRAP 7", 44, STEP_OVER }, + {0xF7, "TRAP 8", 44, STEP_OVER }, + {0xF6, "TRAP 9", 44, STEP_OVER }, + {0xF5, "TRAP 10", 44, STEP_OVER }, + {0xF4, "TRAP 11", 44, STEP_OVER }, + {0xF3, "TRAP 12", 44, STEP_OVER }, + {0xF2, "TRAP 13", 44, STEP_OVER }, + {0xF1, "TRAP 14", 44, STEP_OVER }, + {0xF0, "TRAP 15", 44, STEP_OVER }, + {0xEF, "TRAP 16", 44, STEP_OVER }, + {0xEE, "TRAP 17", 44, STEP_OVER }, + {0xED, "TRAP 18", 44, STEP_OVER }, + {0xEC, "TRAP 19", 44, STEP_OVER }, + {0xEB, "TRAP 20", 44, STEP_OVER }, + {0xEA, "TRAP 21", 44, STEP_OVER }, + {0xE9, "TRAP 22", 44, STEP_OVER }, + {0xE8, "TRAP 23", 44, STEP_OVER }, {0xB7, "SWAP A", 23, 0 }, {0xC7, "SWAP B", 23, 0 }, @@ -367,17 +352,22 @@ static const tms7000_opcodeinfo opcodes[] = { {0x00, "NOP", 23, 0 } }; -CPU_DISASSEMBLE(tms7000) +u32 tms7000_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t tms7000_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { int opcode, i/*, size = 1*/; - int pos = 0; + offs_t pos = pc; char tmpbuf[32]; - opcode = oprom[pos++]; + opcode = opcodes.r8(pos++); - for( i=0; i>(15-(n2))) & (MASK>>(15-((n2)-(n1))))) -enum format_t -{ - format_1, /* 2 address instructions */ - format_2a, /* jump instructions */ - format_2b, /* bit I/O instructions */ - format_3_9, /* logical, multiply, and divide instructions */ - format_4, /* CRU instructions */ - format_5, /* register shift instructions */ - format_6, /* single address instructions */ - format_7, /* instructions without operands */ - format_8a, /* immediate instructions (destination register) */ - format_8b, /* immediate instructions (no destination register) */ - format_9, /* extended operation instruction */ - format_10, /* memory map file instruction */ - format_11, /* multiple precision instructions */ - format_12, /* string instructions */ - format_13, /* multiple precision shift instructions */ - format_14, /* bit testing instructions */ - format_15, /* invert order of field instruction */ - format_16, /* field instructions */ - format_17, /* alter register and jump instructions */ - format_18, /* single register operand instructions */ - format_liim,/* format for liim (looks like format 18) */ - format_19, /* move address instruction */ - format_20, /* list search instructions */ - format_21, /* extend precision instruction */ - - illegal -}; - -/* definitions for flags */ -enum -{ - /* processor set on which opcodes are available */ - ps_any = 0x01, /* every processor in the tms9900/ti990 family */ - ps_mapper = 0x02, /* processors with memory mapper (ti990/10, ti990/12, - and tms99000 with mapper coprocessor) */ - ps_tms9995 = 0x04, /* ti990/12, tms9995, and later */ - ps_tms99000 = 0x08, /* ti990/12, tms99000, and later */ - ps_ti990_12 = 0x10, /* ti990/12 only */ - - /* additional flags for special decoding */ - sd_11 = 0x100, /* bit 11 should be cleared in li, ai, andi, ori, ci, stwp, stst */ - sd_11_15 = 0x200 /* bits 11-15 should be cleared in lwpi, limi, idle, rset, rtwp, ckon, ckof, lrex */ -}; -struct description_t -{ - const char *mnemonic; - format_t format; - int flags; -}; - - -enum opcodes { - /* basic instruction set */ - _a=0, _ab, _c, _cb, _s, _sb, _soc, _socb, _szc, _szcb, - _mov, _movb, _coc, _czc, _xor, _mpy, _div, _xop, _b, _bl, - _blwp, _clr, _seto, _inv, _neg, _abs, _swpb, _inc, _inct, _dec, - _dect, _x, _ldcr, _stcr, _sbo, _sbz, _tb, _jeq, _jgt, _jh, - _jhe, _jl, _jle, _jlt, _jmp, _jnc, _jne, _jno, _joc, _jop, - _sla, _sra, _src, _srl, _ai, _andi, _ci, _li, _ori, _lwpi, - _limi, _stst, _stwp, _rtwp, _idle, _rset, _ckof, _ckon, _lrex, - - /* mapper instruction set */ - _lds, _ldd, _lmf, - - /* tms9995 instruction set */ - _divs, _mpys, _lst, _lwp, - - /* tms99000 instruction set */ - _bind, - - /* ti990/12 instruction set */ - _sram, _slam, _rto, _lto, _cnto, _slsl, _slsp, _bdc, _dbc, _swpm, - _xorm, _orm, _andm, _sm, _am, _mova, _emd, _eint, _dint, _stpc, - _cs, _seqb, _movs, _lim, _lcs, _blsk, _mvsr, _mvsk, _pops, _pshs, - - _cri, _cdi, _negr, _negd, _cre, _cde, _cer, _ced, _nrm, _tmb, - _tcmb, _tsmb, _srj, _arj, _xit, _insf, _xv, _xf, _ar, _cir, - _sr, _mr, _dr, _lr, _str, _iof, _sneb, _crc, _ts, _ad, - _cid, _sd, _md, _dd, _ld, _std, _ep, - - /* tms9940-only instruction set */ - _liim, _dca, _dcs, - - _ill -}; - - -static const description_t descriptions[144+3+1] = +const tms9900_disassembler::description_t tms9900_disassembler::descriptions[144+3+1] = { /* basic instruction set */ { "a", format_1, ps_any }, { "ab", format_1, ps_any }, @@ -203,51 +114,51 @@ static const description_t descriptions[144+3+1] = }; -static const enum opcodes ops_4000_ffff_s12[12]= +const enum tms9900_disassembler::opcodes tms9900_disassembler::ops_4000_ffff_s12[12]= { _szc, _szcb, _s, _sb, /*4000-7000*/ _c, _cb, _a, _ab, _mov, _movb, _soc, _socb /*8000-f000*/ }; -static const enum opcodes ops_2000_3fff_s10[8]= +const enum tms9900_disassembler::opcodes tms9900_disassembler::ops_2000_3fff_s10[8]= { _coc, _czc, _xor, _xop, _ldcr, _stcr, _mpy, _div /*2000-3800*/ }; -static const enum opcodes ops_1000_1fff_s8[16]= +const enum tms9900_disassembler::opcodes tms9900_disassembler::ops_1000_1fff_s8[16]= { _jmp, _jlt, _jle, _jeq, _jhe, _jgt, _jne, _jnc, /*1000-1700*/ _joc, _jno, _jl, _jh, _jop, _sbo, _sbz, _tb /*1800-1f00*/ }; -static const enum opcodes ops_0e40_0fff_s6[7]= +const enum tms9900_disassembler::opcodes tms9900_disassembler::ops_0e40_0fff_s6[7]= { _ad, _cid, _sd, _md, _dd, _ld, _std /*0e40-0fc0*/ }; -static const enum opcodes ops_0e00_0e3f_s4[4]= +const enum tms9900_disassembler::opcodes tms9900_disassembler::ops_0e00_0e3f_s4[4]= { _iof, _sneb, _crc, _ts /*0e00-0e30*/ }; -static const enum opcodes ops_0c40_0dff_s6[7]= +const enum tms9900_disassembler::opcodes tms9900_disassembler::ops_0c40_0dff_s6[7]= { _ar, _cir, _sr, _mr, _dr, _lr, _str /*0c40-0dc0*/ }; -static const enum opcodes ops_0c10_0c3f_s4[3]= +const enum tms9900_disassembler::opcodes tms9900_disassembler::ops_0c10_0c3f_s4[3]= { _insf, _xv, _xf /*0c10-0c30*/ }; -static const enum opcodes ops_0c00_0c0f_s0[16]= +const enum tms9900_disassembler::opcodes tms9900_disassembler::ops_0c00_0c0f_s0[16]= { _cri, _cdi, _negr, _negd, _cre, _cde, _cer, _ced, /*0c00-0c07*/ _nrm, _tmb, _tcmb, _tsmb, _srj, _arj, _xit, _xit /*0c08-0c0f*/ @@ -255,40 +166,40 @@ static const enum opcodes ops_0c00_0c0f_s0[16]= -static const enum opcodes ops_0800_0bff_s8[4]= +const enum tms9900_disassembler::opcodes tms9900_disassembler::ops_0800_0bff_s8[4]= { _sra, _srl, _sla, _src /*0800-0b00*/ }; -static const enum opcodes ops_0400_07ff_s6[16]= +const enum tms9900_disassembler::opcodes tms9900_disassembler::ops_0400_07ff_s6[16]= { _blwp, _b, _x, _clr, _neg, _inv, _inc, _inct, /*0400-05c0*/ _dec, _dect, _bl, _swpb, _seto, _abs, _lds, _ldd /*0600-07c0*/ }; -static const enum opcodes ops_0200_03ff_s5[16]= +const enum tms9900_disassembler::opcodes tms9900_disassembler::ops_0200_03ff_s5[16]= { _li, _ai, _andi, _ori, _ci, _stwp, _stst, _lwpi, /*0200-02e0*/ _limi, _lmf, _idle, _rset, _rtwp, _ckon, _ckof, _lrex /*0300-03e0*/ }; -static const enum opcodes ops_0100_01ff_s6[4]= +const enum tms9900_disassembler::opcodes tms9900_disassembler::ops_0100_01ff_s6[4]= { _ill, _bind, _divs, _mpys /*0100-01c0*/ }; -static const enum opcodes ops_0030_00ff_s4[13]= +const enum tms9900_disassembler::opcodes tms9900_disassembler::ops_0030_00ff_s4[13]= { _stpc, _cs, _seqb, _movs, _lim, /*0030-0070*/ _lst, _lwp, _lcs, _blsk, _mvsr, _mvsk, _pops, _pshs /*0080-00f0*/ }; -static const enum opcodes ops_001c_002f_s0[20]= +const enum tms9900_disassembler::opcodes tms9900_disassembler::ops_001c_002f_s0[20]= { _sram, _slam, _rto, _lto, /*001c-001f*/ _cnto, _slsl, _slsp, _bdc, _dbc, _swpm, _xorm, _orm, /*0020-0027*/ @@ -296,17 +207,14 @@ static const enum opcodes ops_001c_002f_s0[20]= }; - -static int PC; - - -static inline uint16_t readop_arg(const uint8_t *opram, unsigned pc) +inline uint16_t tms9900_disassembler::readop_arg(const data_buffer ¶ms, offs_t &PC) { - uint16_t result = opram[PC++ - pc] << 8; - return result | opram[PC++ - pc]; + uint16_t result = params.r16(PC); + PC += 2;; + return result; } -static void print_arg (std::ostream &stream, int mode, int arg, const uint8_t *opram, unsigned pc) +void tms9900_disassembler::print_arg (std::ostream &stream, int mode, int arg, const data_buffer ¶ms, offs_t &PC) { int base; @@ -319,7 +227,7 @@ static void print_arg (std::ostream &stream, int mode, int arg, const uint8_t *o util::stream_format(stream, "*R%d", arg); break; case 0x2: /* symbolic|indexed */ - base = readop_arg(opram, pc); + base = readop_arg(params, PC); if (arg) /* indexed */ util::stream_format(stream, "@>%04x(R%d)", base, arg); else /* symbolic (direct) */ @@ -331,11 +239,19 @@ static void print_arg (std::ostream &stream, int mode, int arg, const uint8_t *o } } +tms9900_disassembler::tms9900_disassembler(int model) : m_model_id(model) +{ +} + +u32 tms9900_disassembler::opcode_alignment() const +{ + return 2; +} /***************************************************************************** * Disassemble a single command and return the number of bytes it uses. *****************************************************************************/ -static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const uint8_t *oprom, const uint8_t *opram) +offs_t tms9900_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { int OP, OP2, opc; int sarg, darg, smode, dmode; @@ -355,26 +271,26 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const Additionally, ti990/12 and tms9995 will generate an illegal error when bits 12-15 are non-zero. */ - #define BETTER_0200_DECODING (model_id == TI990_10_ID) - #define COMPLETE_0200_DECODING (/*(model_id == TI990_12_ID) ||*/ (model_id >= TMS9995_ID)) + #define BETTER_0200_DECODING (m_model_id == TI990_10_ID) + #define COMPLETE_0200_DECODING (/*(m_model_id == TI990_12_ID) ||*/ (m_model_id >= TMS9995_ID)) int processor_mask = ps_any; - if ((model_id == TI990_10_ID) /*|| (model_id == TI990_12_ID)*/ || (model_id >= TMS99000_ID)) + if ((m_model_id == TI990_10_ID) /*|| (m_model_id == TI990_12_ID)*/ || (m_model_id >= TMS99000_ID)) processor_mask |= ps_mapper; /* processors with memory mapper (ti990/10, ti990/12, and tms99000 with mapper coprocessor) */ - if (/*(model_id == TI990_12_ID) ||*/ (model_id >= TMS9995_ID)) + if (/*(m_model_id == TI990_12_ID) ||*/ (m_model_id >= TMS9995_ID)) processor_mask |= ps_tms9995; /* ti990/12, tms9995, and later */ - if (/*(model_id == TI990_12_ID) ||*/ (model_id >= TMS99000_ID)) + if (/*(m_model_id == TI990_12_ID) ||*/ (m_model_id >= TMS99000_ID)) processor_mask |= ps_tms99000; /* ti990/12, tms99000, and later */ - /*if ((model_id == TI990_12_ID)) + /*if ((m_model_id == TI990_12_ID)) processor_mask |= ps_ti990_12;*/ /* ti990/12, tms99000, and later */ - PC = pc; - OP = oprom[PC++ - pc] << 8; - OP |= oprom[PC++ - pc]; + offs_t PC = pc; + OP = opcodes.r16(PC); + PC += 2; /* let's identify the opcode */ if (OP >= 0x4000) @@ -434,7 +350,7 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const } /* tms9940 replace a few xops with custom instructions */ - if ((opc == _xop) && ((model_id == TMS9940_ID) || (model_id == TMS9985_ID))) + if ((opc == _xop) && ((m_model_id == TMS9940_ID) || (m_model_id == TMS9985_ID))) { switch (BITS(OP,6,9)) { @@ -473,11 +389,11 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const /* bl and blwp instructions are subroutines */ if (mnemonic != nullptr && mnemonic[0] == 'b' && mnemonic[1] == 'l') - dasmflags = DASMFLAG_STEP_OVER; + dasmflags = STEP_OVER; /* b *r11 and rtwp are returns */ else if (opc == 0x045b || (mnemonic != nullptr && strcmp(mnemonic, "rtwp") == 0)) - dasmflags = DASMFLAG_STEP_OUT; + dasmflags = STEP_OUT; switch (format) { @@ -488,9 +404,9 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const darg = BITS(OP,6,9); util::stream_format(stream, "%-4s ", mnemonic); - print_arg(stream, smode, sarg, opram, pc); + print_arg(stream, smode, sarg, params, PC); util::stream_format(stream, ","); - print_arg(stream, dmode, darg, opram, pc); + print_arg(stream, dmode, darg, params, PC); break; case format_2a: /* jump instructions */ @@ -516,13 +432,13 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const if (format == format_3_9) { util::stream_format(stream, "%-4s ", mnemonic); - print_arg(stream, smode, sarg, opram, pc); + print_arg(stream, smode, sarg, params, PC); util::stream_format(stream, ",R%d", darg); } else { util::stream_format(stream, "%-4s ", mnemonic); - print_arg(stream, smode, sarg, opram, pc); + print_arg(stream, smode, sarg, params, PC); util::stream_format(stream, ",%d", darg); } break; @@ -539,7 +455,7 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const sarg = BITS(OP,12,15); util::stream_format(stream, "%-4s ", mnemonic); - print_arg(stream, smode, sarg, opram, pc); + print_arg(stream, smode, sarg, params, PC); break; case format_7: /* instructions without operands */ @@ -548,13 +464,13 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const case format_8a: /* immediate instructions (destination register) */ darg = BITS(OP,12,15); - sarg = readop_arg(opram, pc); + sarg = readop_arg(params, PC); util::stream_format(stream, "%-4s R%d,>%04x", mnemonic, darg, sarg); break; case format_8b: /* immediate instructions (no destination register) */ - sarg = readop_arg(opram, pc); + sarg = readop_arg(params, PC); util::stream_format(stream, "%-4s >%04x", mnemonic, sarg); break; @@ -567,7 +483,7 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const break; case format_11: /* multiple precision instructions */ - OP2 = readop_arg(opram, pc); + OP2 = readop_arg(params, PC); smode = BITS(OP2,10,11); sarg = BITS(OP2,12,15); @@ -576,14 +492,14 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const byte_count = BITS(OP2,0,3); util::stream_format(stream, "%-4s ", mnemonic); - print_arg(stream, smode, sarg, opram, pc); + print_arg(stream, smode, sarg, params, PC); util::stream_format(stream, ","); - print_arg(stream, dmode, darg, opram, pc); + print_arg(stream, dmode, darg, params, PC); util::stream_format(stream, byte_count ? ",%d" : ",R%d", byte_count); break; case format_12: /* string instructions */ - OP2 = readop_arg(opram, pc); + OP2 = readop_arg(params, PC); smode = BITS(OP2,10,11); sarg = BITS(OP2,12,15); @@ -593,14 +509,14 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const checkpoint = BITS(OP,12,15); util::stream_format(stream, "%-4s ", mnemonic); - print_arg(stream, smode, sarg, opram, pc); + print_arg(stream, smode, sarg, params, PC); util::stream_format(stream, ","); - print_arg(stream, dmode, darg, opram, pc); + print_arg(stream, dmode, darg, params, PC); util::stream_format(stream, byte_count ? ",%d,R%d" : ",R%d,R%d", byte_count, checkpoint); break; case format_13: /* multiple precision shift instructions */ - OP2 = readop_arg(opram, pc); + OP2 = readop_arg(params, PC); smode = BITS(OP2,10,11); sarg = BITS(OP2,12,15); @@ -608,20 +524,20 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const byte_count = BITS(OP2,0,3); util::stream_format(stream, "%-4s ", mnemonic); - print_arg(stream, smode, sarg, opram, pc); + print_arg(stream, smode, sarg, params, PC); util::stream_format(stream, byte_count ? ",%d" : ",R%d", byte_count); util::stream_format(stream, darg ? ",%d" : ",R%d", darg); break; case format_14: /* bit testing instructions */ - OP2 = readop_arg(opram, pc); + OP2 = readop_arg(params, PC); smode = BITS(OP2,10,11); sarg = BITS(OP2,12,15); darg = BITS(OP2,0,9); util::stream_format(stream, "%-4s ", mnemonic); - print_arg(stream, smode, sarg, opram, pc); + print_arg(stream, smode, sarg, params, PC); if (darg == 0x3ff) util::stream_format(stream, ",R0"); else @@ -629,7 +545,7 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const break; case format_15: /* invert order of field instruction */ - OP2 = readop_arg(opram, pc); + OP2 = readop_arg(params, PC); smode = BITS(OP2,10,11); sarg = BITS(OP2,12,15); @@ -637,13 +553,13 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const bit_width = BITS(OP,12,15); util::stream_format(stream, "%-4s ", mnemonic); - print_arg(stream, smode, sarg, opram, pc); + print_arg(stream, smode, sarg, params, PC); util::stream_format(stream, bit_position ? ",(%d," : ",(R%d,", bit_position); util::stream_format(stream, bit_width ? "%d)" : "R%d)", bit_width); break; case format_16: /* field instructions */ - OP2 = readop_arg(opram, pc); + OP2 = readop_arg(params, PC); smode = BITS(OP2,10,11); sarg = BITS(OP2,12,15); @@ -653,15 +569,15 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const bit_width = BITS(OP,12,15); util::stream_format(stream, "%-4s ", mnemonic); - print_arg(stream, smode, sarg, opram, pc); + print_arg(stream, smode, sarg, params, PC); util::stream_format(stream, ","); - print_arg(stream, dmode, darg, opram, pc); + print_arg(stream, dmode, darg, params, PC); util::stream_format(stream, bit_position ? ",(%d," : ",(%d,", bit_position); util::stream_format(stream, bit_width ? "%d)" : "R%d)", bit_width); break; case format_17: /* alter register and jump instructions */ - OP2 = readop_arg(opram, pc); + OP2 = readop_arg(params, PC); displacement = (signed char)BITS(OP2,8,15); sarg = BITS(OP2,4,7); @@ -684,7 +600,7 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const break; case format_19: /* move address instruction */ - OP2 = readop_arg(opram, pc); + OP2 = readop_arg(params, PC); smode = BITS(OP2,10,11); sarg = BITS(OP2,12,15); @@ -692,16 +608,16 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const darg = BITS(OP2,6,9); util::stream_format(stream, "%-4s ", mnemonic); - print_arg(stream, smode, sarg, opram, pc); + print_arg(stream, smode, sarg, params, PC); util::stream_format(stream, ","); - print_arg(stream, dmode, darg, opram, pc); + print_arg(stream, dmode, darg, params, PC); break; case format_20: /* list search instructions */ { const char *condition_code; - OP2 = readop_arg(opram, pc); + OP2 = readop_arg(params, PC); smode = BITS(OP2,10,11); sarg = BITS(OP2,12,15); @@ -746,9 +662,9 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const } util::stream_format(stream, "%-4s %s,", mnemonic, condition_code); - print_arg(stream, smode, sarg, opram, pc); + print_arg(stream, smode, sarg, params, PC); util::stream_format(stream, ","); - print_arg(stream, dmode, darg, opram, pc); + print_arg(stream, dmode, darg, params, PC); break; } @@ -756,7 +672,7 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const { int dest_byte_count; - OP2 = readop_arg(opram, pc); + OP2 = readop_arg(params, PC); smode = BITS(OP2,10,11); sarg = BITS(OP2,12,15); @@ -766,9 +682,9 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const dest_byte_count = BITS(OP,12,15); util::stream_format(stream, "%-4s ", mnemonic); - print_arg(stream, smode, sarg, opram, pc); + print_arg(stream, smode, sarg, params, PC); util::stream_format(stream, ","); - print_arg(stream, dmode, darg, opram, pc); + print_arg(stream, dmode, darg, params, PC); util::stream_format(stream, byte_count ? ",%d" : ",R%d", byte_count); util::stream_format(stream, dest_byte_count ? ",%d" : ",R%d", dest_byte_count); break; @@ -781,20 +697,5 @@ static unsigned Dasm9900 (std::ostream &stream, unsigned pc, int model_id, const break; } - return (PC - pc) | DASMFLAG_SUPPORTED | dasmflags; -} - -CPU_DISASSEMBLE( tms9900 ) -{ - return Dasm9900(stream, pc, TMS9900_ID, oprom, opram); -} - -CPU_DISASSEMBLE( tms9980 ) -{ - return Dasm9900(stream, pc, TMS9980_ID, oprom, opram); -} - -CPU_DISASSEMBLE( tms9995 ) -{ - return Dasm9900(stream, pc, TMS9995_ID, oprom, opram); + return (PC - pc) | SUPPORTED | dasmflags; } diff --git a/src/devices/cpu/tms9900/9900dasm.h b/src/devices/cpu/tms9900/9900dasm.h new file mode 100644 index 00000000000..53fa192284d --- /dev/null +++ b/src/devices/cpu/tms9900/9900dasm.h @@ -0,0 +1,136 @@ +// license:BSD-3-Clause +// copyright-holders:Raphael Nabet +/***************************************************************************** + * + * 9900dasm.c + * TMS 9900 family disassembler + * + *****************************************************************************/ + +#ifndef MAME_CPU_TMS9900_TMS9900DASM_H +#define MAME_CPU_TMS9900_TMS9900DASM_H + +#pragma once + +class tms9900_disassembler : public util::disasm_interface +{ +public: + tms9900_disassembler(int model); + virtual ~tms9900_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum format_t + { + format_1, /* 2 address instructions */ + format_2a, /* jump instructions */ + format_2b, /* bit I/O instructions */ + format_3_9, /* logical, multiply, and divide instructions */ + format_4, /* CRU instructions */ + format_5, /* register shift instructions */ + format_6, /* single address instructions */ + format_7, /* instructions without operands */ + format_8a, /* immediate instructions (destination register) */ + format_8b, /* immediate instructions (no destination register) */ + format_9, /* extended operation instruction */ + format_10, /* memory map file instruction */ + format_11, /* multiple precision instructions */ + format_12, /* string instructions */ + format_13, /* multiple precision shift instructions */ + format_14, /* bit testing instructions */ + format_15, /* invert order of field instruction */ + format_16, /* field instructions */ + format_17, /* alter register and jump instructions */ + format_18, /* single register operand instructions */ + format_liim,/* format for liim (looks like format 18) */ + format_19, /* move address instruction */ + format_20, /* list search instructions */ + format_21, /* extend precision instruction */ + + illegal + }; + + /* definitions for flags */ + enum + { + /* processor set on which opcodes are available */ + ps_any = 0x01, /* every processor in the tms9900/ti990 family */ + ps_mapper = 0x02, /* processors with memory mapper (ti990/10, ti990/12, + and tms99000 with mapper coprocessor) */ + ps_tms9995 = 0x04, /* ti990/12, tms9995, and later */ + ps_tms99000 = 0x08, /* ti990/12, tms99000, and later */ + ps_ti990_12 = 0x10, /* ti990/12 only */ + + /* additional flags for special decoding */ + sd_11 = 0x100, /* bit 11 should be cleared in li, ai, andi, ori, ci, stwp, stst */ + sd_11_15 = 0x200 /* bits 11-15 should be cleared in lwpi, limi, idle, rset, rtwp, ckon, ckof, lrex */ + }; + + struct description_t + { + const char *mnemonic; + format_t format; + int flags; + }; + + + enum opcodes { + /* basic instruction set */ + _a=0, _ab, _c, _cb, _s, _sb, _soc, _socb, _szc, _szcb, + _mov, _movb, _coc, _czc, _xor, _mpy, _div, _xop, _b, _bl, + _blwp, _clr, _seto, _inv, _neg, _abs, _swpb, _inc, _inct, _dec, + _dect, _x, _ldcr, _stcr, _sbo, _sbz, _tb, _jeq, _jgt, _jh, + _jhe, _jl, _jle, _jlt, _jmp, _jnc, _jne, _jno, _joc, _jop, + _sla, _sra, _src, _srl, _ai, _andi, _ci, _li, _ori, _lwpi, + _limi, _stst, _stwp, _rtwp, _idle, _rset, _ckof, _ckon, _lrex, + + /* mapper instruction set */ + _lds, _ldd, _lmf, + + /* tms9995 instruction set */ + _divs, _mpys, _lst, _lwp, + + /* tms99000 instruction set */ + _bind, + + /* ti990/12 instruction set */ + _sram, _slam, _rto, _lto, _cnto, _slsl, _slsp, _bdc, _dbc, _swpm, + _xorm, _orm, _andm, _sm, _am, _mova, _emd, _eint, _dint, _stpc, + _cs, _seqb, _movs, _lim, _lcs, _blsk, _mvsr, _mvsk, _pops, _pshs, + + _cri, _cdi, _negr, _negd, _cre, _cde, _cer, _ced, _nrm, _tmb, + _tcmb, _tsmb, _srj, _arj, _xit, _insf, _xv, _xf, _ar, _cir, + _sr, _mr, _dr, _lr, _str, _iof, _sneb, _crc, _ts, _ad, + _cid, _sd, _md, _dd, _ld, _std, _ep, + + /* tms9940-only instruction set */ + _liim, _dca, _dcs, + + _ill + }; + + static const description_t descriptions[144+3+1]; + static const enum opcodes ops_4000_ffff_s12[12]; + static const enum opcodes ops_2000_3fff_s10[8]; + static const enum opcodes ops_1000_1fff_s8[16]; + static const enum opcodes ops_0e40_0fff_s6[7]; + static const enum opcodes ops_0e00_0e3f_s4[4]; + static const enum opcodes ops_0c40_0dff_s6[7]; + static const enum opcodes ops_0c10_0c3f_s4[3]; + static const enum opcodes ops_0c00_0c0f_s0[16]; + static const enum opcodes ops_0800_0bff_s8[4]; + static const enum opcodes ops_0400_07ff_s6[16]; + static const enum opcodes ops_0200_03ff_s5[16]; + static const enum opcodes ops_0100_01ff_s6[4]; + static const enum opcodes ops_0030_00ff_s4[13]; + static const enum opcodes ops_001c_002f_s0[20]; + + int m_model_id; + + inline uint16_t readop_arg(const data_buffer ¶ms, offs_t &PC); + void print_arg (std::ostream &stream, int mode, int arg, const data_buffer ¶ms, offs_t &PC); +}; + +#endif diff --git a/src/devices/cpu/tms9900/ti990_10.cpp b/src/devices/cpu/tms9900/ti990_10.cpp index 3f9f60b4129..bcb96cb6d90 100644 --- a/src/devices/cpu/tms9900/ti990_10.cpp +++ b/src/devices/cpu/tms9900/ti990_10.cpp @@ -25,6 +25,7 @@ #include "emu.h" #include "ti990_10.h" +#include "9900dasm.h" /* The following defines can be set to 0 or 1 to disable or enable certain @@ -122,22 +123,10 @@ uint32_t ti990_10_device::execute_input_lines() const return 2; } -// device_disasm_interface overrides -uint32_t ti990_10_device::disasm_min_opcode_bytes() const -{ - return 2; -} - -uint32_t ti990_10_device::disasm_max_opcode_bytes() const -{ - return 6; -} - // TODO: check 9900dasm -offs_t ti990_10_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *ti990_10_device::create_disassembler() { - extern CPU_DISASSEMBLE( tms9900 ); - return CPU_DISASSEMBLE_NAME(tms9900)(this, stream, pc, oprom, opram, options); + return new tms9900_disassembler(TMS9900_ID); } DEFINE_DEVICE_TYPE(TI990_10, ti990_10_device, "ti990_10_cpu", "TI990/10 CPU") diff --git a/src/devices/cpu/tms9900/ti990_10.h b/src/devices/cpu/tms9900/ti990_10.h index bd2d6a65d43..6e9b945e17e 100644 --- a/src/devices/cpu/tms9900/ti990_10.h +++ b/src/devices/cpu/tms9900/ti990_10.h @@ -34,9 +34,7 @@ protected: void execute_run() override; // device_disasm_interface overrides - uint32_t disasm_min_opcode_bytes() const override; - uint32_t disasm_max_opcode_bytes() const override; - offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual space_config_vector memory_space_config() const override; diff --git a/src/devices/cpu/tms9900/tms9900.cpp b/src/devices/cpu/tms9900/tms9900.cpp index e0b207f3335..72631d68ae1 100644 --- a/src/devices/cpu/tms9900/tms9900.cpp +++ b/src/devices/cpu/tms9900/tms9900.cpp @@ -110,6 +110,7 @@ #include "emu.h" #include "tms9900.h" +#include "9900dasm.h" #define NOPRG -1 @@ -2751,20 +2752,10 @@ uint32_t tms99xx_device::execute_input_lines() const // execute_burn = nop // device_disasm_interface overrides -uint32_t tms99xx_device::disasm_min_opcode_bytes() const -{ - return 2; -} - -uint32_t tms99xx_device::disasm_max_opcode_bytes() const -{ - return 6; -} -offs_t tms99xx_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *tms99xx_device::create_disassembler() { - extern CPU_DISASSEMBLE( tms9900 ); - return CPU_DISASSEMBLE_NAME(tms9900)(this, stream, pc, oprom, opram, options); + return new tms9900_disassembler(TMS9900_ID); } diff --git a/src/devices/cpu/tms9900/tms9900.h b/src/devices/cpu/tms9900/tms9900.h index 5486043aaa1..e7a4c3ebd2a 100644 --- a/src/devices/cpu/tms9900/tms9900.h +++ b/src/devices/cpu/tms9900/tms9900.h @@ -82,9 +82,7 @@ protected: virtual void execute_run() override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual space_config_vector memory_space_config() const override; diff --git a/src/devices/cpu/tms9900/tms9980a.cpp b/src/devices/cpu/tms9900/tms9980a.cpp index b2dcc2f389a..fc1d12afbc8 100644 --- a/src/devices/cpu/tms9900/tms9980a.cpp +++ b/src/devices/cpu/tms9900/tms9980a.cpp @@ -53,6 +53,7 @@ #include "emu.h" #include "tms9980a.h" +#include "9900dasm.h" /* The following defines can be set to 0 or 1 to disable or enable certain @@ -282,20 +283,10 @@ uint32_t tms9980a_device::execute_input_lines() const // execute_burn = nop // device_disasm_interface overrides -uint32_t tms9980a_device::disasm_min_opcode_bytes() const -{ - return 2; -} - -uint32_t tms9980a_device::disasm_max_opcode_bytes() const -{ - return 6; -} -offs_t tms9980a_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *tms9980a_device::create_disassembler() { - extern CPU_DISASSEMBLE( tms9980 ); - return CPU_DISASSEMBLE_NAME(tms9980)(this, stream, pc, oprom, opram, options); + return new tms9900_disassembler(TMS9980_ID); } DEFINE_DEVICE_TYPE(TMS9980A, tms9980a_device, "tms9980a", "TMS9980A") diff --git a/src/devices/cpu/tms9900/tms9980a.h b/src/devices/cpu/tms9900/tms9980a.h index 34f6eadc434..72adcaf56c5 100644 --- a/src/devices/cpu/tms9900/tms9980a.h +++ b/src/devices/cpu/tms9900/tms9980a.h @@ -44,9 +44,8 @@ protected: uint32_t execute_input_lines() const override; void execute_set_input(int irqline, int state) override; - uint32_t disasm_min_opcode_bytes() const override; - uint32_t disasm_max_opcode_bytes() const override; - offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; + address_space_config m_program_config80; address_space_config m_io_config80; }; diff --git a/src/devices/cpu/tms9900/tms9995.cpp b/src/devices/cpu/tms9900/tms9995.cpp index d6bab5aaa4b..542f51f88ae 100644 --- a/src/devices/cpu/tms9900/tms9995.cpp +++ b/src/devices/cpu/tms9900/tms9995.cpp @@ -91,6 +91,7 @@ #include "emu.h" #include "tms9995.h" +#include "9900dasm.h" #define NOPRG -1 @@ -3514,20 +3515,9 @@ uint32_t tms9995_device::execute_input_lines() const return 2; } -uint32_t tms9995_device::disasm_min_opcode_bytes() const +util::disasm_interface *tms9995_device::create_disassembler() { - return 2; -} - -uint32_t tms9995_device::disasm_max_opcode_bytes() const -{ - return 6; -} - -offs_t tms9995_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) -{ - extern CPU_DISASSEMBLE( tms9995 ); - return CPU_DISASSEMBLE_NAME(tms9995)(this, stream, pc, oprom, opram, options); + return new tms9900_disassembler(TMS9995_ID); } diff --git a/src/devices/cpu/tms9900/tms9995.h b/src/devices/cpu/tms9900/tms9995.h index a0ffa861f8c..ff0357e74e4 100644 --- a/src/devices/cpu/tms9900/tms9995.h +++ b/src/devices/cpu/tms9900/tms9995.h @@ -94,9 +94,7 @@ protected: virtual void execute_run() override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual space_config_vector memory_space_config() const override; diff --git a/src/devices/cpu/ucom4/ucom4.cpp b/src/devices/cpu/ucom4/ucom4.cpp index 81b4e8ae913..8d1523751a9 100644 --- a/src/devices/cpu/ucom4/ucom4.cpp +++ b/src/devices/cpu/ucom4/ucom4.cpp @@ -22,6 +22,7 @@ #include "emu.h" #include "ucom4.h" +#include "ucom4d.h" #include "debugger.h" @@ -136,14 +137,12 @@ void ucom4_cpu_device::state_string_export(const device_state_entry &entry, std: } } -offs_t ucom4_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +util::disasm_interface *ucom4_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE(ucom4); - return CPU_DISASSEMBLE_NAME(ucom4)(this, stream, pc, oprom, opram, options); + return new ucom4_disassembler; } - //------------------------------------------------- // device_start - device-specific startup //------------------------------------------------- diff --git a/src/devices/cpu/ucom4/ucom4.h b/src/devices/cpu/ucom4/ucom4.h index a442e5c676a..6db82e1a41e 100644 --- a/src/devices/cpu/ucom4/ucom4.h +++ b/src/devices/cpu/ucom4/ucom4.h @@ -134,9 +134,7 @@ protected: virtual space_config_vector memory_space_config() const override; // device_disasm_interface overrides - virtual u32 disasm_min_opcode_bytes() const override { return 1; } - virtual u32 disasm_max_opcode_bytes() const override { return 2; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) override; + virtual util::disasm_interface *create_disassembler() override; // device_state_interface overrides virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; diff --git a/src/devices/cpu/ucom4/ucom4d.cpp b/src/devices/cpu/ucom4/ucom4d.cpp index f83801813ee..678c1952dfc 100644 --- a/src/devices/cpu/ucom4/ucom4d.cpp +++ b/src/devices/cpu/ucom4/ucom4d.cpp @@ -7,24 +7,9 @@ */ #include "emu.h" -#include "debugger.h" -#include "ucom4.h" +#include "ucom4d.h" - -enum e_mnemonics -{ - mLI, mL, mLM, mLDI, mLDZ, mS, mTAL, mTLA, - mX, mXI, mXD, mXM, mXMI, mXMD, mAD, mADC, mADS, mDAA, mDAS, - mEXL, mCLA, mCMA, mCIA, mCLC, mSTC, mTC, mINC, mDEC, mIND, mDED, - mRMB, mSMB, mREB, mSEB, mRPB, mSPB, mJMP, mJCP, mJPA, mCAL, mCZP, mRT, mRTS, - mCI, mCM, mCMB, mTAB, mCLI, mTMB, mTPA, mTPB, - mTIT, mIA, mIP, mOE, mOP, mOCD, mNOP, - mILL, - mTAW, mTAZ, mTHX, mTLY, mXAW, mXAZ, mXHR, mXHX, mXLS, mXLY, mXC, - mSFB, mRFB, mFBT, mFBF, mRAR, mINM, mDEM, mSTM, mTTM, mEI, mDI -}; - -static const char *const s_mnemonics[] = +const char *const ucom4_disassembler::s_mnemonics[] = { "LI", "L", "LM", "LDI", "LDZ", "S", "TAL", "TLA", "X", "XI", "XD", "XM", "XMI", "XMD", "AD", "ADC", "ADS", "DAA", "DAS", @@ -38,7 +23,7 @@ static const char *const s_mnemonics[] = }; // number of bits per opcode parameter, 2 digits means opcode is 2 bytes -static const u8 s_bits[] = +const u8 ucom4_disassembler::s_bits[] = { 4, 0, 2, 80, 4, 0, 0, 0, 0, 0, 0, 2, 2, 2, 0, 0, 0, 0, 0, @@ -51,15 +36,12 @@ static const u8 s_bits[] = 2, 2, 2, 2, 0, 0, 0, 80, 0, 0, 0 }; -#define _OVER DASMFLAG_STEP_OVER -#define _OUT DASMFLAG_STEP_OUT - -static const u32 s_flags[] = +const u32 ucom4_disassembler::s_flags[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, _OVER, _OVER, _OUT, _OUT, + 0, 0, 0, 0, 0, 0, 0, 0, 0, STEP_OVER, STEP_OVER, STEP_OUT, STEP_OUT, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, @@ -68,7 +50,7 @@ static const u32 s_flags[] = }; -static const u8 ucom4_mnemonic[0x100] = +const u8 ucom4_disassembler::ucom4_mnemonic[0x100] = { /* 0x00 */ mNOP, mDI, mS, mTIT, mTC, mTTM, mDAA, mTAL, @@ -112,11 +94,31 @@ static const u8 ucom4_mnemonic[0x100] = }; +u32 ucom4_disassembler::opcode_alignment() const +{ + return 1; +} + +u32 ucom4_disassembler::interface_flags() const +{ + return PAGED2LEVEL; +} + +u32 ucom4_disassembler::page_address_bits() const +{ + return 6; +} + +u32 ucom4_disassembler::page2_address_bits() const +{ + return 2; +} + -CPU_DISASSEMBLE(ucom4) +offs_t ucom4_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - int pos = 0; - u8 op = oprom[pos++]; + offs_t pos = pc; + u8 op = opcodes.r8(pos++); u8 instr = ucom4_mnemonic[op]; util::stream_format(stream,"%-4s ", s_mnemonics[instr]); @@ -128,7 +130,7 @@ CPU_DISASSEMBLE(ucom4) u16 param = op & ((1 << (bits % 10)) - 1); if (bits / 10) { - u8 op2 = oprom[pos++]; + u8 op2 = opcodes.r8(pos++); param = (param << (bits / 10)) | (op2 & ((1 << (bits / 10)) - 1)); bits = (bits % 10) + (bits / 10); } @@ -148,5 +150,5 @@ CPU_DISASSEMBLE(ucom4) util::stream_format(stream, "$%03X", param); } - return pos | s_flags[instr] | DASMFLAG_SUPPORTED; + return (pos - pc) | s_flags[instr] | SUPPORTED; } diff --git a/src/devices/cpu/ucom4/ucom4d.h b/src/devices/cpu/ucom4/ucom4d.h new file mode 100644 index 00000000000..2dd3be4914b --- /dev/null +++ b/src/devices/cpu/ucom4/ucom4d.h @@ -0,0 +1,48 @@ +// license:BSD-3-Clause +// copyright-holders:hap +/* + + NEC uCOM-4 MCU family disassembler + +*/ + + +#ifndef MAME_CPU_UCOM4_UCOM4DASM_H +#define MAME_CPU_UCOM4_UCOM4DASM_H + +#pragma once + +class ucom4_disassembler : public util::disasm_interface +{ +public: + ucom4_disassembler() = default; + virtual ~ucom4_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual u32 interface_flags() const override; + virtual u32 page_address_bits() const override; + virtual u32 page2_address_bits() const override; + + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + enum e_mnemonics + { + mLI, mL, mLM, mLDI, mLDZ, mS, mTAL, mTLA, + mX, mXI, mXD, mXM, mXMI, mXMD, mAD, mADC, mADS, mDAA, mDAS, + mEXL, mCLA, mCMA, mCIA, mCLC, mSTC, mTC, mINC, mDEC, mIND, mDED, + mRMB, mSMB, mREB, mSEB, mRPB, mSPB, mJMP, mJCP, mJPA, mCAL, mCZP, mRT, mRTS, + mCI, mCM, mCMB, mTAB, mCLI, mTMB, mTPA, mTPB, + mTIT, mIA, mIP, mOE, mOP, mOCD, mNOP, + mILL, + mTAW, mTAZ, mTHX, mTLY, mXAW, mXAZ, mXHR, mXHX, mXLS, mXLY, mXC, + mSFB, mRFB, mFBT, mFBF, mRAR, mINM, mDEM, mSTM, mTTM, mEI, mDI + }; + + static const char *const s_mnemonics[]; + static const u8 s_bits[]; + static const u32 s_flags[]; + static const u8 ucom4_mnemonic[0x100]; +}; + +#endif diff --git a/src/devices/cpu/unsp/unsp.cpp b/src/devices/cpu/unsp/unsp.cpp index cb14e9cdec4..c9e346cf981 100644 --- a/src/devices/cpu/unsp/unsp.cpp +++ b/src/devices/cpu/unsp/unsp.cpp @@ -10,6 +10,7 @@ #include "emu.h" #include "unsp.h" +#include "unspdasm.h" #include "debugger.h" @@ -30,10 +31,9 @@ device_memory_interface::space_config_vector unsp_device::memory_space_config() }; } -offs_t unsp_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *unsp_device::create_disassembler() { - extern CPU_DISASSEMBLE( unsp ); - return CPU_DISASSEMBLE_NAME(unsp)(this, stream, pc, oprom, opram, options); + return new unsp_disassembler; } diff --git a/src/devices/cpu/unsp/unsp.h b/src/devices/cpu/unsp/unsp.h index 5a445e05099..331bbf46786 100644 --- a/src/devices/cpu/unsp/unsp.h +++ b/src/devices/cpu/unsp/unsp.h @@ -75,9 +75,7 @@ protected: virtual void state_export(const device_state_entry &entry) override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/unsp/unspdasm.cpp b/src/devices/cpu/unsp/unspdasm.cpp index 68d620fb7b6..b4a731f5fcf 100644 --- a/src/devices/cpu/unsp/unspdasm.cpp +++ b/src/devices/cpu/unsp/unspdasm.cpp @@ -9,22 +9,22 @@ \**************************/ #include "emu.h" -#include +#include "unspdasm.h" /*****************************************************************************/ -static const char *reg[] = +const char *unsp_disassembler::reg[] = { "sp", "r1", "r2", "r3", "r4", "bp", "sr", "pc" }; -static const char *jmp[] = +const char *unsp_disassembler::jmp[] = { "jb", "jae", "jge", "jl", "jne", "je", "jpl", "jmi", "jbe", "ja", "jle", "jg", "jvc", "jvs", "jmp", "" }; -static const char *alu[] = +const char *unsp_disassembler::alu[] = { "add", "adc", "sub", "sbc", "cmp", "", "neg", "", @@ -44,12 +44,17 @@ static const char *alu[] = /*****************************************************************************/ -#define UNSP_DASM_OK ((OP2X ? 2 : 1) | DASMFLAG_SUPPORTED) +#define UNSP_DASM_OK ((OP2X ? 2 : 1) | SUPPORTED) -CPU_DISASSEMBLE(unsp) +u32 unsp_disassembler::opcode_alignment() const { - uint16_t op = *(uint16_t *)oprom; - uint16_t imm16 = *(uint16_t *)(oprom + 2); + return 1; +} + +offs_t unsp_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + uint16_t op = opcodes.r16(pc); + uint16_t imm16 = opcodes.r16(pc+1); op = big_endianize_int16(op); imm16 = big_endianize_int16(imm16); diff --git a/src/devices/cpu/unsp/unspdasm.h b/src/devices/cpu/unsp/unspdasm.h new file mode 100644 index 00000000000..ef25b2a433b --- /dev/null +++ b/src/devices/cpu/unsp/unspdasm.h @@ -0,0 +1,32 @@ +// license:BSD-3-Clause +// copyright-holders:Ryan Holtz +/**************************\ +* +* SunPlus u'nSP disassembler +* +* by Ryan Holtz +* +\**************************/ + + +#ifndef MAME_CPU_UNSP_UNSPDASM_H +#define MAME_CPU_UNSP_UNSPDASM_H + +#pragma once + +class unsp_disassembler : public util::disasm_interface +{ +public: + unsp_disassembler() = default; + virtual ~unsp_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *reg[]; + static const char *jmp[]; + static const char *alu[]; +}; + +#endif diff --git a/src/devices/cpu/upd7725/dasm7725.cpp b/src/devices/cpu/upd7725/dasm7725.cpp index f2e644e0bec..06a9fdd3d16 100644 --- a/src/devices/cpu/upd7725/dasm7725.cpp +++ b/src/devices/cpu/upd7725/dasm7725.cpp @@ -10,11 +10,16 @@ ***************************************************************************/ #include "emu.h" -#include "upd7725.h" +#include "dasm7725.h" -CPU_DISASSEMBLE(upd7725) +u32 necdsp_disassembler::opcode_alignment() const { - uint32_t opcode = oprom[2] | (oprom[1] << 8) | (oprom[0] << 16); + return 1; +} + +offs_t necdsp_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + uint32_t opcode = opcodes.r32(pc); uint32_t type = (opcode >> 22); // printf("dasm: PC %x opcode %08x\n", pc, opcode); @@ -220,5 +225,5 @@ CPU_DISASSEMBLE(upd7725) } } - return 1 | DASMFLAG_SUPPORTED; + return 1 | SUPPORTED; } diff --git a/src/devices/cpu/upd7725/dasm7725.h b/src/devices/cpu/upd7725/dasm7725.h new file mode 100644 index 00000000000..5280c3e4a46 --- /dev/null +++ b/src/devices/cpu/upd7725/dasm7725.h @@ -0,0 +1,27 @@ +// license:BSD-3-Clause +// copyright-holders:R. Belmont,byuu +/*************************************************************************** + + dasm7725.c + Disassembler for the portable uPD7725 emulator. + Written by byuu + MAME conversion by R. Belmont + +***************************************************************************/ + +#ifndef MAME_CPU_UPD7725_DASM7725_H +#define MAME_CPU_UPD7725_DASM7725_H + +#pragma once + +class necdsp_disassembler : public util::disasm_interface +{ +public: + necdsp_disassembler() = default; + virtual ~necdsp_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + +#endif diff --git a/src/devices/cpu/upd7725/upd7725.cpp b/src/devices/cpu/upd7725/upd7725.cpp index 7ef876613db..b509c302aa0 100644 --- a/src/devices/cpu/upd7725/upd7725.cpp +++ b/src/devices/cpu/upd7725/upd7725.cpp @@ -14,6 +14,7 @@ #include "emu.h" #include "debugger.h" #include "upd7725.h" +#include "dasm7725.h" //************************************************************************** @@ -316,35 +317,13 @@ void necdsp_device::execute_set_input(int inputnum, int state) } //------------------------------------------------- -// disasm_min_opcode_bytes - return the length -// of the shortest instruction, in bytes -//------------------------------------------------- - -uint32_t necdsp_device::disasm_min_opcode_bytes() const -{ - return 4; -} - - -//------------------------------------------------- -// disasm_max_opcode_bytes - return the length -// of the longest instruction, in bytes -//------------------------------------------------- - -uint32_t necdsp_device::disasm_max_opcode_bytes() const -{ - return 4; -} - -//------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t necdsp_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *necdsp_device::create_disassembler() { - extern CPU_DISASSEMBLE( upd7725 ); - return CPU_DISASSEMBLE_NAME(upd7725)(this, stream, pc, oprom, opram, options); + return new necdsp_disassembler; } void necdsp_device::execute_run() diff --git a/src/devices/cpu/upd7725/upd7725.h b/src/devices/cpu/upd7725/upd7725.h index 76cc13b9226..63f7b888ef8 100644 --- a/src/devices/cpu/upd7725/upd7725.h +++ b/src/devices/cpu/upd7725/upd7725.h @@ -107,9 +107,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // inline data const address_space_config m_program_config, m_data_config; diff --git a/src/devices/cpu/upd7810/upd7810.cpp b/src/devices/cpu/upd7810/upd7810.cpp index 67b6818ec72..3c23ebb5ebb 100644 --- a/src/devices/cpu/upd7810/upd7810.cpp +++ b/src/devices/cpu/upd7810/upd7810.cpp @@ -374,6 +374,7 @@ STOP 01001000 10111011 12 stop #include "debugger.h" #include "upd7810_macros.h" +#include "upd7810_dasm.h" DEFINE_DEVICE_TYPE(UPD7810, upd7810_device, "upd7810", "uPD7810") @@ -519,28 +520,24 @@ device_memory_interface::space_config_vector upd7810_device::memory_space_config }; } -offs_t upd7810_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *upd7810_device::create_disassembler() { - extern CPU_DISASSEMBLE( upd7810 ); - return CPU_DISASSEMBLE_NAME(upd7810)(this, stream, pc, oprom, opram, options); + return new upd7810_disassembler; } -offs_t upd7807_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *upd7807_device::create_disassembler() { - extern CPU_DISASSEMBLE( upd7807 ); - return CPU_DISASSEMBLE_NAME(upd7807)(this, stream, pc, oprom, opram, options); + return new upd7807_disassembler; } -offs_t upd7801_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *upd7801_device::create_disassembler() { - extern CPU_DISASSEMBLE( upd7801 ); - return CPU_DISASSEMBLE_NAME(upd7801)(this, stream, pc, oprom, opram, options); + return new upd7801_disassembler; } -offs_t upd78c05_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *upd78c05_device::create_disassembler() { - extern CPU_DISASSEMBLE( upd78c05 ); - return CPU_DISASSEMBLE_NAME(upd78c05)(this, stream, pc, oprom, opram, options); + return new upd78c05_disassembler; } WRITE8_MEMBER(upd7810_device::pa_w) diff --git a/src/devices/cpu/upd7810/upd7810.h b/src/devices/cpu/upd7810/upd7810.h index a7d9ec13793..f446cf6bc43 100644 --- a/src/devices/cpu/upd7810/upd7810.h +++ b/src/devices/cpu/upd7810/upd7810.h @@ -227,9 +227,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void handle_timers(int cycles); virtual void upd7810_take_irq(); @@ -1443,7 +1441,7 @@ public: upd7807_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); protected: - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void configure_ops() override; }; @@ -1457,7 +1455,7 @@ public: protected: virtual void device_reset() override; virtual void execute_set_input(int inputnum, int state) override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void handle_timers(int cycles) override; virtual void upd7810_take_irq() override; virtual void configure_ops() override; @@ -1477,7 +1475,7 @@ protected: virtual void device_reset() override; virtual uint64_t execute_clocks_to_cycles(uint64_t clocks) const override { return (clocks + 4 - 1) / 4; } virtual uint64_t execute_cycles_to_clocks(uint64_t cycles) const override { return (cycles * 4); } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; virtual void handle_timers(int cycles) override; virtual void configure_ops() override; }; diff --git a/src/devices/cpu/upd7810/upd7810_dasm.cpp b/src/devices/cpu/upd7810/upd7810_dasm.cpp index f3da1ba4160..1af4415486e 100644 --- a/src/devices/cpu/upd7810/upd7810_dasm.cpp +++ b/src/devices/cpu/upd7810/upd7810_dasm.cpp @@ -9,249 +9,52 @@ *****************************************************************************/ #include "emu.h" -#include "debugger.h" -#include "upd7810.h" +#include "upd7810_dasm.h" -namespace { +const char *upd7810_base_disassembler::dasm_s::name() const +{ + return token_names[m_token]; +} + +const char *upd7810_base_disassembler::dasm_s::args() const +{ + return (m_token != prefix) ? reinterpret_cast(m_args) : nullptr; +} -class dasm_s +bool upd7810_base_disassembler::dasm_s::is_prefix() const { -public: - const char *name() const { return token_names[m_token]; } - const char *args() const { return (m_token != prefix) ? reinterpret_cast(m_args) : nullptr; } + return m_token == prefix; +} - bool is_prefix() const { return m_token == prefix; } - bool is_call() const { return (m_token == CALB) || (m_token == CALF) || (m_token == CALL) || (m_token == CALT); } - bool is_return() const { return (m_token == RET) || (m_token == RETI); } +bool upd7810_base_disassembler::dasm_s::is_call() const +{ + return (m_token == CALB) || (m_token == CALF) || (m_token == CALL) || (m_token == CALT); +} - const dasm_s &prefix_get(uint8_t op) const { assert(m_token == prefix); return reinterpret_cast(m_args)[op]; } +bool upd7810_base_disassembler::dasm_s::is_return() const +{ + return (m_token == RET) || (m_token == RETI); +} - static const dasm_s XX_7810[256]; - static const dasm_s XX_7807[256]; +const upd7810_base_disassembler::dasm_s &upd7810_base_disassembler::dasm_s::prefix_get(uint8_t op) const +{ + assert(m_token == prefix); + return reinterpret_cast(m_args)[op]; +} - static const dasm_s XX_7801[256]; - static const dasm_s XX_78c05[256]; +upd7810_base_disassembler::dasm_s::dasm_s() : m_token(illegal), m_args(nullptr) +{ +} -protected: - enum - { - prefix = 0, - illegal, - ACI, - ADC, - ADCW, - ADCX, - ADD, - ADDNC, - ADDNCW, - ADDNCX, - ADDW, - ADDX, - ADI, - ADINC, - ANA, - ANAW, - ANAX, - AND, - ANI, - ANIW, - BIT, - BLOCK, - CALB, - CALF, - CALL, - CALT, - CLC, - CLR, /* 7807 */ - CMC, /* 7807 */ - DAA, - DADC, - DADD, - DADDNC, - DAN, - DCR, - DCRW, - DCX, - DEQ, - DGT, - DI, - DIV, - DLT, - DMOV, - DNE, - DOFF, - DON, - DOR, - DRLL, - DRLR, - DSBB, - DSLL, - DSLR, - DSUB, - DSUBNB, - DXR, - EADD, - EI, - EQA, - EQAW, - EQAX, - EQI, - EQIW, - ESUB, - EX, /* 7801 */ - EXA, - EXH, - EXX, - EXR, /* 7807 */ - GTA, - GTAW, - GTAX, - GTI, - GTIW, - HALT, - IN, /* 7801 */ - INR, - INRW, - INX, - JB, - JEA, - JMP, - JR, - JRE, - LBCD, - LDAW, - LDAX, - LDEAX, - LDED, - LHLD, - LSPD, - LTA, - LTAW, - LTAX, - LTI, - LTIW, - LXI, - MOV, - MUL, - MVI, - MVIW, - MVIX, - NEA, - NEAW, - NEAX, - NEGA, - NEI, - NEIW, - NOP, - NOT, /* 7807 */ - OFFA, - OFFAW, - OFFAX, - OFFI, - OFFIW, - ONA, - ONAW, - ONAX, - ONI, - ONIW, - OR, /* 7807 */ - ORA, - ORAW, - ORAX, - ORI, - ORIW, - OUT, /* 7801 */ - PER, /* 7801 */ - PEX, /* 7801 */ - POP, - PUSH, - RET, - RETI, - RETS, - RLD, - RLL, - RLR, - RRD, - SBB, - SBBW, - SBBX, - SBCD, - SBI, - SDED, - SETB, /* 7807 */ - SHLD, - SIO, /* 7801 */ - SK, - SKIT, - SKN, - SKNIT, - SLL, - SLLC, - SLR, - SLRC, - SOFTI, - SSPD, - STAW, - STAX, - STC, - STEAX, - STM, /* 7801 */ - STOP, - SUB, - SUBNB, - SUBNBW, - SUBNBX, - SUBW, - SUBX, - SUI, - SUINB, - TABLE, - XOR, /* 7807 */ - XRA, - XRAW, - XRAX, - XRI - }; - - dasm_s() : m_token(illegal), m_args(nullptr) { } - dasm_s(uint8_t t, const char *a) : m_token(t), m_args(a) { } - dasm_s(const dasm_s (&a)[256]) : m_token(prefix), m_args(a) { } - - uint8_t m_token; - const void *m_args; - - static const char *const token_names[]; - - static const dasm_s d48_7810[256]; - static const dasm_s d48_7807[256]; - static const dasm_s d4C_7810[256]; - static const dasm_s d4C_7807[256]; - static const dasm_s d4D_7810[256]; - static const dasm_s d4D_7807[256]; - static const dasm_s d60[256]; - static const dasm_s d64_7810[256]; - static const dasm_s d64_7807[256]; - static const dasm_s d70[256]; - static const dasm_s d74[256]; - - static const dasm_s d48_7801[256]; - static const dasm_s d4C_7801[256]; - static const dasm_s d4D_7801[256]; - static const dasm_s d60_7801[256]; - static const dasm_s d64_7801[256]; - static const dasm_s d70_7801[256]; - static const dasm_s d74_7801[256]; - - static const dasm_s d48_78c05[256]; - static const dasm_s d4C_78c05[256]; - static const dasm_s d4D_78c05[256]; - static const dasm_s d60_78c05[256]; - static const dasm_s d64_78c05[256]; - static const dasm_s d70_78c05[256]; - static const dasm_s d74_78c05[256]; -}; +upd7810_base_disassembler::dasm_s::dasm_s(uint8_t t, const char *a) : m_token(t), m_args(a) +{ +} + +upd7810_base_disassembler::dasm_s::dasm_s(const dasm_s (&a)[256]) : m_token(prefix), m_args(a) +{ +} -const char *const dasm_s::token_names[] = +const char *const upd7810_base_disassembler::dasm_s::token_names[] = { "", "illegal", @@ -431,1386 +234,1389 @@ const char *const dasm_s::token_names[] = "XRI" }; - -// prefix 48 -const dasm_s dasm_s::d48_7810[256] = +// prefix 60 +const upd7810_base_disassembler::dasm_s upd7810_base_disassembler::d60[256] = { - { }, // 00: 0100 1000 0000 0000 - {SLRC, "A" }, // 01: 0100 1000 0000 0001 - {SLRC, "B" }, // 02: 0100 1000 0000 0010 - {SLRC, "C" }, // 03: 0100 1000 0000 0011 - { }, // 04: 0100 1000 0000 0100 - {SLLC, "A" }, // 05: 0100 1000 0000 0101 - {SLLC, "B" }, // 06: 0100 1000 0000 0110 - {SLLC, "C" }, // 07: 0100 1000 0000 0111 - {SK, "NV" }, // 08: 0100 1000 0000 1000 - { }, // 09: 0100 1000 0000 1001 - {SK, "CY" }, // 0a: 0100 1000 0000 1010 - {SK, "HC" }, // 0b: 0100 1000 0000 1011 - {SK, "Z" }, // 0c: 0100 1000 0000 1100 - { }, // 0d: 0100 1000 0000 1101 - { }, // 0e: 0100 1000 0000 1110 - { }, // 0f: 0100 1000 0000 1111 + { }, // 00: 0110 0000 0000 0000 + { }, // 01: 0110 0000 0000 0001 + { }, // 02: 0110 0000 0000 0010 + { }, // 03: 0110 0000 0000 0011 + { }, // 04: 0110 0000 0000 0100 + { }, // 05: 0110 0000 0000 0101 + { }, // 06: 0110 0000 0000 0110 + { }, // 07: 0110 0000 0000 0111 + {ANA, "V,A" }, // 08: 0110 0000 0000 1000 + {ANA, "A,A" }, // 09: 0110 0000 0000 1001 + {ANA, "B,A" }, // 0a: 0110 0000 0000 1010 + {ANA, "C,A" }, // 0b: 0110 0000 0000 1011 + {ANA, "D,A" }, // 0c: 0110 0000 0000 1100 + {ANA, "E,A" }, // 0d: 0110 0000 0000 1101 + {ANA, "H,A" }, // 0e: 0110 0000 0000 1110 + {ANA, "L,A" }, // 0f: 0110 0000 0000 1111 - { }, // 10: 0100 1000 0001 0000 - { }, // 11: 0100 1000 0001 0001 - { }, // 12: 0100 1000 0001 0010 - { }, // 13: 0100 1000 0001 0011 - { }, // 14: 0100 1000 0001 0100 - { }, // 15: 0100 1000 0001 0101 - { }, // 16: 0100 1000 0001 0110 - { }, // 17: 0100 1000 0001 0111 - {SKN, "NV" }, // 18: 0100 1000 0001 1000 - { }, // 19: 0100 1000 0001 1001 - {SKN, "CY" }, // 1a: 0100 1000 0001 1010 - {SKN, "HC" }, // 1b: 0100 1000 0001 1011 - {SKN, "Z" }, // 1c: 0100 1000 0001 1100 - { }, // 1d: 0100 1000 0001 1101 - { }, // 1e: 0100 1000 0001 1110 - { }, // 1f: 0100 1000 0001 1111 + {XRA, "V,A" }, // 10: 0110 0000 0001 0000 + {XRA, "A,A" }, // 11: 0110 0000 0001 0001 + {XRA, "B,A" }, // 12: 0110 0000 0001 0010 + {XRA, "C,A" }, // 13: 0110 0000 0001 0011 + {XRA, "D,A" }, // 14: 0110 0000 0001 0100 + {XRA, "E,A" }, // 15: 0110 0000 0001 0101 + {XRA, "H,A" }, // 16: 0110 0000 0001 0110 + {XRA, "L,A" }, // 17: 0110 0000 0001 0111 + {ORA, "V,A" }, // 18: 0110 0000 0001 1000 + {ORA, "A,A" }, // 19: 0110 0000 0001 1001 + {ORA, "B,A" }, // 1a: 0110 0000 0001 1010 + {ORA, "C,A" }, // 1b: 0110 0000 0001 1011 + {ORA, "D,A" }, // 1c: 0110 0000 0001 1100 + {ORA, "E,A" }, // 1d: 0110 0000 0001 1101 + {ORA, "H,A" }, // 1e: 0110 0000 0001 1110 + {ORA, "L,A" }, // 1f: 0110 0000 0001 1111 - { }, // 20: 0100 1000 0010 0000 - {SLR, "A" }, // 21: 0100 1000 0010 0001 - {SLR, "B" }, // 22: 0100 1000 0010 0010 - {SLR, "C" }, // 23: 0100 1000 0010 0011 - { }, // 24: 0100 1000 0010 0100 - {SLL, "A" }, // 25: 0100 1000 0010 0101 - {SLL, "B" }, // 26: 0100 1000 0010 0110 - {SLL, "C" }, // 27: 0100 1000 0010 0111 - {JEA, nullptr }, // 28: 0100 1000 0010 1000 - {CALB,nullptr }, // 29: 0100 1000 0010 1001 - {CLC, nullptr }, // 2a: 0100 1000 0010 1010 - {STC, nullptr }, // 2b: 0100 1000 0010 1011 - { }, // 2c: 0100 1000 0010 1100 - {MUL, "A" }, // 2d: 0100 1000 0010 1101 - {MUL, "B" }, // 2e: 0100 1000 0010 1110 - {MUL, "C" }, // 2f: 0100 1000 0010 1111 + {ADDNC, "V,A" }, // 20: 0110 0000 0010 0000 + {ADDNC, "A,A" }, // 21: 0110 0000 0010 0001 + {ADDNC, "B,A" }, // 22: 0110 0000 0010 0010 + {ADDNC, "C,A" }, // 23: 0110 0000 0010 0011 + {ADDNC, "D,A" }, // 24: 0110 0000 0010 0100 + {ADDNC, "E,A" }, // 25: 0110 0000 0010 0101 + {ADDNC, "H,A" }, // 26: 0110 0000 0010 0110 + {ADDNC, "L,A" }, // 27: 0110 0000 0010 0111 + {GTA, "V,A" }, // 28: 0110 0000 0010 1000 + {GTA, "A,A" }, // 29: 0110 0000 0010 1001 + {GTA, "B,A" }, // 2a: 0110 0000 0010 1010 + {GTA, "C,A" }, // 2b: 0110 0000 0010 1011 + {GTA, "D,A" }, // 2c: 0110 0000 0010 1100 + {GTA, "E,A" }, // 2d: 0110 0000 0010 1101 + {GTA, "H,A" }, // 2e: 0110 0000 0010 1110 + {GTA, "L,A" }, // 2f: 0110 0000 0010 1111 - { }, // 30: 0100 1000 0011 0000 - {RLR, "A" }, // 31: 0100 1000 0011 0001 - {RLR, "B" }, // 32: 0100 1000 0011 0010 - {RLR, "C" }, // 33: 0100 1000 0011 0011 - { }, // 34: 0100 1000 0011 0100 - {RLL, "A" }, // 35: 0100 1000 0011 0101 - {RLL, "B" }, // 36: 0100 1000 0011 0110 - {RLL, "C" }, // 37: 0100 1000 0011 0111 - {RLD, nullptr }, // 38: 0100 1000 0011 1000 - {RRD, nullptr }, // 39: 0100 1000 0011 1001 - {NEGA, nullptr }, // 3a: 0100 1000 0011 1010 - {HALT, nullptr }, // 3b: 0100 1000 0011 1011 - { }, // 3c: 0100 1000 0011 1100 - {DIV, "A" }, // 3d: 0100 1000 0011 1101 - {DIV, "B" }, // 3e: 0100 1000 0011 1110 - {DIV, "C" }, // 3f: 0100 1000 0011 1111 + {SUBNB, "V,A" }, // 30: 0110 0000 0011 0000 + {SUBNB, "A,A" }, // 31: 0110 0000 0011 0001 + {SUBNB, "B,A" }, // 32: 0110 0000 0011 0010 + {SUBNB, "C,A" }, // 33: 0110 0000 0011 0011 + {SUBNB, "D,A" }, // 34: 0110 0000 0011 0100 + {SUBNB, "E,A" }, // 35: 0110 0000 0011 0101 + {SUBNB, "H,A" }, // 36: 0110 0000 0011 0110 + {SUBNB, "L,A" }, // 37: 0110 0000 0011 0111 + {LTA, "V,A" }, // 38: 0110 0000 0011 1000 + {LTA, "A,A" }, // 39: 0110 0000 0011 1001 + {LTA, "B,A" }, // 3a: 0110 0000 0011 1010 + {LTA, "C,A" }, // 3b: 0110 0000 0011 1011 + {LTA, "D,A" }, // 3c: 0110 0000 0011 1100 + {LTA, "E,A" }, // 3d: 0110 0000 0011 1101 + {LTA, "H,A" }, // 3e: 0110 0000 0011 1110 + {LTA, "L,A" }, // 3f: 0110 0000 0011 1111 - {SKIT, "NMI" }, // 40: 0100 1000 0100 0000 - {SKIT, "FT0" }, // 41: 0100 1000 0100 0001 - {SKIT, "FT1" }, // 42: 0100 1000 0100 0010 - {SKIT, "F1" }, // 43: 0100 1000 0100 0011 - {SKIT, "F2" }, // 44: 0100 1000 0100 0100 - {SKIT, "FE0" }, // 45: 0100 1000 0100 0101 - {SKIT, "FE1" }, // 46: 0100 1000 0100 0110 - {SKIT, "FEIN" }, // 47: 0100 1000 0100 0111 - {SKIT, "FAD" }, // 48: 0100 1000 0100 1000 - {SKIT, "FSR" }, // 49: 0100 1000 0100 1001 - {SKIT, "FST" }, // 4a: 0100 1000 0100 1010 - {SKIT, "ER" }, // 4b: 0100 1000 0100 1011 - {SKIT, "OV" }, // 4c: 0100 1000 0100 1100 - { }, // 4d: 0100 1000 0100 1101 - { }, // 4e: 0100 1000 0100 1110 - { }, // 4f: 0100 1000 0100 1111 + {ADD, "V,A" }, // 40: 0110 0000 0100 0000 + {ADD, "A,A" }, // 41: 0110 0000 0100 0001 + {ADD, "B,A" }, // 42: 0110 0000 0100 0010 + {ADD, "C,A" }, // 43: 0110 0000 0100 0011 + {ADD, "D,A" }, // 44: 0110 0000 0100 0100 + {ADD, "E,A" }, // 45: 0110 0000 0100 0101 + {ADD, "H,A" }, // 46: 0110 0000 0100 0110 + {ADD, "L,A" }, // 47: 0110 0000 0100 0111 + { }, // 48: 0110 0000 0100 1000 + { }, // 49: 0110 0000 0100 1001 + { }, // 4a: 0110 0000 0100 1010 + { }, // 4b: 0110 0000 0100 1011 + { }, // 4c: 0110 0000 0100 1100 + { }, // 4d: 0110 0000 0100 1101 + { }, // 4e: 0110 0000 0100 1110 + { }, // 4f: 0110 0000 0100 1111 - {SKIT, "AN4" }, // 50: 0100 1000 0101 0000 - {SKIT, "AN5" }, // 51: 0100 1000 0101 0001 - {SKIT, "AN6" }, // 52: 0100 1000 0101 0010 - {SKIT, "AN7" }, // 53: 0100 1000 0101 0011 - {SKIT, "SB" }, // 54: 0100 1000 0101 0100 - { }, // 55: 0100 1000 0101 0101 - { }, // 56: 0100 1000 0101 0110 - { }, // 57: 0100 1000 0101 0111 - { }, // 58: 0100 1000 0101 1000 - { }, // 59: 0100 1000 0101 1001 - { }, // 5a: 0100 1000 0101 1010 - { }, // 5b: 0100 1000 0101 1011 - { }, // 5c: 0100 1000 0101 1100 - { }, // 5d: 0100 1000 0101 1101 - { }, // 5e: 0100 1000 0101 1110 - { }, // 5f: 0100 1000 0101 1111 + {ADC, "V,A" }, // 50: 0110 0000 0101 0000 + {ADC, "A,A" }, // 51: 0110 0000 0101 0001 + {ADC, "B,A" }, // 52: 0110 0000 0101 0010 + {ADC, "C,A" }, // 53: 0110 0000 0101 0011 + {ADC, "D,A" }, // 54: 0110 0000 0101 0100 + {ADC, "E,A" }, // 55: 0110 0000 0101 0101 + {ADC, "H,A" }, // 56: 0110 0000 0101 0110 + {ADC, "L,A" }, // 57: 0110 0000 0101 0111 + { }, // 58: 0110 0000 0101 1000 + { }, // 59: 0110 0000 0101 1001 + { }, // 5a: 0110 0000 0101 1010 + { }, // 5b: 0110 0000 0101 1011 + { }, // 5c: 0110 0000 0101 1100 + { }, // 5d: 0110 0000 0101 1101 + { }, // 5e: 0110 0000 0101 1110 + { }, // 5f: 0110 0000 0101 1111 - {SKNIT, "NMI" }, // 60: 0100 1000 0110 0000 - {SKNIT, "FT0" }, // 61: 0100 1000 0110 0001 - {SKNIT, "FT1" }, // 62: 0100 1000 0110 0010 - {SKNIT, "F1" }, // 63: 0100 1000 0110 0011 - {SKNIT, "F2" }, // 64: 0100 1000 0110 0100 - {SKNIT, "FE0" }, // 65: 0100 1000 0110 0101 - {SKNIT, "FE1" }, // 66: 0100 1000 0110 0110 - {SKNIT, "FEIN" }, // 67: 0100 1000 0110 0111 - {SKNIT, "FAD" }, // 68: 0100 1000 0110 1000 - {SKNIT, "FSR" }, // 69: 0100 1000 0110 1001 - {SKNIT, "FST" }, // 6a: 0100 1000 0110 1010 - {SKNIT, "ER" }, // 6b: 0100 1000 0110 1011 - {SKNIT, "OV" }, // 6c: 0100 1000 0110 1100 - { }, // 6d: 0100 1000 0110 1101 - { }, // 6e: 0100 1000 0110 1110 - { }, // 6f: 0100 1000 0110 1111 + {SUB, "V,A" }, // 60: 0110 0000 0110 0000 + {SUB, "A,A" }, // 61: 0110 0000 0110 0001 + {SUB, "B,A" }, // 62: 0110 0000 0110 0010 + {SUB, "C,A" }, // 63: 0110 0000 0110 0011 + {SUB, "D,A" }, // 64: 0110 0000 0110 0100 + {SUB, "E,A" }, // 65: 0110 0000 0110 0101 + {SUB, "H,A" }, // 66: 0110 0000 0110 0110 + {SUB, "L,A" }, // 67: 0110 0000 0110 0111 + {NEA, "V,A" }, // 68: 0110 0000 0110 1000 + {NEA, "A,A" }, // 69: 0110 0000 0110 1001 + {NEA, "B,A" }, // 6a: 0110 0000 0110 1010 + {NEA, "C,A" }, // 6b: 0110 0000 0110 1011 + {NEA, "D,A" }, // 6c: 0110 0000 0110 1100 + {NEA, "E,A" }, // 6d: 0110 0000 0110 1101 + {NEA, "H,A" }, // 6e: 0110 0000 0110 1110 + {NEA, "L,A" }, // 6f: 0110 0000 0110 1111 - {SKNIT, "AN4" }, // 70: 0100 1000 0111 0000 - {SKNIT, "AN5" }, // 71: 0100 1000 0111 0001 - {SKNIT, "AN6" }, // 72: 0100 1000 0111 0010 - {SKNIT, "AN7" }, // 73: 0100 1000 0111 0011 - {SKNIT, "SB" }, // 74: 0100 1000 0111 0100 - { }, // 75: 0100 1000 0111 0101 - { }, // 76: 0100 1000 0111 0110 - { }, // 77: 0100 1000 0111 0111 - { }, // 78: 0100 1000 0111 1000 - { }, // 79: 0100 1000 0111 1001 - { }, // 7a: 0100 1000 0111 1010 - { }, // 7b: 0100 1000 0111 1011 - { }, // 7c: 0100 1000 0111 1100 - { }, // 7d: 0100 1000 0111 1101 - { }, // 7e: 0100 1000 0111 1110 - { }, // 7f: 0100 1000 0111 1111 + {SBB, "V,A" }, // 70: 0110 0000 0111 0000 + {SBB, "A,A" }, // 71: 0110 0000 0111 0001 + {SBB, "B,A" }, // 72: 0110 0000 0111 0010 + {SBB, "C,A" }, // 73: 0110 0000 0111 0011 + {SBB, "D,A" }, // 74: 0110 0000 0111 0100 + {SBB, "E,A" }, // 75: 0110 0000 0111 0101 + {SBB, "H,A" }, // 76: 0110 0000 0111 0110 + {SBB, "L,A" }, // 77: 0110 0000 0111 0111 + {EQA, "V,A" }, // 78: 0110 0000 0111 1000 + {EQA, "A,A" }, // 79: 0110 0000 0111 1001 + {EQA, "B,A" }, // 7a: 0110 0000 0111 1010 + {EQA, "C,A" }, // 7b: 0110 0000 0111 1011 + {EQA, "D,A" }, // 7c: 0110 0000 0111 1100 + {EQA, "E,A" }, // 7d: 0110 0000 0111 1101 + {EQA, "H,A" }, // 7e: 0110 0000 0111 1110 + {EQA, "L,A" }, // 7f: 0110 0000 0111 1111 - { }, // 80: 0100 1000 1000 0000 - { }, // 81: 0100 1000 1000 0001 - {LDEAX, "(DE)" }, // 82: 0100 1000 1000 0010 - {LDEAX, "(HL)" }, // 83: 0100 1000 1000 0011 - {LDEAX, "(DE++)" }, // 84: 0100 1000 1000 0100 - {LDEAX, "(HL++)" }, // 85: 0100 1000 1000 0101 - { }, // 86: 0100 1000 1000 0110 - { }, // 87: 0100 1000 1000 0111 - { }, // 88: 0100 1000 1000 1000 - { }, // 89: 0100 1000 1000 1001 - { }, // 8a: 0100 1000 1000 1010 - {LDEAX, "(DE+%b)" }, // 8b: 0100 1000 1000 1011 xxxx xxxx - {LDEAX, "(HL+A)" }, // 8c: 0100 1000 1000 1100 - {LDEAX, "(HL+B)" }, // 8d: 0100 1000 1000 1101 - {LDEAX, "(HL+EA)" }, // 8e: 0100 1000 1000 1110 - {LDEAX, "(HL+%b)" }, // 8f: 0100 1000 1000 1111 xxxx xxxx + { }, // 80: 0110 0000 1000 0000 + { }, // 81: 0110 0000 1000 0001 + { }, // 82: 0110 0000 1000 0010 + { }, // 83: 0110 0000 1000 0011 + { }, // 84: 0110 0000 1000 0100 + { }, // 85: 0110 0000 1000 0101 + { }, // 86: 0110 0000 1000 0110 + { }, // 87: 0110 0000 1000 0111 + {ANA, "A,V" }, // 88: 0110 0000 1000 1000 + {ANA, "A,A" }, // 89: 0110 0000 1000 1001 + {ANA, "A,B" }, // 8a: 0110 0000 1000 1010 + {ANA, "A,C" }, // 8b: 0110 0000 1000 1011 + {ANA, "A,D" }, // 8c: 0110 0000 1000 1100 + {ANA, "A,E" }, // 8d: 0110 0000 1000 1101 + {ANA, "A,H" }, // 8e: 0110 0000 1000 1110 + {ANA, "A,L" }, // 8f: 0110 0000 1000 1111 - { }, // 90: 0100 1000 1000 0000 - { }, // 91: 0100 1000 1000 0001 - {STEAX, "(DE)" }, // 92: 0100 1000 1000 0010 - {STEAX, "(HL)" }, // 93: 0100 1000 1000 0011 - {STEAX, "(DE++)" }, // 94: 0100 1000 1000 0100 - {STEAX, "(HL++)" }, // 95: 0100 1000 1000 0101 - { }, // 96: 0100 1000 1000 0110 - { }, // 97: 0100 1000 1000 0111 - { }, // 98: 0100 1000 1000 1000 - { }, // 99: 0100 1000 1000 1001 - { }, // 9a: 0100 1000 1000 1010 - {STEAX, "(DE+%b)" }, // 9b: 0100 1000 1000 1011 xxxx xxxx - {STEAX, "(HL+A)" }, // 9c: 0100 1000 1000 1100 - {STEAX, "(HL+B)" }, // 9d: 0100 1000 1000 1101 - {STEAX, "(HL+EA)" }, // 9e: 0100 1000 1000 1110 - {STEAX, "(HL+%b)" }, // 9f: 0100 1000 1000 1111 xxxx xxxx + {XRA, "A,V" }, // 90: 0110 0000 1001 0000 + {XRA, "A,A" }, // 91: 0110 0000 1001 0001 + {XRA, "A,B" }, // 92: 0110 0000 1001 0010 + {XRA, "A,C" }, // 93: 0110 0000 1001 0011 + {XRA, "A,D" }, // 94: 0110 0000 1001 0100 + {XRA, "A,E" }, // 95: 0110 0000 1001 0101 + {XRA, "A,H" }, // 96: 0110 0000 1001 0110 + {XRA, "A,L" }, // 97: 0110 0000 1001 0111 + {ORA, "A,V" }, // 98: 0110 0000 1001 1000 + {ORA, "A,A" }, // 99: 0110 0000 1001 1001 + {ORA, "A,B" }, // 9a: 0110 0000 1001 1010 + {ORA, "A,C" }, // 9b: 0110 0000 1001 1011 + {ORA, "A,D" }, // 9c: 0110 0000 1001 1100 + {ORA, "A,E" }, // 9d: 0110 0000 1001 1101 + {ORA, "A,H" }, // 9e: 0110 0000 1001 1110 + {ORA, "A,L" }, // 9f: 0110 0000 1001 1111 - {DSLR, "EA" }, // a0: 0100 1000 1010 0000 - { }, // a1: 0100 1000 1010 0001 - { }, // a2: 0100 1000 1010 0010 - { }, // a3: 0100 1000 1010 0011 - {DSLL, "EA" }, // a4: 0100 1000 1010 0100 - { }, // a5: 0100 1000 1010 0101 - { }, // a6: 0100 1000 1010 0110 - { }, // a7: 0100 1000 1010 0111 - {TABLE, nullptr }, // a8: 0100 1000 1010 1000 - { }, // a9: 0100 1000 1010 1001 - { }, // aa: 0100 1000 1010 1010 - { }, // ab: 0100 1000 1010 1011 - { }, // ac: 0100 1000 1010 1100 - { }, // ad: 0100 1000 1010 1101 - { }, // ae: 0100 1000 1010 1110 - { }, // af: 0100 1000 1010 1111 + {ADDNC, "A,V" }, // a0: 0110 0000 1010 0000 + {ADDNC, "A,A" }, // a1: 0110 0000 1010 0001 + {ADDNC, "A,B" }, // a2: 0110 0000 1010 0010 + {ADDNC, "A,C" }, // a3: 0110 0000 1010 0011 + {ADDNC, "A,D" }, // a4: 0110 0000 1010 0100 + {ADDNC, "A,E" }, // a5: 0110 0000 1010 0101 + {ADDNC, "A,H" }, // a6: 0110 0000 1010 0110 + {ADDNC, "A,L" }, // a7: 0110 0000 1010 0111 + {GTA, "A,V" }, // a8: 0110 0000 1010 1000 + {GTA, "A,A" }, // a9: 0110 0000 1010 1001 + {GTA, "A,B" }, // aa: 0110 0000 1010 1010 + {GTA, "A,C" }, // ab: 0110 0000 1010 1011 + {GTA, "A,D" }, // ac: 0110 0000 1010 1100 + {GTA, "A,E" }, // ad: 0110 0000 1010 1101 + {GTA, "A,H" }, // ae: 0110 0000 1010 1110 + {GTA, "A,L" }, // af: 0110 0000 1010 1111 - {DRLR, "EA" }, // b0: 0100 1000 1011 0000 - { }, // b1: 0100 1000 1011 0001 - { }, // b2: 0100 1000 1011 0010 - { }, // b3: 0100 1000 1011 0011 - {DRLL, "EA" }, // b4: 0100 1000 1011 0100 - { }, // b5: 0100 1000 1011 0101 - { }, // b6: 0100 1000 1011 0110 - { }, // b7: 0100 1000 1011 0111 - { }, // b8: 0100 1000 1011 1000 - { }, // b9: 0100 1000 1011 1001 - { }, // ba: 0100 1000 1011 1010 - {STOP, nullptr }, // bb: 0100 1000 1011 1011 7810 - { }, // bc: 0100 1000 1011 1100 - { }, // bd: 0100 1000 1011 1101 - { }, // be: 0100 1000 1011 1110 - { }, // bf: 0100 1000 1011 1111 + {SUBNB, "A,V" }, // b0: 0110 0000 1011 0000 + {SUBNB, "A,A" }, // b1: 0110 0000 1011 0001 + {SUBNB, "A,B" }, // b2: 0110 0000 1011 0010 + {SUBNB, "A,C" }, // b3: 0110 0000 1011 0011 + {SUBNB, "A,D" }, // b4: 0110 0000 1011 0100 + {SUBNB, "A,E" }, // b5: 0110 0000 1011 0101 + {SUBNB, "A,H" }, // b6: 0110 0000 1011 0110 + {SUBNB, "A,L" }, // b7: 0110 0000 1011 0111 + {LTA, "A,V" }, // b8: 0110 0000 1011 1000 + {LTA, "A,A" }, // b9: 0110 0000 1011 1001 + {LTA, "A,B" }, // ba: 0110 0000 1011 1010 + {LTA, "A,C" }, // bb: 0110 0000 1011 1011 + {LTA, "A,D" }, // bc: 0110 0000 1011 1100 + {LTA, "A,E" }, // bd: 0110 0000 1011 1101 + {LTA, "A,H" }, // be: 0110 0000 1011 1110 + {LTA, "A,L" }, // bf: 0110 0000 1011 1111 - {DMOV, "EA,ECNT" }, // c0: 0100 1000 1100 0000 - {DMOV, "EA,ECPT" }, // c1: 0100 1000 1100 0001 7810 - { }, // c2: 0100 1000 1100 0010 - { }, // c3: 0100 1000 1100 0011 - { }, // c4: 0100 1000 1100 0100 - { }, // c5: 0100 1000 1100 0101 - { }, // c6: 0100 1000 1100 0110 - { }, // c7: 0100 1000 1100 0111 - { }, // c8: 0100 1000 1100 1000 - { }, // c9: 0100 1000 1100 1001 - { }, // ca: 0100 1000 1100 1010 - { }, // cb: 0100 1000 1100 1011 - { }, // cc: 0100 1000 1100 1100 - { }, // cd: 0100 1000 1100 1101 - { }, // ce: 0100 1000 1100 1110 - { }, // cf: 0100 1000 1100 1111 + {ADD, "A,V" }, // c0: 0110 0000 1100 0000 + {ADD, "A,A" }, // c1: 0110 0000 1100 0001 + {ADD, "A,B" }, // c2: 0110 0000 1100 0010 + {ADD, "A,C" }, // c3: 0110 0000 1100 0011 + {ADD, "A,D" }, // c4: 0110 0000 1100 0100 + {ADD, "A,E" }, // c5: 0110 0000 1100 0101 + {ADD, "A,H" }, // c6: 0110 0000 1100 0110 + {ADD, "A,L" }, // c7: 0110 0000 1100 0111 + {ONA, "A,V" }, // c8: 0110 0000 1100 1000 + {ONA, "A,A" }, // c9: 0110 0000 1100 1001 + {ONA, "A,B" }, // ca: 0110 0000 1100 1010 + {ONA, "A,C" }, // cb: 0110 0000 1100 1011 + {ONA, "A,D" }, // cc: 0110 0000 1100 1100 + {ONA, "A,E" }, // cd: 0110 0000 1100 1101 + {ONA, "A,H" }, // ce: 0110 0000 1100 1110 + {ONA, "A,L" }, // cf: 0110 0000 1100 1111 - { }, // d0: 0100 1000 1101 0000 - { }, // d1: 0100 1000 1101 0001 - {DMOV, "ETM0,EA" }, // d2: 0100 1000 1101 0010 - {DMOV, "ETM1,EA" }, // d3: 0100 1000 1101 0011 - { }, // d4: 0100 1000 1101 0100 - { }, // d5: 0100 1000 1101 0101 - { }, // d6: 0100 1000 1101 0110 - { }, // d7: 0100 1000 1101 0111 - { }, // d8: 0100 1000 1101 1000 - { }, // d9: 0100 1000 1101 1001 - { }, // da: 0100 1000 1101 1010 - { }, // db: 0100 1000 1101 1011 - { }, // dc: 0100 1000 1101 1100 - { }, // dd: 0100 1000 1101 1101 - { }, // de: 0100 1000 1101 1110 - { }, // df: 0100 1000 1101 1111 + {ADC, "A,V" }, // d0: 0110 0000 1101 0000 + {ADC, "A,A" }, // d1: 0110 0000 1101 0001 + {ADC, "A,B" }, // d2: 0110 0000 1101 0010 + {ADC, "A,C" }, // d3: 0110 0000 1101 0011 + {ADC, "A,D" }, // d4: 0110 0000 1101 0100 + {ADC, "A,E" }, // d5: 0110 0000 1101 0101 + {ADC, "A,H" }, // d6: 0110 0000 1101 0110 + {ADC, "A,L" }, // d7: 0110 0000 1101 0111 + {OFFA, "A,V" }, // d8: 0110 0000 1101 1000 + {OFFA, "A,A" }, // d9: 0110 0000 1101 1001 + {OFFA, "A,B" }, // da: 0110 0000 1101 1010 + {OFFA, "A,C" }, // db: 0110 0000 1101 1011 + {OFFA, "A,D" }, // dc: 0110 0000 1101 1100 + {OFFA, "A,E" }, // dd: 0110 0000 1101 1101 + {OFFA, "A,H" }, // de: 0110 0000 1101 1110 + {OFFA, "A,L" }, // df: 0110 0000 1101 1111 - { }, // e0: 0100 1000 1110 0000 - { }, // e1: 0100 1000 1110 0001 - { }, // e2: 0100 1000 1110 0010 - { }, // e3: 0100 1000 1110 0011 - { }, // e4: 0100 1000 1110 0100 - { }, // e5: 0100 1000 1110 0101 - { }, // e6: 0100 1000 1110 0110 - { }, // e7: 0100 1000 1110 0111 - { }, // e8: 0100 1000 1110 1000 - { }, // e9: 0100 1000 1110 1001 - { }, // ea: 0100 1000 1110 1010 - { }, // eb: 0100 1000 1110 1011 - { }, // ec: 0100 1000 1110 1100 - { }, // ed: 0100 1000 1110 1101 - { }, // ee: 0100 1000 1110 1110 - { }, // ef: 0100 1000 1110 1111 + {SUB, "A,V" }, // e0: 0110 0000 1110 0000 + {SUB, "A,A" }, // e1: 0110 0000 1110 0001 + {SUB, "A,B" }, // e2: 0110 0000 1110 0010 + {SUB, "A,C" }, // e3: 0110 0000 1110 0011 + {SUB, "A,D" }, // e4: 0110 0000 1110 0100 + {SUB, "A,E" }, // e5: 0110 0000 1110 0101 + {SUB, "A,H" }, // e6: 0110 0000 1110 0110 + {SUB, "A,L" }, // e7: 0110 0000 1110 0111 + {NEA, "A,V" }, // e8: 0110 0000 1110 1000 + {NEA, "A,A" }, // e9: 0110 0000 1110 1001 + {NEA, "A,B" }, // ea: 0110 0000 1110 1010 + {NEA, "A,C" }, // eb: 0110 0000 1110 1011 + {NEA, "A,D" }, // ec: 0110 0000 1110 1100 + {NEA, "A,E" }, // ed: 0110 0000 1110 1101 + {NEA, "A,H" }, // ee: 0110 0000 1110 1110 + {NEA, "A,L" }, // ef: 0110 0000 1110 1111 - { }, // f0: 0100 1000 1111 0000 - { }, // f1: 0100 1000 1111 0001 - { }, // f2: 0100 1000 1111 0010 - { }, // f3: 0100 1000 1111 0011 - { }, // f4: 0100 1000 1111 0100 - { }, // f5: 0100 1000 1111 0101 - { }, // f6: 0100 1000 1111 0110 - { }, // f7: 0100 1000 1111 0111 - { }, // f8: 0100 1000 1111 1000 - { }, // f9: 0100 1000 1111 1001 - { }, // fa: 0100 1000 1111 1010 - { }, // fb: 0100 1000 1111 1011 - { }, // fc: 0100 1000 1111 1100 - { }, // fd: 0100 1000 1111 1101 - { }, // fe: 0100 1000 1111 1110 - { } // ff: 0100 1000 1111 1111 + {SBB, "A,V" }, // f0: 0110 0000 1111 0000 + {SBB, "A,A" }, // f1: 0110 0000 1111 0001 + {SBB, "A,B" }, // f2: 0110 0000 1111 0010 + {SBB, "A,C" }, // f3: 0110 0000 1111 0011 + {SBB, "A,D" }, // f4: 0110 0000 1111 0100 + {SBB, "A,E" }, // f5: 0110 0000 1111 0101 + {SBB, "A,H" }, // f6: 0110 0000 1111 0110 + {SBB, "A,L" }, // f7: 0110 0000 1111 0111 + {EQA, "A,V" }, // f8: 0110 0000 1111 1000 + {EQA, "A,A" }, // f9: 0110 0000 1111 1001 + {EQA, "A,B" }, // fa: 0110 0000 1111 1010 + {EQA, "A,C" }, // fb: 0110 0000 1111 1011 + {EQA, "A,D" }, // fc: 0110 0000 1111 1100 + {EQA, "A,E" }, // fd: 0110 0000 1111 1101 + {EQA, "A,H" }, // fe: 0110 0000 1111 1110 + {EQA, "A,L" } // ff: 0110 0000 1111 1111 }; -const dasm_s dasm_s::d48_7807[256] = +// prefix 70 +const upd7810_base_disassembler::dasm_s upd7810_base_disassembler::d70[256] = { - { }, // 00: 0100 1000 0000 0000 - {SLRC, "A" }, // 01: 0100 1000 0000 0001 - {SLRC, "B" }, // 02: 0100 1000 0000 0010 - {SLRC, "C" }, // 03: 0100 1000 0000 0011 - { }, // 04: 0100 1000 0000 0100 - {SLLC, "A" }, // 05: 0100 1000 0000 0101 - {SLLC, "B" }, // 06: 0100 1000 0000 0110 - {SLLC, "C" }, // 07: 0100 1000 0000 0111 - {SK, "NV" }, // 08: 0100 1000 0000 1000 - { }, // 09: 0100 1000 0000 1001 - {SK, "CY" }, // 0a: 0100 1000 0000 1010 - {SK, "HC" }, // 0b: 0100 1000 0000 1011 - {SK, "Z" }, // 0c: 0100 1000 0000 1100 - { }, // 0d: 0100 1000 0000 1101 - { }, // 0e: 0100 1000 0000 1110 - { }, // 0f: 0100 1000 0000 1111 + { }, // 00: 0111 0000 0000 0000 + { }, // 01: 0111 0000 0000 0001 + { }, // 02: 0111 0000 0000 0010 + { }, // 03: 0111 0000 0000 0011 + { }, // 04: 0111 0000 0000 0100 + { }, // 05: 0111 0000 0000 0101 + { }, // 06: 0111 0000 0000 0110 + { }, // 07: 0111 0000 0000 0111 + { }, // 08: 0111 0000 0000 1000 + { }, // 09: 0111 0000 0000 1001 + { }, // 0a: 0111 0000 0000 1010 + { }, // 0b: 0111 0000 0000 1011 + { }, // 0c: 0111 0000 0000 1100 + { }, // 0d: 0111 0000 0000 1101 + {SSPD, "%w" }, // 0e: 0111 0000 0000 1110 llll llll hhhh hhhh + {LSPD, "%w" }, // 0f: 0111 0000 0000 1111 llll llll hhhh hhhh - { }, // 10: 0100 1000 0001 0000 - { }, // 11: 0100 1000 0001 0001 - { }, // 12: 0100 1000 0001 0010 - { }, // 13: 0100 1000 0001 0011 - { }, // 14: 0100 1000 0001 0100 - { }, // 15: 0100 1000 0001 0101 - { }, // 16: 0100 1000 0001 0110 - { }, // 17: 0100 1000 0001 0111 - {SKN, "NV" }, // 18: 0100 1000 0001 1000 - { }, // 19: 0100 1000 0001 1001 - {SKN, "CY" }, // 1a: 0100 1000 0001 1010 - {SKN, "HC" }, // 1b: 0100 1000 0001 1011 - {SKN, "Z" }, // 1c: 0100 1000 0001 1100 - { }, // 1d: 0100 1000 0001 1101 - { }, // 1e: 0100 1000 0001 1110 - { }, // 1f: 0100 1000 0001 1111 + { }, // 10: 0111 0000 0001 0000 + { }, // 11: 0111 0000 0001 0001 + { }, // 12: 0111 0000 0001 0010 + { }, // 13: 0111 0000 0001 0011 + { }, // 14: 0111 0000 0001 0100 + { }, // 15: 0111 0000 0001 0101 + { }, // 16: 0111 0000 0001 0110 + { }, // 17: 0111 0000 0001 0111 + { }, // 18: 0111 0000 0001 1000 + { }, // 19: 0111 0000 0001 1001 + { }, // 1a: 0111 0000 0001 1010 + { }, // 1b: 0111 0000 0001 1011 + { }, // 1c: 0111 0000 0001 1100 + { }, // 1d: 0111 0000 0001 1101 + {SBCD, "%w" }, // 1e: 0111 0000 0001 1110 llll llll hhhh hhhh + {LBCD, "%w" }, // 1f: 0111 0000 0001 1111 llll llll hhhh hhhh - { }, // 20: 0100 1000 0010 0000 - {SLR, "A" }, // 21: 0100 1000 0010 0001 - {SLR, "B" }, // 22: 0100 1000 0010 0010 - {SLR, "C" }, // 23: 0100 1000 0010 0011 - { }, // 24: 0100 1000 0010 0100 - {SLL, "A" }, // 25: 0100 1000 0010 0101 - {SLL, "B" }, // 26: 0100 1000 0010 0110 - {SLL, "C" }, // 27: 0100 1000 0010 0111 - {JEA, nullptr }, // 28: 0100 1000 0010 1000 - {CALB, nullptr }, // 29: 0100 1000 0010 1001 - {CLC, nullptr }, // 2a: 0100 1000 0010 1010 - {STC, nullptr }, // 2b: 0100 1000 0010 1011 - { }, // 2c: 0100 1000 0010 1100 - {MUL, "A" }, // 2d: 0100 1000 0010 1101 - {MUL, "B" }, // 2e: 0100 1000 0010 1110 - {MUL, "C" }, // 2f: 0100 1000 0010 1111 + { }, // 20: 0111 0000 0010 0000 + { }, // 21: 0111 0000 0010 0001 + { }, // 22: 0111 0000 0010 0010 + { }, // 23: 0111 0000 0010 0011 + { }, // 24: 0111 0000 0010 0100 + { }, // 25: 0111 0000 0010 0101 + { }, // 26: 0111 0000 0010 0110 + { }, // 27: 0111 0000 0010 0111 + { }, // 28: 0111 0000 0010 1000 + { }, // 29: 0111 0000 0010 1001 + { }, // 2a: 0111 0000 0010 1010 + { }, // 2b: 0111 0000 0010 1011 + { }, // 2c: 0111 0000 0010 1100 + { }, // 2d: 0111 0000 0010 1101 + {SDED, "%w" }, // 2e: 0111 0000 0010 1110 llll llll hhhh hhhh + {LDED, "%w" }, // 2f: 0111 0000 0010 1111 llll llll hhhh hhhh - { }, // 30: 0100 1000 0011 0000 - {RLR, "A" }, // 31: 0100 1000 0011 0001 - {RLR, "B" }, // 32: 0100 1000 0011 0010 - {RLR, "C" }, // 33: 0100 1000 0011 0011 - { }, // 34: 0100 1000 0011 0100 - {RLL, "A" }, // 35: 0100 1000 0011 0101 - {RLL, "B" }, // 36: 0100 1000 0011 0110 - {RLL, "C" }, // 37: 0100 1000 0011 0111 - {RLD, nullptr }, // 38: 0100 1000 0011 1000 - {RRD, nullptr }, // 39: 0100 1000 0011 1001 - {NEGA, nullptr }, // 3a: 0100 1000 0011 1010 - {HALT, nullptr }, // 3b: 0100 1000 0011 1011 - { }, // 3c: 0100 1000 0011 1100 - {DIV, "A" }, // 3d: 0100 1000 0011 1101 - {DIV, "B" }, // 3e: 0100 1000 0011 1110 - {DIV, "C" }, // 3f: 0100 1000 0011 1111 + { }, // 30: 0111 0000 0011 0000 + { }, // 31: 0111 0000 0011 0001 + { }, // 32: 0111 0000 0011 0010 + { }, // 33: 0111 0000 0011 0011 + { }, // 34: 0111 0000 0011 0100 + { }, // 35: 0111 0000 0011 0101 + { }, // 36: 0111 0000 0011 0110 + { }, // 37: 0111 0000 0011 0111 + { }, // 38: 0111 0000 0011 1000 + { }, // 39: 0111 0000 0011 1001 + { }, // 3a: 0111 0000 0011 1010 + { }, // 3b: 0111 0000 0011 1011 + { }, // 3c: 0111 0000 0011 1100 + { }, // 3d: 0111 0000 0011 1101 + {SHLD, "%w" }, // 3e: 0111 0000 0011 1110 llll llll hhhh hhhh + {LHLD, "%w" }, // 3f: 0111 0000 0011 1111 llll llll hhhh hhhh - {SKIT, "NMI" }, // 40: 0100 1000 0100 0000 - {SKIT, "FT0" }, // 41: 0100 1000 0100 0001 - {SKIT, "FT1" }, // 42: 0100 1000 0100 0010 - {SKIT, "F1" }, // 43: 0100 1000 0100 0011 - {SKIT, "F2" }, // 44: 0100 1000 0100 0100 - {SKIT, "FE0" }, // 45: 0100 1000 0100 0101 - {SKIT, "FE1" }, // 46: 0100 1000 0100 0110 - {SKIT, "FEIN" }, // 47: 0100 1000 0100 0111 - {SKIT, "FAD" }, // 48: 0100 1000 0100 1000 - {SKIT, "FSR" }, // 49: 0100 1000 0100 1001 - {SKIT, "FST" }, // 4a: 0100 1000 0100 1010 - {SKIT, "ER" }, // 4b: 0100 1000 0100 1011 - {SKIT, "OV" }, // 4c: 0100 1000 0100 1100 - { }, // 4d: 0100 1000 0100 1101 - { }, // 4e: 0100 1000 0100 1110 - { }, // 4f: 0100 1000 0100 1111 + {EADD, "EA,V" }, // 40: 0111 0000 0100 0000 + {EADD, "EA,A" }, // 41: 0111 0000 0100 0001 + {EADD, "EA,B" }, // 42: 0111 0000 0100 0010 + {EADD, "EA,C" }, // 43: 0111 0000 0100 0011 + { }, // 44: 0111 0000 0100 0100 + { }, // 45: 0111 0000 0100 0101 + { }, // 46: 0111 0000 0100 0110 + { }, // 47: 0111 0000 0100 0111 + { }, // 48: 0111 0000 0100 1000 + { }, // 49: 0111 0000 0100 1001 + { }, // 4a: 0111 0000 0100 1010 + { }, // 4b: 0111 0000 0100 1011 + { }, // 4c: 0111 0000 0100 1100 + { }, // 4d: 0111 0000 0100 1101 + { }, // 4e: 0111 0000 0100 1110 + { }, // 4f: 0111 0000 0100 1111 - {SKIT, "AN4" }, // 50: 0100 1000 0101 0000 - {SKIT, "AN5" }, // 51: 0100 1000 0101 0001 - {SKIT, "AN6" }, // 52: 0100 1000 0101 0010 - {SKIT, "AN7" }, // 53: 0100 1000 0101 0011 - {SKIT, "SB" }, // 54: 0100 1000 0101 0100 - { }, // 55: 0100 1000 0101 0101 - { }, // 56: 0100 1000 0101 0110 - { }, // 57: 0100 1000 0101 0111 - { }, // 58: 0100 1000 0101 1000 - { }, // 59: 0100 1000 0101 1001 - { }, // 5a: 0100 1000 0101 1010 - { }, // 5b: 0100 1000 0101 1011 - { }, // 5c: 0100 1000 0101 1100 - { }, // 5d: 0100 1000 0101 1101 - { }, // 5e: 0100 1000 0101 1110 - { }, // 5f: 0100 1000 0101 1111 + { }, // 50: 0111 0000 0101 0000 + { }, // 51: 0111 0000 0101 0001 + { }, // 52: 0111 0000 0101 0010 + { }, // 53: 0111 0000 0101 0011 + { }, // 54: 0111 0000 0101 0100 + { }, // 55: 0111 0000 0101 0101 + { }, // 56: 0111 0000 0101 0110 + { }, // 57: 0111 0000 0101 0111 + { }, // 58: 0111 0000 0101 1000 + { }, // 59: 0111 0000 0101 1001 + { }, // 5a: 0111 0000 0101 1010 + { }, // 5b: 0111 0000 0101 1011 + { }, // 5c: 0111 0000 0101 1100 + { }, // 5d: 0111 0000 0101 1101 + { }, // 5e: 0111 0000 0101 1110 + { }, // 5f: 0111 0000 0101 1111 - {SKNIT, "NMI" }, // 60: 0100 1000 0110 0000 - {SKNIT, "FT0" }, // 61: 0100 1000 0110 0001 - {SKNIT, "FT1" }, // 62: 0100 1000 0110 0010 - {SKNIT, "F1" }, // 63: 0100 1000 0110 0011 - {SKNIT, "F2" }, // 64: 0100 1000 0110 0100 - {SKNIT, "FE0" }, // 65: 0100 1000 0110 0101 - {SKNIT, "FE1" }, // 66: 0100 1000 0110 0110 - {SKNIT, "FEIN" }, // 67: 0100 1000 0110 0111 - {SKNIT, "FAD" }, // 68: 0100 1000 0110 1000 - {SKNIT, "FSR" }, // 69: 0100 1000 0110 1001 - {SKNIT, "FST" }, // 6a: 0100 1000 0110 1010 - {SKNIT, "ER" }, // 6b: 0100 1000 0110 1011 - {SKNIT, "OV" }, // 6c: 0100 1000 0110 1100 - { }, // 6d: 0100 1000 0110 1101 - { }, // 6e: 0100 1000 0110 1110 - { }, // 6f: 0100 1000 0110 1111 + {ESUB, "EA,V" }, // 60: 0111 0000 0110 0000 + {ESUB, "EA,A" }, // 61: 0111 0000 0110 0001 + {ESUB, "EA,B" }, // 62: 0111 0000 0110 0010 + {ESUB, "EA,C" }, // 63: 0111 0000 0110 0011 + { }, // 64: 0111 0000 0110 0100 + { }, // 65: 0111 0000 0110 0101 + { }, // 66: 0111 0000 0110 0110 + { }, // 67: 0111 0000 0110 0111 + {MOV, "V,(%w)" }, // 68: 0111 0000 0110 1000 llll llll hhhh hhhh + {MOV, "A,(%w)" }, // 69: 0111 0000 0110 1001 llll llll hhhh hhhh + {MOV, "B,(%w)" }, // 6a: 0111 0000 0110 1010 llll llll hhhh hhhh + {MOV, "C,(%w)" }, // 6b: 0111 0000 0110 1011 llll llll hhhh hhhh + {MOV, "D,(%w)" }, // 6c: 0111 0000 0110 1100 llll llll hhhh hhhh + {MOV, "E,(%w)" }, // 6d: 0111 0000 0110 1101 llll llll hhhh hhhh + {MOV, "H,(%w)" }, // 6e: 0111 0000 0110 1110 llll llll hhhh hhhh + {MOV, "L,(%w)" }, // 6f: 0111 0000 0110 1111 llll llll hhhh hhhh - {SKNIT, "AN4" }, // 70: 0100 1000 0111 0000 - {SKNIT, "AN5" }, // 71: 0100 1000 0111 0001 - {SKNIT, "AN6" }, // 72: 0100 1000 0111 0010 - {SKNIT, "AN7" }, // 73: 0100 1000 0111 0011 - {SKNIT, "SB" }, // 74: 0100 1000 0111 0100 - { }, // 75: 0100 1000 0111 0101 - { }, // 76: 0100 1000 0111 0110 - { }, // 77: 0100 1000 0111 0111 - { }, // 78: 0100 1000 0111 1000 - { }, // 79: 0100 1000 0111 1001 - { }, // 7a: 0100 1000 0111 1010 - { }, // 7b: 0100 1000 0111 1011 - { }, // 7c: 0100 1000 0111 1100 - { }, // 7d: 0100 1000 0111 1101 - { }, // 7e: 0100 1000 0111 1110 - { }, // 7f: 0100 1000 0111 1111 + { }, // 70: 0111 0000 0111 0000 + { }, // 71: 0111 0000 0111 0001 + { }, // 72: 0111 0000 0111 0010 + { }, // 73: 0111 0000 0111 0011 + { }, // 74: 0111 0000 0111 0100 + { }, // 75: 0111 0000 0111 0101 + { }, // 76: 0111 0000 0111 0110 + { }, // 77: 0111 0000 0111 0111 + {MOV, "(%w),V" }, // 78: 0111 0000 0111 1000 llll llll hhhh hhhh + {MOV, "(%w),A" }, // 79: 0111 0000 0111 1001 llll llll hhhh hhhh + {MOV, "(%w),B" }, // 7a: 0111 0000 0111 1010 llll llll hhhh hhhh + {MOV, "(%w),C" }, // 7b: 0111 0000 0111 1011 llll llll hhhh hhhh + {MOV, "(%w),D" }, // 7c: 0111 0000 0111 1100 llll llll hhhh hhhh + {MOV, "(%w),E" }, // 7d: 0111 0000 0111 1101 llll llll hhhh hhhh + {MOV, "(%w),H" }, // 7e: 0111 0000 0111 1110 llll llll hhhh hhhh + {MOV, "(%w),L" }, // 7f: 0111 0000 0111 1111 llll llll hhhh hhhh - { }, // 80: 0100 1000 1000 0000 - { }, // 81: 0100 1000 1000 0001 - {LDEAX, "(DE)" }, // 82: 0100 1000 1000 0010 - {LDEAX, "(HL)" }, // 83: 0100 1000 1000 0011 - {LDEAX, "(DE++)" }, // 84: 0100 1000 1000 0100 - {LDEAX, "(HL++)" }, // 85: 0100 1000 1000 0101 - { }, // 86: 0100 1000 1000 0110 - { }, // 87: 0100 1000 1000 0111 - { }, // 88: 0100 1000 1000 1000 - { }, // 89: 0100 1000 1000 1001 - { }, // 8a: 0100 1000 1000 1010 - {LDEAX, "(DE+%b)" }, // 8b: 0100 1000 1000 1011 xxxx xxxx - {LDEAX, "(HL+A)" }, // 8c: 0100 1000 1000 1100 - {LDEAX, "(HL+B)" }, // 8d: 0100 1000 1000 1101 - {LDEAX, "(HL+EA)" }, // 8e: 0100 1000 1000 1110 - {LDEAX, "(HL+%b)" }, // 8f: 0100 1000 1000 1111 xxxx xxxx + { }, // 80: 0111 0000 1000 0000 + { }, // 81: 0111 0000 1000 0001 + { }, // 82: 0111 0000 1000 0010 + { }, // 83: 0111 0000 1000 0011 + { }, // 84: 0111 0000 1000 0100 + { }, // 85: 0111 0000 1000 0101 + { }, // 86: 0111 0000 1000 0110 + { }, // 87: 0111 0000 1000 0111 + { }, // 88: 0111 0000 1000 1000 + {ANAX, "(BC)" }, // 89: 0111 0000 1000 1001 + {ANAX, "(DE)" }, // 8a: 0111 0000 1000 1010 + {ANAX, "(HL)" }, // 8b: 0111 0000 1000 1011 + {ANAX, "(DE+)" }, // 8c: 0111 0000 1000 1100 + {ANAX, "(HL+)" }, // 8d: 0111 0000 1000 1101 + {ANAX, "(DE-)" }, // 8e: 0111 0000 1000 1110 + {ANAX, "(HL-)" }, // 8f: 0111 0000 1000 1111 - { }, // 90: 0100 1000 1000 0000 - { }, // 91: 0100 1000 1000 0001 - {STEAX, "(DE)" }, // 92: 0100 1000 1000 0010 - {STEAX, "(HL)" }, // 93: 0100 1000 1000 0011 - {STEAX, "(DE++)" }, // 94: 0100 1000 1000 0100 - {STEAX, "(HL++)" }, // 95: 0100 1000 1000 0101 - { }, // 96: 0100 1000 1000 0110 - { }, // 97: 0100 1000 1000 0111 - { }, // 98: 0100 1000 1000 1000 - { }, // 99: 0100 1000 1000 1001 - { }, // 9a: 0100 1000 1000 1010 - {STEAX, "(DE+%b)" }, // 9b: 0100 1000 1000 1011 xxxx xxxx - {STEAX, "(HL+A)" }, // 9c: 0100 1000 1000 1100 - {STEAX, "(HL+B)" }, // 9d: 0100 1000 1000 1101 - {STEAX, "(HL+EA)" }, // 9e: 0100 1000 1000 1110 - {STEAX, "(HL+%b)" }, // 9f: 0100 1000 1000 1111 xxxx xxxx + { }, // 90: 0111 0000 1001 0000 + {XRAX, "(BC)" }, // 91: 0111 0000 1001 0001 + {XRAX, "(DE)" }, // 92: 0111 0000 1001 0010 + {XRAX, "(HL)" }, // 93: 0111 0000 1001 0011 + {XRAX, "(DE+)" }, // 94: 0111 0000 1001 0100 + {XRAX, "(HL+)" }, // 95: 0111 0000 1001 0101 + {XRAX, "(DE-)" }, // 96: 0111 0000 1001 0110 + {XRAX, "(HL-)" }, // 97: 0111 0000 1001 0111 + { }, // 98: 0111 0000 1001 1000 + {ORAX, "(BC)" }, // 99: 0111 0000 1001 1001 + {ORAX, "(DE)" }, // 9a: 0111 0000 1001 1010 + {ORAX, "(HL)" }, // 9b: 0111 0000 1001 1011 + {ORAX, "(DE+)" }, // 9c: 0111 0000 1001 1100 + {ORAX, "(HL+)" }, // 9d: 0111 0000 1001 1101 + {ORAX, "(DE-)" }, // 9e: 0111 0000 1001 1110 + {ORAX, "(HL-)" }, // 9f: 0111 0000 1001 1111 - {DSLR, "EA" }, // a0: 0100 1000 1010 0000 - { }, // a1: 0100 1000 1010 0001 - { }, // a2: 0100 1000 1010 0010 - { }, // a3: 0100 1000 1010 0011 - {DSLL, "EA" }, // a4: 0100 1000 1010 0100 - { }, // a5: 0100 1000 1010 0101 - { }, // a6: 0100 1000 1010 0110 - { }, // a7: 0100 1000 1010 0111 - {TABLE, nullptr }, // a8: 0100 1000 1010 1000 - { }, // a9: 0100 1000 1010 1001 - {CMC, nullptr }, // aa: 0100 1000 1010 1010 7807 - { }, // ab: 0100 1000 1010 1011 - {EXA, nullptr }, // ac: 0100 1000 1010 1100 7807 - {EXR, nullptr }, // ad: 0100 1000 1010 1101 7807 - {EXH, nullptr }, // ae: 0100 1000 1010 1110 7807 - {EXX, nullptr }, // af: 0100 1000 1010 1111 7807 + { }, // a0: 0111 0000 1010 0000 + {ADDNCX, "(BC)" }, // a1: 0111 0000 1010 0001 + {ADDNCX, "(DE)" }, // a2: 0111 0000 1010 0010 + {ADDNCX, "(HL)" }, // a3: 0111 0000 1010 0011 + {ADDNCX, "(DE+)" }, // a4: 0111 0000 1010 0100 + {ADDNCX, "(HL+)" }, // a5: 0111 0000 1010 0101 + {ADDNCX, "(DE-)" }, // a6: 0111 0000 1010 0110 + {ADDNCX, "(HL-)" }, // a7: 0111 0000 1010 0111 + { }, // a8: 0111 0000 1010 1000 + {GTAX, "(BC)" }, // a9: 0111 0000 1010 1001 + {GTAX, "(DE)" }, // aa: 0111 0000 1010 1010 + {GTAX, "(HL)" }, // ab: 0111 0000 1010 1011 + {GTAX, "(DE+)" }, // ac: 0111 0000 1010 1100 + {GTAX, "(HL+)" }, // ad: 0111 0000 1010 1101 + {GTAX, "(DE-)" }, // ae: 0111 0000 1010 1110 + {GTAX, "(HL-)" }, // af: 0111 0000 1010 1111 - {DRLR, "EA" }, // b0: 0100 1000 1011 0000 - { }, // b1: 0100 1000 1011 0001 - { }, // b2: 0100 1000 1011 0010 - { }, // b3: 0100 1000 1011 0011 - {DRLL, "EA" }, // b4: 0100 1000 1011 0100 - { }, // b5: 0100 1000 1011 0101 - { }, // b6: 0100 1000 1011 0110 - { }, // b7: 0100 1000 1011 0111 - { }, // b8: 0100 1000 1011 1000 - { }, // b9: 0100 1000 1011 1001 - { }, // ba: 0100 1000 1011 1010 - { }, // bb: 0100 1000 1011 1011 - { }, // bc: 0100 1000 1011 1100 - { }, // bd: 0100 1000 1011 1101 - { }, // be: 0100 1000 1011 1110 - { }, // bf: 0100 1000 1011 1111 + { }, // b0: 0111 0000 1011 0000 + {SUBNBX, "(BC)" }, // b1: 0111 0000 1011 0001 + {SUBNBX, "(DE)" }, // b2: 0111 0000 1011 0010 + {SUBNBX, "(HL)" }, // b3: 0111 0000 1011 0011 + {SUBNBX, "(DE+)" }, // b4: 0111 0000 1011 0100 + {SUBNBX, "(HL+)" }, // b5: 0111 0000 1011 0101 + {SUBNBX, "(DE-)" }, // b6: 0111 0000 1011 0110 + {SUBNBX, "(HL-)" }, // b7: 0111 0000 1011 0111 + { }, // b8: 0111 0000 1011 1000 + {LTAX, "(BC)" }, // b9: 0111 0000 1011 1001 + {LTAX, "(DE)" }, // ba: 0111 0000 1011 1010 + {LTAX, "(HL)" }, // bb: 0111 0000 1011 1011 + {LTAX, "(DE+)" }, // bc: 0111 0000 1011 1100 + {LTAX, "(HL+)" }, // bd: 0111 0000 1011 1101 + {LTAX, "(DE-)" }, // be: 0111 0000 1011 1110 + {LTAX, "(HL-)" }, // bf: 0111 0000 1011 1111 - {DMOV, "EA,ECNT" }, // c0: 0100 1000 1100 0000 - {DMOV, "EA,ECPT0"}, // c1: 0100 1000 1100 0001 7807 - {DMOV, "EA,ECPT1"}, // c2: 0100 1000 1100 0010 7807 - { }, // c3: 0100 1000 1100 0011 - { }, // c4: 0100 1000 1100 0100 - { }, // c5: 0100 1000 1100 0101 - { }, // c6: 0100 1000 1100 0110 - { }, // c7: 0100 1000 1100 0111 - { }, // c8: 0100 1000 1100 1000 - { }, // c9: 0100 1000 1100 1001 - { }, // ca: 0100 1000 1100 1010 - { }, // cb: 0100 1000 1100 1011 - { }, // cc: 0100 1000 1100 1100 - { }, // cd: 0100 1000 1100 1101 - { }, // ce: 0100 1000 1100 1110 - { }, // cf: 0100 1000 1100 1111 + { }, // c0: 0111 0000 1100 0000 + {ADDX, "(BC)" }, // c1: 0111 0000 1100 0001 + {ADDX, "(DE)" }, // c2: 0111 0000 1100 0010 + {ADDX, "(HL)" }, // c3: 0111 0000 1100 0011 + {ADDX, "(DE+)" }, // c4: 0111 0000 1100 0100 + {ADDX, "(HL+)" }, // c5: 0111 0000 1100 0101 + {ADDX, "(DE-)" }, // c6: 0111 0000 1100 0110 + {ADDX, "(HL-)" }, // c7: 0111 0000 1100 0111 + { }, // c8: 0111 0000 1100 1000 + {ONAX, "(BC)" }, // c9: 0111 0000 1100 1001 + {ONAX, "(DE)" }, // ca: 0111 0000 1100 1010 + {ONAX, "(HL)" }, // cb: 0111 0000 1100 1011 + {ONAX, "(DE+)" }, // cc: 0111 0000 1100 1100 + {ONAX, "(HL+)" }, // cd: 0111 0000 1100 1101 + {ONAX, "(DE-)" }, // ce: 0111 0000 1100 1110 + {ONAX, "(HL-)" }, // cf: 0111 0000 1100 1111 - { }, // d0: 0100 1000 1101 0000 - { }, // d1: 0100 1000 1101 0001 - {DMOV, "ETM0,EA" }, // d2: 0100 1000 1101 0010 - {DMOV, "ETM1,EA" }, // d3: 0100 1000 1101 0011 - { }, // d4: 0100 1000 1101 0100 - { }, // d5: 0100 1000 1101 0101 - { }, // d6: 0100 1000 1101 0110 - { }, // d7: 0100 1000 1101 0111 - { }, // d8: 0100 1000 1101 1000 - { }, // d9: 0100 1000 1101 1001 - { }, // da: 0100 1000 1101 1010 - { }, // db: 0100 1000 1101 1011 - { }, // dc: 0100 1000 1101 1100 - { }, // dd: 0100 1000 1101 1101 - { }, // de: 0100 1000 1101 1110 - { }, // df: 0100 1000 1101 1111 + { }, // d0: 0111 0000 1101 0000 + {ADCX, "(BC)" }, // d1: 0111 0000 1101 0001 + {ADCX, "(DE)" }, // d2: 0111 0000 1101 0010 + {ADCX, "(HL)" }, // d3: 0111 0000 1101 0011 + {ADCX, "(DE+)" }, // d4: 0111 0000 1101 0100 + {ADCX, "(HL+)" }, // d5: 0111 0000 1101 0101 + {ADCX, "(DE-)" }, // d6: 0111 0000 1101 0110 + {ADCX, "(HL-)" }, // d7: 0111 0000 1101 0111 + { }, // d8: 0111 0000 1101 1000 + {OFFAX, "(BC)" }, // d9: 0111 0000 1101 1001 + {OFFAX, "(DE)" }, // da: 0111 0000 1101 1010 + {OFFAX, "(HL)" }, // db: 0111 0000 1101 1011 + {OFFAX, "(DE+)" }, // dc: 0111 0000 1101 1100 + {OFFAX, "(HL+)" }, // dd: 0111 0000 1101 1101 + {OFFAX, "(DE-)" }, // de: 0111 0000 1101 1110 + {OFFAX, "(HL-)" }, // df: 0111 0000 1101 1111 - { }, // e0: 0100 1000 1110 0000 - { }, // e1: 0100 1000 1110 0001 - { }, // e2: 0100 1000 1110 0010 - { }, // e3: 0100 1000 1110 0011 - { }, // e4: 0100 1000 1110 0100 - { }, // e5: 0100 1000 1110 0101 - { }, // e6: 0100 1000 1110 0110 - { }, // e7: 0100 1000 1110 0111 - { }, // e8: 0100 1000 1110 1000 - { }, // e9: 0100 1000 1110 1001 - { }, // ea: 0100 1000 1110 1010 - { }, // eb: 0100 1000 1110 1011 - { }, // ec: 0100 1000 1110 1100 - { }, // ed: 0100 1000 1110 1101 - { }, // ee: 0100 1000 1110 1110 - { }, // ef: 0100 1000 1110 1111 + { }, // e0: 0111 0000 1110 0000 + {SUBX, "(BC)" }, // e1: 0111 0000 1110 0001 + {SUBX, "(DE)" }, // e2: 0111 0000 1110 0010 + {SUBX, "(HL)" }, // e3: 0111 0000 1110 0011 + {SUBX, "(DE+)" }, // e4: 0111 0000 1110 0100 + {SUBX, "(HL+)" }, // e5: 0111 0000 1110 0101 + {SUBX, "(DE-)" }, // e6: 0111 0000 1110 0110 + {SUBX, "(HL-)" }, // e7: 0111 0000 1110 0111 + { }, // e8: 0111 0000 1110 1000 + {NEAX, "(BC)" }, // e9: 0111 0000 1110 1001 + {NEAX, "(DE)" }, // ea: 0111 0000 1110 1010 + {NEAX, "(HL)" }, // eb: 0111 0000 1110 1011 + {NEAX, "(DE+)" }, // ec: 0111 0000 1110 1100 + {NEAX, "(HL+)" }, // ed: 0111 0000 1110 1101 + {NEAX, "(DE-)" }, // ee: 0111 0000 1110 1110 + {NEAX, "(HL-)" }, // ef: 0111 0000 1110 1111 - { }, // f0: 0100 1000 1111 0000 - { }, // f1: 0100 1000 1111 0001 - { }, // f2: 0100 1000 1111 0010 - { }, // f3: 0100 1000 1111 0011 - { }, // f4: 0100 1000 1111 0100 - { }, // f5: 0100 1000 1111 0101 - { }, // f6: 0100 1000 1111 0110 - { }, // f7: 0100 1000 1111 0111 - { }, // f8: 0100 1000 1111 1000 - { }, // f9: 0100 1000 1111 1001 - { }, // fa: 0100 1000 1111 1010 - { }, // fb: 0100 1000 1111 1011 - { }, // fc: 0100 1000 1111 1100 - { }, // fd: 0100 1000 1111 1101 - { }, // fe: 0100 1000 1111 1110 - { } // ff: 0100 1000 1111 1111 + { }, // f0: 0111 0000 1111 0000 + {SBBX, "(BC)" }, // f1: 0111 0000 1111 0001 + {SBBX, "(DE)" }, // f2: 0111 0000 1111 0010 + {SBBX, "(HL)" }, // f3: 0111 0000 1111 0011 + {SBBX, "(DE+)" }, // f4: 0111 0000 1111 0100 + {SBBX, "(HL+)" }, // f5: 0111 0000 1111 0101 + {SBBX, "(DE-)" }, // f6: 0111 0000 1111 0110 + {SBBX, "(HL-)" }, // f7: 0111 0000 1111 0111 + { }, // f8: 0111 0000 1111 1000 + {EQAX, "(BC)" }, // f9: 0111 0000 1111 1001 + {EQAX, "(DE)" }, // fa: 0111 0000 1111 1010 + {EQAX, "(HL)" }, // fb: 0111 0000 1111 1011 + {EQAX, "(DE+)" }, // fc: 0111 0000 1111 1100 + {EQAX, "(HL+)" }, // fd: 0111 0000 1111 1101 + {EQAX, "(DE-)" }, // fe: 0111 0000 1111 1110 + {EQAX, "(HL-)" } // ff: 0111 0000 1111 1111 }; -// prefix 4C -const dasm_s dasm_s::d4C_7810[256] = +// prefix 74 +const upd7810_base_disassembler::dasm_s upd7810_base_disassembler::d74[256] = { - { }, // 00: 0100 1100 0000 0000 - { }, // 01: 0100 1100 0000 0001 - { }, // 02: 0100 1100 0000 0010 - { }, // 03: 0100 1100 0000 0011 - { }, // 04: 0100 1100 0000 0100 - { }, // 05: 0100 1100 0000 0101 - { }, // 06: 0100 1100 0000 0110 - { }, // 07: 0100 1100 0000 0111 - { }, // 08: 0100 1100 0000 1000 - { }, // 09: 0100 1100 0000 1001 - { }, // 0a: 0100 1100 0000 1010 - { }, // 0b: 0100 1100 0000 1011 - { }, // 0c: 0100 1100 0000 1100 - { }, // 0d: 0100 1100 0000 1101 - { }, // 0e: 0100 1100 0000 1110 - { }, // 0f: 0100 1100 0000 1111 + { }, // 00: 0111 0100 0000 0000 + { }, // 01: 0111 0100 0000 0001 + { }, // 02: 0111 0100 0000 0010 + { }, // 03: 0111 0100 0000 0011 + { }, // 04: 0111 0100 0000 0100 + { }, // 05: 0111 0100 0000 0101 + { }, // 06: 0111 0100 0000 0110 + { }, // 07: 0111 0100 0000 0111 + {ANI, "V,%b" }, // 08: 0111 0100 0000 1000 xxxx xxxx + {ANI, "A,%b" }, // 09: 0111 0100 0000 1001 xxxx xxxx + {ANI, "B,%b" }, // 0a: 0111 0100 0000 1010 xxxx xxxx + {ANI, "C,%b" }, // 0b: 0111 0100 0000 1011 xxxx xxxx + {ANI, "D,%b" }, // 0c: 0111 0100 0000 1100 xxxx xxxx + {ANI, "E,%b" }, // 0d: 0111 0100 0000 1101 xxxx xxxx + {ANI, "H,%b" }, // 0e: 0111 0100 0000 1110 xxxx xxxx + {ANI, "L,%b" }, // 0f: 0111 0100 0000 1111 xxxx xxxx - { }, // 10: 0100 1100 0001 0000 - { }, // 11: 0100 1100 0001 0001 - { }, // 12: 0100 1100 0001 0010 - { }, // 13: 0100 1100 0001 0011 - { }, // 14: 0100 1100 0001 0100 - { }, // 15: 0100 1100 0001 0101 - { }, // 16: 0100 1100 0001 0110 - { }, // 17: 0100 1100 0001 0111 - { }, // 18: 0100 1100 0001 1000 - { }, // 19: 0100 1100 0001 1001 - { }, // 1a: 0100 1100 0001 1010 - { }, // 1b: 0100 1100 0001 1011 - { }, // 1c: 0100 1100 0001 1100 - { }, // 1d: 0100 1100 0001 1101 - { }, // 1e: 0100 1100 0001 1110 - { }, // 1f: 0100 1100 0001 1111 + {XRI, "V,%b" }, // 10: 0111 0100 0001 0000 xxxx xxxx + {XRI, "A,%b" }, // 11: 0111 0100 0001 0001 xxxx xxxx + {XRI, "B,%b" }, // 12: 0111 0100 0001 0010 xxxx xxxx + {XRI, "C,%b" }, // 13: 0111 0100 0001 0011 xxxx xxxx + {XRI, "D,%b" }, // 14: 0111 0100 0001 0100 xxxx xxxx + {XRI, "E,%b" }, // 15: 0111 0100 0001 0101 xxxx xxxx + {XRI, "H,%b" }, // 16: 0111 0100 0001 0110 xxxx xxxx + {XRI, "L,%b" }, // 17: 0111 0100 0001 0111 xxxx xxxx + {ORI, "V,%b" }, // 18: 0111 0100 0001 1000 xxxx xxxx + {ORI, "A,%b" }, // 19: 0111 0100 0001 1001 xxxx xxxx + {ORI, "B,%b" }, // 1a: 0111 0100 0001 1010 xxxx xxxx + {ORI, "C,%b" }, // 1b: 0111 0100 0001 1011 xxxx xxxx + {ORI, "D,%b" }, // 1c: 0111 0100 0001 1100 xxxx xxxx + {ORI, "E,%b" }, // 1d: 0111 0100 0001 1101 xxxx xxxx + {ORI, "H,%b" }, // 1e: 0111 0100 0001 1110 xxxx xxxx + {ORI, "L,%b" }, // 1f: 0111 0100 0001 1111 xxxx xxxx - { }, // 20: 0100 1100 0010 0000 - { }, // 21: 0100 1100 0010 0001 - { }, // 22: 0100 1100 0010 0010 - { }, // 23: 0100 1100 0010 0011 - { }, // 24: 0100 1100 0010 0100 - { }, // 25: 0100 1100 0010 0101 - { }, // 26: 0100 1100 0010 0110 - { }, // 27: 0100 1100 0010 0111 - { }, // 28: 0100 1100 0010 1000 - { }, // 29: 0100 1100 0010 1001 - { }, // 2a: 0100 1100 0010 1010 - { }, // 2b: 0100 1100 0010 1011 - { }, // 2c: 0100 1100 0010 1100 - { }, // 2d: 0100 1100 0010 1101 - { }, // 2e: 0100 1100 0010 1110 - { }, // 2f: 0100 1100 0010 1111 + {ADINC, "V,%b" }, // 20: 0111 0100 0010 0000 xxxx xxxx + {ADINC, "A,%b" }, // 21: 0111 0100 0010 0001 xxxx xxxx + {ADINC, "B,%b" }, // 22: 0111 0100 0010 0010 xxxx xxxx + {ADINC, "C,%b" }, // 23: 0111 0100 0010 0011 xxxx xxxx + {ADINC, "D,%b" }, // 24: 0111 0100 0010 0100 xxxx xxxx + {ADINC, "E,%b" }, // 25: 0111 0100 0010 0101 xxxx xxxx + {ADINC, "H,%b" }, // 26: 0111 0100 0010 0110 xxxx xxxx + {ADINC, "L,%b" }, // 27: 0111 0100 0010 0111 xxxx xxxx + {GTI, "V,%b" }, // 28: 0111 0100 0010 1000 xxxx xxxx + {GTI, "A,%b" }, // 29: 0111 0100 0010 1001 xxxx xxxx + {GTI, "B,%b" }, // 2a: 0111 0100 0010 1010 xxxx xxxx + {GTI, "C,%b" }, // 2b: 0111 0100 0010 1011 xxxx xxxx + {GTI, "D,%b" }, // 2c: 0111 0100 0010 1100 xxxx xxxx + {GTI, "E,%b" }, // 2d: 0111 0100 0010 1101 xxxx xxxx + {GTI, "H,%b" }, // 2e: 0111 0100 0010 1110 xxxx xxxx + {GTI, "L,%b" }, // 2f: 0111 0100 0010 1111 xxxx xxxx - { }, // 30: 0100 1100 0011 0000 - { }, // 31: 0100 1100 0011 0001 - { }, // 32: 0100 1100 0011 0010 - { }, // 33: 0100 1100 0011 0011 - { }, // 34: 0100 1100 0011 0100 - { }, // 35: 0100 1100 0011 0101 - { }, // 36: 0100 1100 0011 0110 - { }, // 37: 0100 1100 0011 0111 - { }, // 38: 0100 1100 0011 1000 - { }, // 39: 0100 1100 0011 1001 - { }, // 3a: 0100 1100 0011 1010 - { }, // 3b: 0100 1100 0011 1011 - { }, // 3c: 0100 1100 0011 1100 - { }, // 3d: 0100 1100 0011 1101 - { }, // 3e: 0100 1100 0011 1110 - { }, // 3f: 0100 1100 0011 1111 + {SUINB, "V,%b" }, // 30: 0111 0100 0011 0000 xxxx xxxx + {SUINB, "A,%b" }, // 31: 0111 0100 0011 0001 xxxx xxxx + {SUINB, "B,%b" }, // 32: 0111 0100 0011 0010 xxxx xxxx + {SUINB, "C,%b" }, // 33: 0111 0100 0011 0011 xxxx xxxx + {SUINB, "D,%b" }, // 34: 0111 0100 0011 0100 xxxx xxxx + {SUINB, "E,%b" }, // 35: 0111 0100 0011 0101 xxxx xxxx + {SUINB, "H,%b" }, // 36: 0111 0100 0011 0110 xxxx xxxx + {SUINB, "L,%b" }, // 37: 0111 0100 0011 0111 xxxx xxxx + {LTI, "V,%b" }, // 37: 0111 0100 0011 1000 xxxx xxxx + {LTI, "A,%b" }, // 39: 0111 0100 0011 1001 xxxx xxxx + {LTI, "B,%b" }, // 3a: 0111 0100 0011 1010 xxxx xxxx + {LTI, "C,%b" }, // 3b: 0111 0100 0011 1011 xxxx xxxx + {LTI, "D,%b" }, // 3c: 0111 0100 0011 1100 xxxx xxxx + {LTI, "E,%b" }, // 3d: 0111 0100 0011 1101 xxxx xxxx + {LTI, "H,%b" }, // 3e: 0111 0100 0011 1110 xxxx xxxx + {LTI, "L,%b" }, // 3f: 0111 0100 0011 1111 xxxx xxxx - { }, // 40: 0100 1100 0100 0000 - { }, // 41: 0100 1100 0100 0001 - { }, // 42: 0100 1100 0100 0010 - { }, // 43: 0100 1100 0100 0011 - { }, // 44: 0100 1100 0100 0100 - { }, // 45: 0100 1100 0100 0101 - { }, // 46: 0100 1100 0100 0110 - { }, // 47: 0100 1100 0100 0111 - { }, // 48: 0100 1100 0100 1000 - { }, // 49: 0100 1100 0100 1001 - { }, // 4a: 0100 1100 0100 1010 - { }, // 4b: 0100 1100 0100 1011 - { }, // 4c: 0100 1100 0100 1100 - { }, // 4d: 0100 1100 0100 1101 - { }, // 4e: 0100 1100 0100 1110 - { }, // 4f: 0100 1100 0100 1111 + {ADI, "V,%b" }, // 40: 0111 0100 0100 0000 xxxx xxxx + {ADI, "A,%b" }, // 41: 0111 0100 0100 0001 xxxx xxxx + {ADI, "B,%b" }, // 42: 0111 0100 0100 0010 xxxx xxxx + {ADI, "C,%b" }, // 43: 0111 0100 0100 0011 xxxx xxxx + {ADI, "D,%b" }, // 44: 0111 0100 0100 0100 xxxx xxxx + {ADI, "E,%b" }, // 45: 0111 0100 0100 0101 xxxx xxxx + {ADI, "H,%b" }, // 46: 0111 0100 0100 0110 xxxx xxxx + {ADI, "L,%b" }, // 47: 0111 0100 0100 0111 xxxx xxxx + {ONI, "V,%b" }, // 48: 0111 0100 0100 1000 xxxx xxxx + {ONI, "A,%b" }, // 49: 0111 0100 0100 1001 xxxx xxxx + {ONI, "B,%b" }, // 4a: 0111 0100 0100 1010 xxxx xxxx + {ONI, "C,%b" }, // 4b: 0111 0100 0100 1011 xxxx xxxx + {ONI, "D,%b" }, // 4c: 0111 0100 0100 1100 xxxx xxxx + {ONI, "E,%b" }, // 4d: 0111 0100 0100 1101 xxxx xxxx + {ONI, "H,%b" }, // 4e: 0111 0100 0100 1110 xxxx xxxx + {ONI, "L,%b" }, // 4f: 0111 0100 0100 1111 xxxx xxxx - { }, // 50: 0100 1100 0101 0000 - { }, // 51: 0100 1100 0101 0001 - { }, // 52: 0100 1100 0101 0010 - { }, // 53: 0100 1100 0101 0011 - { }, // 54: 0100 1100 0101 0100 - { }, // 55: 0100 1100 0101 0101 - { }, // 56: 0100 1100 0101 0110 - { }, // 57: 0100 1100 0101 0111 - { }, // 58: 0100 1100 0101 1000 - { }, // 59: 0100 1100 0101 1001 - { }, // 5a: 0100 1100 0101 1010 - { }, // 5b: 0100 1100 0101 1011 - { }, // 5c: 0100 1100 0101 1100 - { }, // 5d: 0100 1100 0101 1101 - { }, // 5e: 0100 1100 0101 1110 - { }, // 5f: 0100 1100 0101 1111 + {ACI, "V,%b" }, // 50: 0111 0100 0101 0000 xxxx xxxx + {ACI, "A,%b" }, // 51: 0111 0100 0101 0001 xxxx xxxx + {ACI, "B,%b" }, // 52: 0111 0100 0101 0010 xxxx xxxx + {ACI, "C,%b" }, // 53: 0111 0100 0101 0011 xxxx xxxx + {ACI, "D,%b" }, // 54: 0111 0100 0101 0100 xxxx xxxx + {ACI, "E,%b" }, // 55: 0111 0100 0101 0101 xxxx xxxx + {ACI, "H,%b" }, // 56: 0111 0100 0101 0110 xxxx xxxx + {ACI, "L,%b" }, // 57: 0111 0100 0101 0111 xxxx xxxx + {OFFI, "V,%b" }, // 58: 0111 0100 0101 1000 xxxx xxxx + {OFFI, "A,%b" }, // 59: 0111 0100 0101 1001 xxxx xxxx + {OFFI, "B,%b" }, // 5a: 0111 0100 0101 1010 xxxx xxxx + {OFFI, "C,%b" }, // 5b: 0111 0100 0101 1011 xxxx xxxx + {OFFI, "D,%b" }, // 5c: 0111 0100 0101 1100 xxxx xxxx + {OFFI, "E,%b" }, // 5d: 0111 0100 0101 1101 xxxx xxxx + {OFFI, "H,%b" }, // 5e: 0111 0100 0101 1110 xxxx xxxx + {OFFI, "L,%b" }, // 5f: 0111 0100 0101 1111 xxxx xxxx - { }, // 60: 0100 1100 0110 0000 - { }, // 61: 0100 1100 0110 0001 - { }, // 62: 0100 1100 0110 0010 - { }, // 63: 0100 1100 0110 0011 - { }, // 64: 0100 1100 0110 0100 - { }, // 65: 0100 1100 0110 0101 - { }, // 66: 0100 1100 0110 0110 - { }, // 67: 0100 1100 0110 0111 - { }, // 68: 0100 1100 0110 1000 - { }, // 69: 0100 1100 0110 1001 - { }, // 6a: 0100 1100 0110 1010 - { }, // 6b: 0100 1100 0110 1011 - { }, // 6c: 0100 1100 0110 1100 - { }, // 6d: 0100 1100 0110 1101 - { }, // 6e: 0100 1100 0110 1110 - { }, // 6f: 0100 1100 0110 1111 + {SUI, "V,%b" }, // 60: 0111 0100 0110 0000 xxxx xxxx + {SUI, "A,%b" }, // 61: 0111 0100 0110 0001 xxxx xxxx + {SUI, "B,%b" }, // 62: 0111 0100 0110 0010 xxxx xxxx + {SUI, "C,%b" }, // 63: 0111 0100 0110 0011 xxxx xxxx + {SUI, "D,%b" }, // 64: 0111 0100 0110 0100 xxxx xxxx + {SUI, "E,%b" }, // 65: 0111 0100 0110 0101 xxxx xxxx + {SUI, "H,%b" }, // 66: 0111 0100 0110 0110 xxxx xxxx + {SUI, "L,%b" }, // 67: 0111 0100 0110 0111 xxxx xxxx + {NEI, "V,%b" }, // 68: 0111 0100 0110 1000 xxxx xxxx + {NEI, "A,%b" }, // 69: 0111 0100 0110 1001 xxxx xxxx + {NEI, "B,%b" }, // 6a: 0111 0100 0110 1010 xxxx xxxx + {NEI, "C,%b" }, // 6b: 0111 0100 0110 1011 xxxx xxxx + {NEI, "D,%b" }, // 6c: 0111 0100 0110 1100 xxxx xxxx + {NEI, "E,%b" }, // 6d: 0111 0100 0110 1101 xxxx xxxx + {NEI, "H,%b" }, // 6e: 0111 0100 0110 1110 xxxx xxxx + {NEI, "L,%b" }, // 6f: 0111 0100 0110 1111 xxxx xxxx - { }, // 70: 0100 1100 0111 0000 - { }, // 71: 0100 1100 0111 0001 - { }, // 72: 0100 1100 0111 0010 - { }, // 73: 0100 1100 0111 0011 - { }, // 74: 0100 1100 0111 0100 - { }, // 75: 0100 1100 0111 0101 - { }, // 76: 0100 1100 0111 0110 - { }, // 77: 0100 1100 0111 0111 - { }, // 78: 0100 1100 0111 1000 - { }, // 79: 0100 1100 0111 1001 - { }, // 7a: 0100 1100 0111 1010 - { }, // 7b: 0100 1100 0111 1011 - { }, // 7c: 0100 1100 0111 1100 - { }, // 7d: 0100 1100 0111 1101 - { }, // 7e: 0100 1100 0111 1110 - { }, // 7f: 0100 1100 0111 1111 + {SBI, "V,%b" }, // 70: 0111 0100 0111 0000 xxxx xxxx + {SBI, "A,%b" }, // 71: 0111 0100 0111 0001 xxxx xxxx + {SBI, "B,%b" }, // 72: 0111 0100 0111 0010 xxxx xxxx + {SBI, "C,%b" }, // 73: 0111 0100 0111 0011 xxxx xxxx + {SBI, "D,%b" }, // 74: 0111 0100 0111 0100 xxxx xxxx + {SBI, "E,%b" }, // 75: 0111 0100 0111 0101 xxxx xxxx + {SBI, "H,%b" }, // 76: 0111 0100 0111 0110 xxxx xxxx + {SBI, "L,%b" }, // 77: 0111 0100 0111 0111 xxxx xxxx + {EQI, "V,%b" }, // 78: 0111 0100 0111 1000 xxxx xxxx + {EQI, "A,%b" }, // 79: 0111 0100 0111 1001 xxxx xxxx + {EQI, "B,%b" }, // 7a: 0111 0100 0111 1010 xxxx xxxx + {EQI, "C,%b" }, // 7b: 0111 0100 0111 1011 xxxx xxxx + {EQI, "D,%b" }, // 7c: 0111 0100 0111 1100 xxxx xxxx + {EQI, "E,%b" }, // 7d: 0111 0100 0111 1101 xxxx xxxx + {EQI, "H,%b" }, // 7e: 0111 0100 0111 1110 xxxx xxxx + {EQI, "L,%b" }, // 7f: 0111 0100 0111 1111 xxxx xxxx - { }, // 80: 0100 1100 1000 0000 - { }, // 81: 0100 1100 1000 0001 - { }, // 82: 0100 1100 1000 0010 - { }, // 83: 0100 1100 1000 0011 - { }, // 84: 0100 1100 1000 0100 - { }, // 85: 0100 1100 1000 0101 - { }, // 86: 0100 1100 1000 0110 - { }, // 87: 0100 1100 1000 0111 - { }, // 88: 0100 1100 1000 1000 - { }, // 89: 0100 1100 1000 1001 - { }, // 8a: 0100 1100 1000 1010 - { }, // 8b: 0100 1100 1000 1011 - { }, // 8c: 0100 1100 1000 1100 - { }, // 8d: 0100 1100 1000 1101 - { }, // 8e: 0100 1100 1000 1110 - { }, // 8f: 0100 1100 1000 1111 + { }, // 80: 0111 0100 1000 0000 + { }, // 81: 0111 0100 1000 0001 + { }, // 82: 0111 0100 1000 0010 + { }, // 83: 0111 0100 1000 0011 + { }, // 84: 0111 0100 1000 0100 + { }, // 85: 0111 0100 1000 0101 + { }, // 86: 0111 0100 1000 0110 + { }, // 87: 0111 0100 1000 0111 + {ANAW, "%a" }, // 88: 0111 0100 1000 1000 oooo oooo + { }, // 89: 0111 0100 1000 1001 + { }, // 8a: 0111 0100 1000 1010 + { }, // 8b: 0111 0100 1000 1011 + { }, // 8c: 0111 0100 1000 1100 + {DAN, "EA,BC" }, // 8d: 0111 0100 1000 1101 + {DAN, "EA,DE" }, // 8e: 0111 0100 1000 1110 + {DAN, "EA,HL" }, // 8f: 0111 0100 1000 1111 - { }, // 90: 0100 1100 1001 0000 - { }, // 91: 0100 1100 1001 0001 - { }, // 92: 0100 1100 1001 0010 - { }, // 93: 0100 1100 1001 0011 - { }, // 94: 0100 1100 1001 0100 - { }, // 95: 0100 1100 1001 0101 - { }, // 96: 0100 1100 1001 0110 - { }, // 97: 0100 1100 1001 0111 - { }, // 98: 0100 1100 1001 1000 - { }, // 99: 0100 1100 1001 1001 - { }, // 9a: 0100 1100 1001 1010 - { }, // 9b: 0100 1100 1001 1011 - { }, // 9c: 0100 1100 1001 1100 - { }, // 9d: 0100 1100 1001 1101 - { }, // 9e: 0100 1100 1001 1110 - { }, // 9f: 0100 1100 1001 1111 + {XRAW, "%a" }, // 90: 0111 0100 1001 0000 oooo oooo + { }, // 91: 0111 0100 1001 0001 + { }, // 92: 0111 0100 1001 0010 + { }, // 93: 0111 0100 1001 0011 + { }, // 94: 0111 0100 1001 0100 + {DXR, "EA,BC" }, // 95: 0111 0100 1001 0101 + {DXR, "EA,DE" }, // 96: 0111 0100 1001 0110 + {DXR, "EA,HL" }, // 97: 0111 0100 1001 0111 + {ORAW, "%a" }, // 98: 0111 0100 1001 1000 oooo oooo + { }, // 99: 0111 0100 1001 1001 + { }, // 9a: 0111 0100 1001 1010 + { }, // 9b: 0111 0100 1001 1011 + { }, // 9c: 0111 0100 1001 1100 + {DOR, "EA,BC" }, // 9d: 0111 0100 1001 1101 + {DOR, "EA,DE" }, // 9e: 0111 0100 1001 1110 + {DOR, "EA,HL" }, // 9f: 0111 0100 1001 1111 - { }, // a0: 0100 1100 1010 0000 - { }, // a1: 0100 1100 1010 0001 - { }, // a2: 0100 1100 1010 0010 - { }, // a3: 0100 1100 1010 0011 - { }, // a4: 0100 1100 1010 0100 - { }, // a5: 0100 1100 1010 0101 - { }, // a6: 0100 1100 1010 0110 - { }, // a7: 0100 1100 1010 0111 - { }, // a8: 0100 1100 1010 1000 - { }, // a9: 0100 1100 1010 1001 - { }, // aa: 0100 1100 1010 1010 - { }, // ab: 0100 1100 1010 1011 - { }, // ac: 0100 1100 1010 1100 - { }, // ad: 0100 1100 1010 1101 - { }, // ae: 0100 1100 1010 1110 - { }, // af: 0100 1100 1010 1111 + {ADDNCW, "%a" }, // a0: 0111 0100 1010 0000 oooo oooo + { }, // a1: 0111 0100 1010 0001 + { }, // a2: 0111 0100 1010 0010 + { }, // a3: 0111 0100 1010 0011 + { }, // a4: 0111 0100 1010 0100 + {DADDNC, "EA,BC" }, // a5: 0111 0100 1010 0101 + {DADDNC, "EA,DE" }, // a6: 0111 0100 1010 0110 + {DADDNC, "EA,HL" }, // a7: 0111 0100 1010 0111 + {GTAW, "%a" }, // a8: 0111 0100 1010 1000 oooo oooo + { }, // a9: 0111 0100 1010 1001 + { }, // aa: 0111 0100 1010 1010 + { }, // ab: 0111 0100 1010 1011 + { }, // ac: 0111 0100 1010 1100 + {DGT, "EA,BC" }, // ad: 0111 0100 1010 1101 + {DGT, "EA,DE" }, // ae: 0111 0100 1010 1110 + {DGT, "EA,HL" }, // af: 0111 0100 1010 1111 - { }, // b0: 0100 1100 1011 0000 - { }, // b1: 0100 1100 1011 0001 - { }, // b2: 0100 1100 1011 0010 - { }, // b3: 0100 1100 1011 0011 - { }, // b4: 0100 1100 1011 0100 - { }, // b5: 0100 1100 1011 0101 - { }, // b6: 0100 1100 1011 0110 - { }, // b7: 0100 1100 1011 0111 - { }, // b8: 0100 1100 1011 1000 - { }, // b9: 0100 1100 1011 1001 - { }, // ba: 0100 1100 1011 1010 - { }, // bb: 0100 1100 1011 1011 - { }, // bc: 0100 1100 1011 1100 - { }, // bd: 0100 1100 1011 1101 - { }, // be: 0100 1100 1011 1110 - { }, // bf: 0100 1100 1011 1111 + {SUBNBW, "%a" }, // b0: 0111 0100 1011 0000 oooo oooo + { }, // b1: 0111 0100 1011 0001 + { }, // b2: 0111 0100 1011 0010 + { }, // b3: 0111 0100 1011 0011 + { }, // b4: 0111 0100 1011 0100 + {DSUBNB, "EA,BC" }, // b5: 0111 0100 1011 0101 + {DSUBNB, "EA,DE" }, // b6: 0111 0100 1011 0110 + {DSUBNB, "EA,HL" }, // b7: 0111 0100 1011 0111 + {LTAW, "%a" }, // b8: 0111 0100 1011 1000 oooo oooo + { }, // b9: 0111 0100 1011 1001 + { }, // ba: 0111 0100 1011 1010 + { }, // bb: 0111 0100 1011 1011 + { }, // bc: 0111 0100 1011 1100 + {DLT, "EA,BC" }, // bd: 0111 0100 1011 1101 + {DLT, "EA,DE" }, // be: 0111 0100 1011 1110 + {DLT, "EA,HL" }, // bf: 0111 0100 1011 1111 - {MOV, "A,PA" }, // c0: 0100 1100 1100 0000 - {MOV, "A,PB" }, // c1: 0100 1100 1100 0001 - {MOV, "A,PC" }, // c2: 0100 1100 1100 0010 - {MOV, "A,PD" }, // c3: 0100 1100 1100 0011 - { }, // c4: 0100 1100 1100 0100 - {MOV, "A,PF" }, // c5: 0100 1100 1100 0101 - {MOV, "A,MKH" }, // c6: 0100 1100 1100 0110 - {MOV, "A,MKL" }, // c7: 0100 1100 1100 0111 - {MOV, "A,ANM" }, // c8: 0100 1100 1100 1000 7810 - {MOV, "A,SMH" }, // c9: 0100 1100 1100 1001 - { }, // ca: 0100 1100 1100 1010 - {MOV, "A,EOM" }, // cb: 0100 1100 1100 1011 - { }, // cc: 0100 1100 1100 1100 - {MOV, "A,TMM" }, // cd: 0100 1100 1100 1101 - { }, // ce: 0100 1100 1100 1110 - { }, // cf: 0100 1100 1100 1111 + {ADDW, "%a" }, // c0: 0111 0100 1100 0000 oooo oooo + { }, // c1: 0111 0100 1100 0001 + { }, // c2: 0111 0100 1100 0010 + { }, // c3: 0111 0100 1100 0011 + { }, // c4: 0111 0100 1100 0100 + {DADD, "EA,BC" }, // c5: 0111 0100 1100 0101 + {DADD, "EA,DE" }, // c6: 0111 0100 1100 0110 + {DADD, "EA,HL" }, // c7: 0111 0100 1100 0111 + {ONAW, "%a" }, // c8: 0111 0100 1100 1000 oooo oooo + { }, // c9: 0111 0100 1100 1001 + { }, // ca: 0111 0100 1100 1010 + { }, // cb: 0111 0100 1100 1011 + { }, // cc: 0111 0100 1100 1100 + {DON, "EA,BC" }, // cd: 0111 0100 1100 1101 + {DON, "EA,DE" }, // ce: 0111 0100 1100 1110 + {DON, "EA,HL" }, // cf: 0111 0100 1100 1111 - { }, // d0: 0100 1100 1101 0000 - { }, // d1: 0100 1100 1101 0001 - { }, // d2: 0100 1100 1101 0010 - { }, // d3: 0100 1100 1101 0011 - { }, // d4: 0100 1100 1101 0100 - { }, // d5: 0100 1100 1101 0101 - { }, // d6: 0100 1100 1101 0110 - { }, // d7: 0100 1100 1101 0111 - { }, // d8: 0100 1100 1101 1000 - {MOV, "A,RXB" }, // d9: 0100 1100 1101 1001 - { }, // da: 0100 1100 1101 1010 - { }, // db: 0100 1100 1101 1011 - { }, // dc: 0100 1100 1101 1100 - { }, // dd: 0100 1100 1101 1101 - { }, // de: 0100 1100 1101 1110 - { }, // df: 0100 1100 1101 1111 + {ADCW, "%a" }, // d0: 0111 0100 1101 0000 oooo oooo + { }, // d1: 0111 0100 1101 0001 + { }, // d2: 0111 0100 1101 0010 + { }, // d3: 0111 0100 1101 0011 + { }, // d4: 0111 0100 1101 0100 + {DADC, "EA,BC" }, // d5: 0111 0100 1101 0101 + {DADC, "EA,DE" }, // d6: 0111 0100 1101 0110 + {DADC, "EA,HL" }, // d7: 0111 0100 1101 0111 + {OFFAW, "%a" }, // d8: 0111 0100 1101 1000 oooo oooo + { }, // d9: 0111 0100 1101 1001 + { }, // da: 0111 0100 1101 1010 + { }, // db: 0111 0100 1101 1011 + { }, // dc: 0111 0100 1101 1100 + {DOFF, "EA,BC" }, // dd: 0111 0100 1101 1101 + {DOFF, "EA,DE" }, // de: 0111 0100 1101 1110 + {DOFF, "EA,HL" }, // df: 0111 0100 1101 1111 - {MOV, "A,CR0" }, // e0: 0100 1100 1110 0000 7810 - {MOV, "A,CR1" }, // e1: 0100 1100 1110 0001 7810 - {MOV, "A,CR2" }, // e2: 0100 1100 1110 0010 7810 - {MOV, "A,CR3" }, // e3: 0100 1100 1110 0011 7810 - { }, // e4: 0100 1100 1110 0100 - { }, // e5: 0100 1100 1110 0101 - { }, // e6: 0100 1100 1110 0110 - { }, // e7: 0100 1100 1110 0111 - { }, // e8: 0100 1100 1110 1000 - { }, // e9: 0100 1100 1110 1001 - { }, // ea: 0100 1100 1110 1010 - { }, // eb: 0100 1100 1110 1011 - { }, // ec: 0100 1100 1110 1100 - { }, // ed: 0100 1100 1110 1101 - { }, // ee: 0100 1100 1110 1110 - { }, // ef: 0100 1100 1110 1111 + {SUBW, "%a" }, // e0: 0111 0100 1110 0000 oooo oooo + { }, // e1: 0111 0100 1110 0001 + { }, // e2: 0111 0100 1110 0010 + { }, // e3: 0111 0100 1110 0011 + { }, // e4: 0111 0100 1110 0100 + {DSUB, "EA,BC" }, // e5: 0111 0100 1110 0101 + {DSUB, "EA,DE" }, // e6: 0111 0100 1110 0110 + {DSUB, "EA,HL" }, // e7: 0111 0100 1110 0111 + {NEAW, "%a" }, // e8: 0111 0100 1110 1000 oooo oooo + { }, // e9: 0111 0100 1110 1001 + { }, // ea: 0111 0100 1110 1010 + { }, // eb: 0111 0100 1110 1011 + { }, // ec: 0111 0100 1110 1100 + {DNE, "EA,BC" }, // ed: 0111 0100 1110 1101 + {DNE, "EA,DE" }, // ee: 0111 0100 1110 1110 + {DNE, "EA,HL" }, // ef: 0111 0100 1110 1111 - { }, // f0: 0100 1100 1111 0000 - { }, // f1: 0100 1100 1111 0001 - { }, // f2: 0100 1100 1111 0010 - { }, // f3: 0100 1100 1111 0011 - { }, // f4: 0100 1100 1111 0100 - { }, // f5: 0100 1100 1111 0101 - { }, // f6: 0100 1100 1111 0110 - { }, // f7: 0100 1100 1111 0111 - { }, // f8: 0100 1100 1111 1000 - { }, // f9: 0100 1100 1111 1001 - { }, // fa: 0100 1100 1111 1010 - { }, // fb: 0100 1100 1111 1011 - { }, // fc: 0100 1100 1111 1100 - { }, // fd: 0100 1100 1111 1101 - { }, // fe: 0100 1100 1111 1110 - { } // ff: 0100 1100 1111 1111 + {SBBW, "%a" }, // f0: 0111 0100 1111 0000 oooo oooo + { }, // f1: 0111 0100 1111 0001 + { }, // f2: 0111 0100 1111 0010 + { }, // f3: 0111 0100 1111 0011 + { }, // f4: 0111 0100 1111 0100 + {DSBB, "EA,BC" }, // f5: 0111 0100 1111 0101 + {DSBB, "EA,DE" }, // f6: 0111 0100 1111 0110 + {DSBB, "EA,HL" }, // f7: 0111 0100 1111 0111 + {EQAW, "%a" }, // f8: 0111 0100 1111 1000 oooo oooo + { }, // f9: 0111 0100 1111 1001 + { }, // fa: 0111 0100 1111 1010 + { }, // fb: 0111 0100 1111 1011 + { }, // fc: 0111 0100 1111 1100 + {DEQ, "EA,BC" }, // fd: 0111 0100 1111 1101 + {DEQ, "EA,DE" }, // fe: 0111 0100 1111 1110 + {DEQ, "EA,HL" } // ff: 0111 0100 1111 1111 }; -const dasm_s dasm_s::d4C_7807[256] = +// prefix 48 +const upd7810_base_disassembler::dasm_s upd7810_disassembler::d48_7810[256] = { - { }, // 00: 0100 1100 0000 0000 - { }, // 01: 0100 1100 0000 0001 - { }, // 02: 0100 1100 0000 0010 - { }, // 03: 0100 1100 0000 0011 - { }, // 04: 0100 1100 0000 0100 - { }, // 05: 0100 1100 0000 0101 - { }, // 06: 0100 1100 0000 0110 - { }, // 07: 0100 1100 0000 0111 - { }, // 08: 0100 1100 0000 1000 - { }, // 09: 0100 1100 0000 1001 - { }, // 0a: 0100 1100 0000 1010 - { }, // 0b: 0100 1100 0000 1011 - { }, // 0c: 0100 1100 0000 1100 - { }, // 0d: 0100 1100 0000 1101 - { }, // 0e: 0100 1100 0000 1110 - { }, // 0f: 0100 1100 0000 1111 + { }, // 00: 0100 1000 0000 0000 + {SLRC, "A" }, // 01: 0100 1000 0000 0001 + {SLRC, "B" }, // 02: 0100 1000 0000 0010 + {SLRC, "C" }, // 03: 0100 1000 0000 0011 + { }, // 04: 0100 1000 0000 0100 + {SLLC, "A" }, // 05: 0100 1000 0000 0101 + {SLLC, "B" }, // 06: 0100 1000 0000 0110 + {SLLC, "C" }, // 07: 0100 1000 0000 0111 + {SK, "NV" }, // 08: 0100 1000 0000 1000 + { }, // 09: 0100 1000 0000 1001 + {SK, "CY" }, // 0a: 0100 1000 0000 1010 + {SK, "HC" }, // 0b: 0100 1000 0000 1011 + {SK, "Z" }, // 0c: 0100 1000 0000 1100 + { }, // 0d: 0100 1000 0000 1101 + { }, // 0e: 0100 1000 0000 1110 + { }, // 0f: 0100 1000 0000 1111 - { }, // 10: 0100 1100 0001 0000 - { }, // 11: 0100 1100 0001 0001 - { }, // 12: 0100 1100 0001 0010 - { }, // 13: 0100 1100 0001 0011 - { }, // 14: 0100 1100 0001 0100 - { }, // 15: 0100 1100 0001 0101 - { }, // 16: 0100 1100 0001 0110 - { }, // 17: 0100 1100 0001 0111 - { }, // 18: 0100 1100 0001 1000 - { }, // 19: 0100 1100 0001 1001 - { }, // 1a: 0100 1100 0001 1010 - { }, // 1b: 0100 1100 0001 1011 - { }, // 1c: 0100 1100 0001 1100 - { }, // 1d: 0100 1100 0001 1101 - { }, // 1e: 0100 1100 0001 1110 - { }, // 1f: 0100 1100 0001 1111 + { }, // 10: 0100 1000 0001 0000 + { }, // 11: 0100 1000 0001 0001 + { }, // 12: 0100 1000 0001 0010 + { }, // 13: 0100 1000 0001 0011 + { }, // 14: 0100 1000 0001 0100 + { }, // 15: 0100 1000 0001 0101 + { }, // 16: 0100 1000 0001 0110 + { }, // 17: 0100 1000 0001 0111 + {SKN, "NV" }, // 18: 0100 1000 0001 1000 + { }, // 19: 0100 1000 0001 1001 + {SKN, "CY" }, // 1a: 0100 1000 0001 1010 + {SKN, "HC" }, // 1b: 0100 1000 0001 1011 + {SKN, "Z" }, // 1c: 0100 1000 0001 1100 + { }, // 1d: 0100 1000 0001 1101 + { }, // 1e: 0100 1000 0001 1110 + { }, // 1f: 0100 1000 0001 1111 - { }, // 20: 0100 1100 0010 0000 - { }, // 21: 0100 1100 0010 0001 - { }, // 22: 0100 1100 0010 0010 - { }, // 23: 0100 1100 0010 0011 - { }, // 24: 0100 1100 0010 0100 - { }, // 25: 0100 1100 0010 0101 - { }, // 26: 0100 1100 0010 0110 - { }, // 27: 0100 1100 0010 0111 - { }, // 28: 0100 1100 0010 1000 - { }, // 29: 0100 1100 0010 1001 - { }, // 2a: 0100 1100 0010 1010 - { }, // 2b: 0100 1100 0010 1011 - { }, // 2c: 0100 1100 0010 1100 - { }, // 2d: 0100 1100 0010 1101 - { }, // 2e: 0100 1100 0010 1110 - { }, // 2f: 0100 1100 0010 1111 + { }, // 20: 0100 1000 0010 0000 + {SLR, "A" }, // 21: 0100 1000 0010 0001 + {SLR, "B" }, // 22: 0100 1000 0010 0010 + {SLR, "C" }, // 23: 0100 1000 0010 0011 + { }, // 24: 0100 1000 0010 0100 + {SLL, "A" }, // 25: 0100 1000 0010 0101 + {SLL, "B" }, // 26: 0100 1000 0010 0110 + {SLL, "C" }, // 27: 0100 1000 0010 0111 + {JEA, nullptr }, // 28: 0100 1000 0010 1000 + {CALB,nullptr }, // 29: 0100 1000 0010 1001 + {CLC, nullptr }, // 2a: 0100 1000 0010 1010 + {STC, nullptr }, // 2b: 0100 1000 0010 1011 + { }, // 2c: 0100 1000 0010 1100 + {MUL, "A" }, // 2d: 0100 1000 0010 1101 + {MUL, "B" }, // 2e: 0100 1000 0010 1110 + {MUL, "C" }, // 2f: 0100 1000 0010 1111 - { }, // 30: 0100 1100 0011 0000 - { }, // 31: 0100 1100 0011 0001 - { }, // 32: 0100 1100 0011 0010 - { }, // 33: 0100 1100 0011 0011 - { }, // 34: 0100 1100 0011 0100 - { }, // 35: 0100 1100 0011 0101 - { }, // 36: 0100 1100 0011 0110 - { }, // 37: 0100 1100 0011 0111 - { }, // 38: 0100 1100 0011 1000 - { }, // 39: 0100 1100 0011 1001 - { }, // 3a: 0100 1100 0011 1010 - { }, // 3b: 0100 1100 0011 1011 - { }, // 3c: 0100 1100 0011 1100 - { }, // 3d: 0100 1100 0011 1101 - { }, // 3e: 0100 1100 0011 1110 - { }, // 3f: 0100 1100 0011 1111 + { }, // 30: 0100 1000 0011 0000 + {RLR, "A" }, // 31: 0100 1000 0011 0001 + {RLR, "B" }, // 32: 0100 1000 0011 0010 + {RLR, "C" }, // 33: 0100 1000 0011 0011 + { }, // 34: 0100 1000 0011 0100 + {RLL, "A" }, // 35: 0100 1000 0011 0101 + {RLL, "B" }, // 36: 0100 1000 0011 0110 + {RLL, "C" }, // 37: 0100 1000 0011 0111 + {RLD, nullptr }, // 38: 0100 1000 0011 1000 + {RRD, nullptr }, // 39: 0100 1000 0011 1001 + {NEGA, nullptr }, // 3a: 0100 1000 0011 1010 + {HALT, nullptr }, // 3b: 0100 1000 0011 1011 + { }, // 3c: 0100 1000 0011 1100 + {DIV, "A" }, // 3d: 0100 1000 0011 1101 + {DIV, "B" }, // 3e: 0100 1000 0011 1110 + {DIV, "C" }, // 3f: 0100 1000 0011 1111 - { }, // 40: 0100 1100 0100 0000 - { }, // 41: 0100 1100 0100 0001 - { }, // 42: 0100 1100 0100 0010 - { }, // 43: 0100 1100 0100 0011 - { }, // 44: 0100 1100 0100 0100 - { }, // 45: 0100 1100 0100 0101 - { }, // 46: 0100 1100 0100 0110 - { }, // 47: 0100 1100 0100 0111 - { }, // 48: 0100 1100 0100 1000 - { }, // 49: 0100 1100 0100 1001 - { }, // 4a: 0100 1100 0100 1010 - { }, // 4b: 0100 1100 0100 1011 - { }, // 4c: 0100 1100 0100 1100 - { }, // 4d: 0100 1100 0100 1101 - { }, // 4e: 0100 1100 0100 1110 - { }, // 4f: 0100 1100 0100 1111 + {SKIT, "NMI" }, // 40: 0100 1000 0100 0000 + {SKIT, "FT0" }, // 41: 0100 1000 0100 0001 + {SKIT, "FT1" }, // 42: 0100 1000 0100 0010 + {SKIT, "F1" }, // 43: 0100 1000 0100 0011 + {SKIT, "F2" }, // 44: 0100 1000 0100 0100 + {SKIT, "FE0" }, // 45: 0100 1000 0100 0101 + {SKIT, "FE1" }, // 46: 0100 1000 0100 0110 + {SKIT, "FEIN" }, // 47: 0100 1000 0100 0111 + {SKIT, "FAD" }, // 48: 0100 1000 0100 1000 + {SKIT, "FSR" }, // 49: 0100 1000 0100 1001 + {SKIT, "FST" }, // 4a: 0100 1000 0100 1010 + {SKIT, "ER" }, // 4b: 0100 1000 0100 1011 + {SKIT, "OV" }, // 4c: 0100 1000 0100 1100 + { }, // 4d: 0100 1000 0100 1101 + { }, // 4e: 0100 1000 0100 1110 + { }, // 4f: 0100 1000 0100 1111 - { }, // 50: 0100 1100 0101 0000 - { }, // 51: 0100 1100 0101 0001 - { }, // 52: 0100 1100 0101 0010 - { }, // 53: 0100 1100 0101 0011 - { }, // 54: 0100 1100 0101 0100 - { }, // 55: 0100 1100 0101 0101 - { }, // 56: 0100 1100 0101 0110 - { }, // 57: 0100 1100 0101 0111 - { }, // 58: 0100 1100 0101 1000 - { }, // 59: 0100 1100 0101 1001 - { }, // 5a: 0100 1100 0101 1010 - { }, // 5b: 0100 1100 0101 1011 - { }, // 5c: 0100 1100 0101 1100 - { }, // 5d: 0100 1100 0101 1101 - { }, // 5e: 0100 1100 0101 1110 - { }, // 5f: 0100 1100 0101 1111 + {SKIT, "AN4" }, // 50: 0100 1000 0101 0000 + {SKIT, "AN5" }, // 51: 0100 1000 0101 0001 + {SKIT, "AN6" }, // 52: 0100 1000 0101 0010 + {SKIT, "AN7" }, // 53: 0100 1000 0101 0011 + {SKIT, "SB" }, // 54: 0100 1000 0101 0100 + { }, // 55: 0100 1000 0101 0101 + { }, // 56: 0100 1000 0101 0110 + { }, // 57: 0100 1000 0101 0111 + { }, // 58: 0100 1000 0101 1000 + { }, // 59: 0100 1000 0101 1001 + { }, // 5a: 0100 1000 0101 1010 + { }, // 5b: 0100 1000 0101 1011 + { }, // 5c: 0100 1000 0101 1100 + { }, // 5d: 0100 1000 0101 1101 + { }, // 5e: 0100 1000 0101 1110 + { }, // 5f: 0100 1000 0101 1111 - { }, // 60: 0100 1100 0110 0000 - { }, // 61: 0100 1100 0110 0001 - { }, // 62: 0100 1100 0110 0010 - { }, // 63: 0100 1100 0110 0011 - { }, // 64: 0100 1100 0110 0100 - { }, // 65: 0100 1100 0110 0101 - { }, // 66: 0100 1100 0110 0110 - { }, // 67: 0100 1100 0110 0111 - { }, // 68: 0100 1100 0110 1000 - { }, // 69: 0100 1100 0110 1001 - { }, // 6a: 0100 1100 0110 1010 - { }, // 6b: 0100 1100 0110 1011 - { }, // 6c: 0100 1100 0110 1100 - { }, // 6d: 0100 1100 0110 1101 - { }, // 6e: 0100 1100 0110 1110 - { }, // 6f: 0100 1100 0110 1111 + {SKNIT, "NMI" }, // 60: 0100 1000 0110 0000 + {SKNIT, "FT0" }, // 61: 0100 1000 0110 0001 + {SKNIT, "FT1" }, // 62: 0100 1000 0110 0010 + {SKNIT, "F1" }, // 63: 0100 1000 0110 0011 + {SKNIT, "F2" }, // 64: 0100 1000 0110 0100 + {SKNIT, "FE0" }, // 65: 0100 1000 0110 0101 + {SKNIT, "FE1" }, // 66: 0100 1000 0110 0110 + {SKNIT, "FEIN" }, // 67: 0100 1000 0110 0111 + {SKNIT, "FAD" }, // 68: 0100 1000 0110 1000 + {SKNIT, "FSR" }, // 69: 0100 1000 0110 1001 + {SKNIT, "FST" }, // 6a: 0100 1000 0110 1010 + {SKNIT, "ER" }, // 6b: 0100 1000 0110 1011 + {SKNIT, "OV" }, // 6c: 0100 1000 0110 1100 + { }, // 6d: 0100 1000 0110 1101 + { }, // 6e: 0100 1000 0110 1110 + { }, // 6f: 0100 1000 0110 1111 - { }, // 70: 0100 1100 0111 0000 - { }, // 71: 0100 1100 0111 0001 - { }, // 72: 0100 1100 0111 0010 - { }, // 73: 0100 1100 0111 0011 - { }, // 74: 0100 1100 0111 0100 - { }, // 75: 0100 1100 0111 0101 - { }, // 76: 0100 1100 0111 0110 - { }, // 77: 0100 1100 0111 0111 - { }, // 78: 0100 1100 0111 1000 - { }, // 79: 0100 1100 0111 1001 - { }, // 7a: 0100 1100 0111 1010 - { }, // 7b: 0100 1100 0111 1011 - { }, // 7c: 0100 1100 0111 1100 - { }, // 7d: 0100 1100 0111 1101 - { }, // 7e: 0100 1100 0111 1110 - { }, // 7f: 0100 1100 0111 1111 + {SKNIT, "AN4" }, // 70: 0100 1000 0111 0000 + {SKNIT, "AN5" }, // 71: 0100 1000 0111 0001 + {SKNIT, "AN6" }, // 72: 0100 1000 0111 0010 + {SKNIT, "AN7" }, // 73: 0100 1000 0111 0011 + {SKNIT, "SB" }, // 74: 0100 1000 0111 0100 + { }, // 75: 0100 1000 0111 0101 + { }, // 76: 0100 1000 0111 0110 + { }, // 77: 0100 1000 0111 0111 + { }, // 78: 0100 1000 0111 1000 + { }, // 79: 0100 1000 0111 1001 + { }, // 7a: 0100 1000 0111 1010 + { }, // 7b: 0100 1000 0111 1011 + { }, // 7c: 0100 1000 0111 1100 + { }, // 7d: 0100 1000 0111 1101 + { }, // 7e: 0100 1000 0111 1110 + { }, // 7f: 0100 1000 0111 1111 - { }, // 80: 0100 1100 1000 0000 - { }, // 81: 0100 1100 1000 0001 - { }, // 82: 0100 1100 1000 0010 - { }, // 83: 0100 1100 1000 0011 - { }, // 84: 0100 1100 1000 0100 - { }, // 85: 0100 1100 1000 0101 - { }, // 86: 0100 1100 1000 0110 - { }, // 87: 0100 1100 1000 0111 - { }, // 88: 0100 1100 1000 1000 - { }, // 89: 0100 1100 1000 1001 - { }, // 8a: 0100 1100 1000 1010 - { }, // 8b: 0100 1100 1000 1011 - { }, // 8c: 0100 1100 1000 1100 - { }, // 8d: 0100 1100 1000 1101 - { }, // 8e: 0100 1100 1000 1110 - { }, // 8f: 0100 1100 1000 1111 + { }, // 80: 0100 1000 1000 0000 + { }, // 81: 0100 1000 1000 0001 + {LDEAX, "(DE)" }, // 82: 0100 1000 1000 0010 + {LDEAX, "(HL)" }, // 83: 0100 1000 1000 0011 + {LDEAX, "(DE++)" }, // 84: 0100 1000 1000 0100 + {LDEAX, "(HL++)" }, // 85: 0100 1000 1000 0101 + { }, // 86: 0100 1000 1000 0110 + { }, // 87: 0100 1000 1000 0111 + { }, // 88: 0100 1000 1000 1000 + { }, // 89: 0100 1000 1000 1001 + { }, // 8a: 0100 1000 1000 1010 + {LDEAX, "(DE+%b)" }, // 8b: 0100 1000 1000 1011 xxxx xxxx + {LDEAX, "(HL+A)" }, // 8c: 0100 1000 1000 1100 + {LDEAX, "(HL+B)" }, // 8d: 0100 1000 1000 1101 + {LDEAX, "(HL+EA)" }, // 8e: 0100 1000 1000 1110 + {LDEAX, "(HL+%b)" }, // 8f: 0100 1000 1000 1111 xxxx xxxx - { }, // 90: 0100 1100 1001 0000 - { }, // 91: 0100 1100 1001 0001 - { }, // 92: 0100 1100 1001 0010 - { }, // 93: 0100 1100 1001 0011 - { }, // 94: 0100 1100 1001 0100 - { }, // 95: 0100 1100 1001 0101 - { }, // 96: 0100 1100 1001 0110 - { }, // 97: 0100 1100 1001 0111 - { }, // 98: 0100 1100 1001 1000 - { }, // 99: 0100 1100 1001 1001 - { }, // 9a: 0100 1100 1001 1010 - { }, // 9b: 0100 1100 1001 1011 - { }, // 9c: 0100 1100 1001 1100 - { }, // 9d: 0100 1100 1001 1101 - { }, // 9e: 0100 1100 1001 1110 - { }, // 9f: 0100 1100 1001 1111 + { }, // 90: 0100 1000 1000 0000 + { }, // 91: 0100 1000 1000 0001 + {STEAX, "(DE)" }, // 92: 0100 1000 1000 0010 + {STEAX, "(HL)" }, // 93: 0100 1000 1000 0011 + {STEAX, "(DE++)" }, // 94: 0100 1000 1000 0100 + {STEAX, "(HL++)" }, // 95: 0100 1000 1000 0101 + { }, // 96: 0100 1000 1000 0110 + { }, // 97: 0100 1000 1000 0111 + { }, // 98: 0100 1000 1000 1000 + { }, // 99: 0100 1000 1000 1001 + { }, // 9a: 0100 1000 1000 1010 + {STEAX, "(DE+%b)" }, // 9b: 0100 1000 1000 1011 xxxx xxxx + {STEAX, "(HL+A)" }, // 9c: 0100 1000 1000 1100 + {STEAX, "(HL+B)" }, // 9d: 0100 1000 1000 1101 + {STEAX, "(HL+EA)" }, // 9e: 0100 1000 1000 1110 + {STEAX, "(HL+%b)" }, // 9f: 0100 1000 1000 1111 xxxx xxxx - { }, // a0: 0100 1100 1010 0000 - { }, // a1: 0100 1100 1010 0001 - { }, // a2: 0100 1100 1010 0010 - { }, // a3: 0100 1100 1010 0011 - { }, // a4: 0100 1100 1010 0100 - { }, // a5: 0100 1100 1010 0101 - { }, // a6: 0100 1100 1010 0110 - { }, // a7: 0100 1100 1010 0111 - { }, // a8: 0100 1100 1010 1000 - { }, // a9: 0100 1100 1010 1001 - { }, // aa: 0100 1100 1010 1010 - { }, // ab: 0100 1100 1010 1011 - { }, // ac: 0100 1100 1010 1100 - { }, // ad: 0100 1100 1010 1101 - { }, // ae: 0100 1100 1010 1110 - { }, // af: 0100 1100 1010 1111 + {DSLR, "EA" }, // a0: 0100 1000 1010 0000 + { }, // a1: 0100 1000 1010 0001 + { }, // a2: 0100 1000 1010 0010 + { }, // a3: 0100 1000 1010 0011 + {DSLL, "EA" }, // a4: 0100 1000 1010 0100 + { }, // a5: 0100 1000 1010 0101 + { }, // a6: 0100 1000 1010 0110 + { }, // a7: 0100 1000 1010 0111 + {TABLE, nullptr }, // a8: 0100 1000 1010 1000 + { }, // a9: 0100 1000 1010 1001 + { }, // aa: 0100 1000 1010 1010 + { }, // ab: 0100 1000 1010 1011 + { }, // ac: 0100 1000 1010 1100 + { }, // ad: 0100 1000 1010 1101 + { }, // ae: 0100 1000 1010 1110 + { }, // af: 0100 1000 1010 1111 - { }, // b0: 0100 1100 1011 0000 - { }, // b1: 0100 1100 1011 0001 - { }, // b2: 0100 1100 1011 0010 - { }, // b3: 0100 1100 1011 0011 - { }, // b4: 0100 1100 1011 0100 - { }, // b5: 0100 1100 1011 0101 - { }, // b6: 0100 1100 1011 0110 - { }, // b7: 0100 1100 1011 0111 - { }, // b8: 0100 1100 1011 1000 - { }, // b9: 0100 1100 1011 1001 - { }, // ba: 0100 1100 1011 1010 - { }, // bb: 0100 1100 1011 1011 - { }, // bc: 0100 1100 1011 1100 - { }, // bd: 0100 1100 1011 1101 - { }, // be: 0100 1100 1011 1110 - { }, // bf: 0100 1100 1011 1111 + {DRLR, "EA" }, // b0: 0100 1000 1011 0000 + { }, // b1: 0100 1000 1011 0001 + { }, // b2: 0100 1000 1011 0010 + { }, // b3: 0100 1000 1011 0011 + {DRLL, "EA" }, // b4: 0100 1000 1011 0100 + { }, // b5: 0100 1000 1011 0101 + { }, // b6: 0100 1000 1011 0110 + { }, // b7: 0100 1000 1011 0111 + { }, // b8: 0100 1000 1011 1000 + { }, // b9: 0100 1000 1011 1001 + { }, // ba: 0100 1000 1011 1010 + {STOP, nullptr }, // bb: 0100 1000 1011 1011 7810 + { }, // bc: 0100 1000 1011 1100 + { }, // bd: 0100 1000 1011 1101 + { }, // be: 0100 1000 1011 1110 + { }, // bf: 0100 1000 1011 1111 - {MOV, "A,PA" }, // c0: 0100 1100 1100 0000 - {MOV, "A,PB" }, // c1: 0100 1100 1100 0001 - {MOV, "A,PC" }, // c2: 0100 1100 1100 0010 - {MOV, "A,PD" }, // c3: 0100 1100 1100 0011 - { }, // c4: 0100 1100 1100 0100 - {MOV, "A,PF" }, // c5: 0100 1100 1100 0101 - {MOV, "A,MKH" }, // c6: 0100 1100 1100 0110 - {MOV, "A,MKL" }, // c7: 0100 1100 1100 0111 - { }, // c8: 0100 1100 1100 1000 - {MOV, "A,SMH" }, // c9: 0100 1100 1100 1001 - { }, // ca: 0100 1100 1100 1010 - {MOV, "A,EOM" }, // cb: 0100 1100 1100 1011 - { }, // cc: 0100 1100 1100 1100 - {MOV, "A,TMM" }, // cd: 0100 1100 1100 1101 - {MOV, "A,PT" }, // ce: 0100 1100 1100 1110 7807 - { }, // cf: 0100 1100 1100 1111 + {DMOV, "EA,ECNT" }, // c0: 0100 1000 1100 0000 + {DMOV, "EA,ECPT" }, // c1: 0100 1000 1100 0001 7810 + { }, // c2: 0100 1000 1100 0010 + { }, // c3: 0100 1000 1100 0011 + { }, // c4: 0100 1000 1100 0100 + { }, // c5: 0100 1000 1100 0101 + { }, // c6: 0100 1000 1100 0110 + { }, // c7: 0100 1000 1100 0111 + { }, // c8: 0100 1000 1100 1000 + { }, // c9: 0100 1000 1100 1001 + { }, // ca: 0100 1000 1100 1010 + { }, // cb: 0100 1000 1100 1011 + { }, // cc: 0100 1000 1100 1100 + { }, // cd: 0100 1000 1100 1101 + { }, // ce: 0100 1000 1100 1110 + { }, // cf: 0100 1000 1100 1111 - { }, // d0: 0100 1100 1101 0000 - { }, // d1: 0100 1100 1101 0001 - { }, // d2: 0100 1100 1101 0010 - { }, // d3: 0100 1100 1101 0011 - { }, // d4: 0100 1100 1101 0100 - { }, // d5: 0100 1100 1101 0101 - { }, // d6: 0100 1100 1101 0110 - { }, // d7: 0100 1100 1101 0111 - { }, // d8: 0100 1100 1101 1000 - {MOV, "A,RXB" }, // d9: 0100 1100 1101 1001 - { }, // da: 0100 1100 1101 1010 - { }, // db: 0100 1100 1101 1011 - { }, // dc: 0100 1100 1101 1100 - { }, // dd: 0100 1100 1101 1101 - { }, // de: 0100 1100 1101 1110 - { }, // df: 0100 1100 1101 1111 + { }, // d0: 0100 1000 1101 0000 + { }, // d1: 0100 1000 1101 0001 + {DMOV, "ETM0,EA" }, // d2: 0100 1000 1101 0010 + {DMOV, "ETM1,EA" }, // d3: 0100 1000 1101 0011 + { }, // d4: 0100 1000 1101 0100 + { }, // d5: 0100 1000 1101 0101 + { }, // d6: 0100 1000 1101 0110 + { }, // d7: 0100 1000 1101 0111 + { }, // d8: 0100 1000 1101 1000 + { }, // d9: 0100 1000 1101 1001 + { }, // da: 0100 1000 1101 1010 + { }, // db: 0100 1000 1101 1011 + { }, // dc: 0100 1000 1101 1100 + { }, // dd: 0100 1000 1101 1101 + { }, // de: 0100 1000 1101 1110 + { }, // df: 0100 1000 1101 1111 - { }, // e0: 0100 1100 1110 0000 - { }, // e1: 0100 1100 1110 0001 - { }, // e2: 0100 1100 1110 0010 - { }, // e3: 0100 1100 1110 0011 - { }, // e4: 0100 1100 1110 0100 - { }, // e5: 0100 1100 1110 0101 - { }, // e6: 0100 1100 1110 0110 - { }, // e7: 0100 1100 1110 0111 - { }, // e8: 0100 1100 1110 1000 - { }, // e9: 0100 1100 1110 1001 - { }, // ea: 0100 1100 1110 1010 - { }, // eb: 0100 1100 1110 1011 - { }, // ec: 0100 1100 1110 1100 - { }, // ed: 0100 1100 1110 1101 - { }, // ee: 0100 1100 1110 1110 - { }, // ef: 0100 1100 1110 1111 + { }, // e0: 0100 1000 1110 0000 + { }, // e1: 0100 1000 1110 0001 + { }, // e2: 0100 1000 1110 0010 + { }, // e3: 0100 1000 1110 0011 + { }, // e4: 0100 1000 1110 0100 + { }, // e5: 0100 1000 1110 0101 + { }, // e6: 0100 1000 1110 0110 + { }, // e7: 0100 1000 1110 0111 + { }, // e8: 0100 1000 1110 1000 + { }, // e9: 0100 1000 1110 1001 + { }, // ea: 0100 1000 1110 1010 + { }, // eb: 0100 1000 1110 1011 + { }, // ec: 0100 1000 1110 1100 + { }, // ed: 0100 1000 1110 1101 + { }, // ee: 0100 1000 1110 1110 + { }, // ef: 0100 1000 1110 1111 - { }, // f0: 0100 1100 1111 0000 - { }, // f1: 0100 1100 1111 0001 - { }, // f2: 0100 1100 1111 0010 - { }, // f3: 0100 1100 1111 0011 - { }, // f4: 0100 1100 1111 0100 - { }, // f5: 0100 1100 1111 0101 - { }, // f6: 0100 1100 1111 0110 - { }, // f7: 0100 1100 1111 0111 - { }, // f8: 0100 1100 1111 1000 - { }, // f9: 0100 1100 1111 1001 - { }, // fa: 0100 1100 1111 1010 - { }, // fb: 0100 1100 1111 1011 - { }, // fc: 0100 1100 1111 1100 - { }, // fd: 0100 1100 1111 1101 - { }, // fe: 0100 1100 1111 1110 - { } // ff: 0100 1100 1111 1111 + { }, // f0: 0100 1000 1111 0000 + { }, // f1: 0100 1000 1111 0001 + { }, // f2: 0100 1000 1111 0010 + { }, // f3: 0100 1000 1111 0011 + { }, // f4: 0100 1000 1111 0100 + { }, // f5: 0100 1000 1111 0101 + { }, // f6: 0100 1000 1111 0110 + { }, // f7: 0100 1000 1111 0111 + { }, // f8: 0100 1000 1111 1000 + { }, // f9: 0100 1000 1111 1001 + { }, // fa: 0100 1000 1111 1010 + { }, // fb: 0100 1000 1111 1011 + { }, // fc: 0100 1000 1111 1100 + { }, // fd: 0100 1000 1111 1101 + { }, // fe: 0100 1000 1111 1110 + { } // ff: 0100 1000 1111 1111 }; -// prefix 4D -const dasm_s dasm_s::d4D_7810[256] = +// prefix 4C +const upd7810_base_disassembler::dasm_s upd7810_disassembler::d4C_7810[256] = { - { }, // 00: 0100 1101 0000 0000 - { }, // 01: 0100 1101 0000 0001 - { }, // 02: 0100 1101 0000 0010 - { }, // 03: 0100 1101 0000 0011 - { }, // 04: 0100 1101 0000 0100 - { }, // 05: 0100 1101 0000 0101 - { }, // 06: 0100 1101 0000 0110 - { }, // 07: 0100 1101 0000 0111 - { }, // 08: 0100 1101 0000 1000 - { }, // 09: 0100 1101 0000 1001 - { }, // 0a: 0100 1101 0000 1010 - { }, // 0b: 0100 1101 0000 1011 - { }, // 0c: 0100 1101 0000 1100 - { }, // 0d: 0100 1101 0000 1101 - { }, // 0e: 0100 1101 0000 1110 - { }, // 0f: 0100 1101 0000 1111 + { }, // 00: 0100 1100 0000 0000 + { }, // 01: 0100 1100 0000 0001 + { }, // 02: 0100 1100 0000 0010 + { }, // 03: 0100 1100 0000 0011 + { }, // 04: 0100 1100 0000 0100 + { }, // 05: 0100 1100 0000 0101 + { }, // 06: 0100 1100 0000 0110 + { }, // 07: 0100 1100 0000 0111 + { }, // 08: 0100 1100 0000 1000 + { }, // 09: 0100 1100 0000 1001 + { }, // 0a: 0100 1100 0000 1010 + { }, // 0b: 0100 1100 0000 1011 + { }, // 0c: 0100 1100 0000 1100 + { }, // 0d: 0100 1100 0000 1101 + { }, // 0e: 0100 1100 0000 1110 + { }, // 0f: 0100 1100 0000 1111 - { }, // 10: 0100 1101 0001 0000 - { }, // 11: 0100 1101 0001 0001 - { }, // 12: 0100 1101 0001 0010 - { }, // 13: 0100 1101 0001 0011 - { }, // 14: 0100 1101 0001 0100 - { }, // 15: 0100 1101 0001 0101 - { }, // 16: 0100 1101 0001 0110 - { }, // 17: 0100 1101 0001 0111 - { }, // 18: 0100 1101 0001 1000 - { }, // 19: 0100 1101 0001 1001 - { }, // 1a: 0100 1101 0001 1010 - { }, // 1b: 0100 1101 0001 1011 - { }, // 1c: 0100 1101 0001 1100 - { }, // 1d: 0100 1101 0001 1101 - { }, // 1e: 0100 1101 0001 1110 - { }, // 1f: 0100 1101 0001 1111 + { }, // 10: 0100 1100 0001 0000 + { }, // 11: 0100 1100 0001 0001 + { }, // 12: 0100 1100 0001 0010 + { }, // 13: 0100 1100 0001 0011 + { }, // 14: 0100 1100 0001 0100 + { }, // 15: 0100 1100 0001 0101 + { }, // 16: 0100 1100 0001 0110 + { }, // 17: 0100 1100 0001 0111 + { }, // 18: 0100 1100 0001 1000 + { }, // 19: 0100 1100 0001 1001 + { }, // 1a: 0100 1100 0001 1010 + { }, // 1b: 0100 1100 0001 1011 + { }, // 1c: 0100 1100 0001 1100 + { }, // 1d: 0100 1100 0001 1101 + { }, // 1e: 0100 1100 0001 1110 + { }, // 1f: 0100 1100 0001 1111 - { }, // 20: 0100 1101 0010 0000 - { }, // 21: 0100 1101 0010 0001 - { }, // 22: 0100 1101 0010 0010 - { }, // 23: 0100 1101 0010 0011 - { }, // 24: 0100 1101 0010 0100 - { }, // 25: 0100 1101 0010 0101 - { }, // 26: 0100 1101 0010 0110 - { }, // 27: 0100 1101 0010 0111 - { }, // 28: 0100 1101 0010 1000 - { }, // 29: 0100 1101 0010 1001 - { }, // 2a: 0100 1101 0010 1010 - { }, // 2b: 0100 1101 0010 1011 - { }, // 2c: 0100 1101 0010 1100 - { }, // 2d: 0100 1101 0010 1101 - { }, // 2e: 0100 1101 0010 1110 - { }, // 2f: 0100 1101 0010 1111 + { }, // 20: 0100 1100 0010 0000 + { }, // 21: 0100 1100 0010 0001 + { }, // 22: 0100 1100 0010 0010 + { }, // 23: 0100 1100 0010 0011 + { }, // 24: 0100 1100 0010 0100 + { }, // 25: 0100 1100 0010 0101 + { }, // 26: 0100 1100 0010 0110 + { }, // 27: 0100 1100 0010 0111 + { }, // 28: 0100 1100 0010 1000 + { }, // 29: 0100 1100 0010 1001 + { }, // 2a: 0100 1100 0010 1010 + { }, // 2b: 0100 1100 0010 1011 + { }, // 2c: 0100 1100 0010 1100 + { }, // 2d: 0100 1100 0010 1101 + { }, // 2e: 0100 1100 0010 1110 + { }, // 2f: 0100 1100 0010 1111 - { }, // 30: 0100 1101 0011 0000 - { }, // 31: 0100 1101 0011 0001 - { }, // 32: 0100 1101 0011 0010 - { }, // 33: 0100 1101 0011 0011 - { }, // 34: 0100 1101 0011 0100 - { }, // 35: 0100 1101 0011 0101 - { }, // 36: 0100 1101 0011 0110 - { }, // 37: 0100 1101 0011 0111 - { }, // 38: 0100 1101 0011 1000 - { }, // 39: 0100 1101 0011 1001 - { }, // 3a: 0100 1101 0011 1010 - { }, // 3b: 0100 1101 0011 1011 - { }, // 3c: 0100 1101 0011 1100 - { }, // 3d: 0100 1101 0011 1101 - { }, // 3e: 0100 1101 0011 1110 - { }, // 3f: 0100 1101 0011 1111 + { }, // 30: 0100 1100 0011 0000 + { }, // 31: 0100 1100 0011 0001 + { }, // 32: 0100 1100 0011 0010 + { }, // 33: 0100 1100 0011 0011 + { }, // 34: 0100 1100 0011 0100 + { }, // 35: 0100 1100 0011 0101 + { }, // 36: 0100 1100 0011 0110 + { }, // 37: 0100 1100 0011 0111 + { }, // 38: 0100 1100 0011 1000 + { }, // 39: 0100 1100 0011 1001 + { }, // 3a: 0100 1100 0011 1010 + { }, // 3b: 0100 1100 0011 1011 + { }, // 3c: 0100 1100 0011 1100 + { }, // 3d: 0100 1100 0011 1101 + { }, // 3e: 0100 1100 0011 1110 + { }, // 3f: 0100 1100 0011 1111 - { }, // 40: 0100 1101 0100 0000 - { }, // 41: 0100 1101 0100 0001 - { }, // 42: 0100 1101 0100 0010 - { }, // 43: 0100 1101 0100 0011 - { }, // 44: 0100 1101 0100 0100 - { }, // 45: 0100 1101 0100 0101 - { }, // 46: 0100 1101 0100 0110 - { }, // 47: 0100 1101 0100 0111 - { }, // 48: 0100 1101 0100 1000 - { }, // 49: 0100 1101 0100 1001 - { }, // 4a: 0100 1101 0100 1010 - { }, // 4b: 0100 1101 0100 1011 - { }, // 4c: 0100 1101 0100 1100 - { }, // 4d: 0100 1101 0100 1101 - { }, // 4e: 0100 1101 0100 1110 - { }, // 4f: 0100 1101 0100 1111 + { }, // 40: 0100 1100 0100 0000 + { }, // 41: 0100 1100 0100 0001 + { }, // 42: 0100 1100 0100 0010 + { }, // 43: 0100 1100 0100 0011 + { }, // 44: 0100 1100 0100 0100 + { }, // 45: 0100 1100 0100 0101 + { }, // 46: 0100 1100 0100 0110 + { }, // 47: 0100 1100 0100 0111 + { }, // 48: 0100 1100 0100 1000 + { }, // 49: 0100 1100 0100 1001 + { }, // 4a: 0100 1100 0100 1010 + { }, // 4b: 0100 1100 0100 1011 + { }, // 4c: 0100 1100 0100 1100 + { }, // 4d: 0100 1100 0100 1101 + { }, // 4e: 0100 1100 0100 1110 + { }, // 4f: 0100 1100 0100 1111 - { }, // 50: 0100 1101 0101 0000 - { }, // 51: 0100 1101 0101 0001 - { }, // 52: 0100 1101 0101 0010 - { }, // 53: 0100 1101 0101 0011 - { }, // 54: 0100 1101 0101 0100 - { }, // 55: 0100 1101 0101 0101 - { }, // 56: 0100 1101 0101 0110 - { }, // 57: 0100 1101 0101 0111 - { }, // 58: 0100 1101 0101 1000 - { }, // 59: 0100 1101 0101 1001 - { }, // 5a: 0100 1101 0101 1010 - { }, // 5b: 0100 1101 0101 1011 - { }, // 5c: 0100 1101 0101 1100 - { }, // 5d: 0100 1101 0101 1101 - { }, // 5e: 0100 1101 0101 1110 - { }, // 5f: 0100 1101 0101 1111 + { }, // 50: 0100 1100 0101 0000 + { }, // 51: 0100 1100 0101 0001 + { }, // 52: 0100 1100 0101 0010 + { }, // 53: 0100 1100 0101 0011 + { }, // 54: 0100 1100 0101 0100 + { }, // 55: 0100 1100 0101 0101 + { }, // 56: 0100 1100 0101 0110 + { }, // 57: 0100 1100 0101 0111 + { }, // 58: 0100 1100 0101 1000 + { }, // 59: 0100 1100 0101 1001 + { }, // 5a: 0100 1100 0101 1010 + { }, // 5b: 0100 1100 0101 1011 + { }, // 5c: 0100 1100 0101 1100 + { }, // 5d: 0100 1100 0101 1101 + { }, // 5e: 0100 1100 0101 1110 + { }, // 5f: 0100 1100 0101 1111 - { }, // 60: 0100 1101 0110 0000 - { }, // 61: 0100 1101 0110 0001 - { }, // 62: 0100 1101 0110 0010 - { }, // 63: 0100 1101 0110 0011 - { }, // 64: 0100 1101 0110 0100 - { }, // 65: 0100 1101 0110 0101 - { }, // 66: 0100 1101 0110 0110 - { }, // 67: 0100 1101 0110 0111 - { }, // 68: 0100 1101 0110 1000 - { }, // 69: 0100 1101 0110 1001 - { }, // 6a: 0100 1101 0110 1010 - { }, // 6b: 0100 1101 0110 1011 - { }, // 6c: 0100 1101 0110 1100 - { }, // 6d: 0100 1101 0110 1101 - { }, // 6e: 0100 1101 0110 1110 - { }, // 6f: 0100 1101 0110 1111 + { }, // 60: 0100 1100 0110 0000 + { }, // 61: 0100 1100 0110 0001 + { }, // 62: 0100 1100 0110 0010 + { }, // 63: 0100 1100 0110 0011 + { }, // 64: 0100 1100 0110 0100 + { }, // 65: 0100 1100 0110 0101 + { }, // 66: 0100 1100 0110 0110 + { }, // 67: 0100 1100 0110 0111 + { }, // 68: 0100 1100 0110 1000 + { }, // 69: 0100 1100 0110 1001 + { }, // 6a: 0100 1100 0110 1010 + { }, // 6b: 0100 1100 0110 1011 + { }, // 6c: 0100 1100 0110 1100 + { }, // 6d: 0100 1100 0110 1101 + { }, // 6e: 0100 1100 0110 1110 + { }, // 6f: 0100 1100 0110 1111 - { }, // 70: 0100 1101 0111 0000 - { }, // 71: 0100 1101 0111 0001 - { }, // 72: 0100 1101 0111 0010 - { }, // 73: 0100 1101 0111 0011 - { }, // 74: 0100 1101 0111 0100 - { }, // 75: 0100 1101 0111 0101 - { }, // 76: 0100 1101 0111 0110 - { }, // 77: 0100 1101 0111 0111 - { }, // 78: 0100 1101 0111 1000 - { }, // 79: 0100 1101 0111 1001 - { }, // 7a: 0100 1101 0111 1010 - { }, // 7b: 0100 1101 0111 1011 - { }, // 7c: 0100 1101 0111 1100 - { }, // 7d: 0100 1101 0111 1101 - { }, // 7e: 0100 1101 0111 1110 - { }, // 7f: 0100 1101 0111 1111 + { }, // 70: 0100 1100 0111 0000 + { }, // 71: 0100 1100 0111 0001 + { }, // 72: 0100 1100 0111 0010 + { }, // 73: 0100 1100 0111 0011 + { }, // 74: 0100 1100 0111 0100 + { }, // 75: 0100 1100 0111 0101 + { }, // 76: 0100 1100 0111 0110 + { }, // 77: 0100 1100 0111 0111 + { }, // 78: 0100 1100 0111 1000 + { }, // 79: 0100 1100 0111 1001 + { }, // 7a: 0100 1100 0111 1010 + { }, // 7b: 0100 1100 0111 1011 + { }, // 7c: 0100 1100 0111 1100 + { }, // 7d: 0100 1100 0111 1101 + { }, // 7e: 0100 1100 0111 1110 + { }, // 7f: 0100 1100 0111 1111 - { }, // 80: 0100 1101 1000 0000 - { }, // 81: 0100 1101 1000 0001 - { }, // 82: 0100 1101 1000 0010 - { }, // 83: 0100 1101 1000 0011 - { }, // 84: 0100 1101 1000 0100 - { }, // 85: 0100 1101 1000 0101 - { }, // 86: 0100 1101 1000 0110 - { }, // 87: 0100 1101 1000 0111 - { }, // 88: 0100 1101 1000 1000 - { }, // 89: 0100 1101 1000 1001 - { }, // 8a: 0100 1101 1000 1010 - { }, // 8b: 0100 1101 1000 1011 - { }, // 8c: 0100 1101 1000 1100 - { }, // 8d: 0100 1101 1000 1101 - { }, // 8e: 0100 1101 1000 1110 - { }, // 8f: 0100 1101 1000 1111 + { }, // 80: 0100 1100 1000 0000 + { }, // 81: 0100 1100 1000 0001 + { }, // 82: 0100 1100 1000 0010 + { }, // 83: 0100 1100 1000 0011 + { }, // 84: 0100 1100 1000 0100 + { }, // 85: 0100 1100 1000 0101 + { }, // 86: 0100 1100 1000 0110 + { }, // 87: 0100 1100 1000 0111 + { }, // 88: 0100 1100 1000 1000 + { }, // 89: 0100 1100 1000 1001 + { }, // 8a: 0100 1100 1000 1010 + { }, // 8b: 0100 1100 1000 1011 + { }, // 8c: 0100 1100 1000 1100 + { }, // 8d: 0100 1100 1000 1101 + { }, // 8e: 0100 1100 1000 1110 + { }, // 8f: 0100 1100 1000 1111 - { }, // 90: 0100 1101 1001 0000 - { }, // 91: 0100 1101 1001 0001 - { }, // 92: 0100 1101 1001 0010 - { }, // 93: 0100 1101 1001 0011 - { }, // 94: 0100 1101 1001 0100 - { }, // 95: 0100 1101 1001 0101 - { }, // 96: 0100 1101 1001 0110 - { }, // 97: 0100 1101 1001 0111 - { }, // 98: 0100 1101 1001 1000 - { }, // 99: 0100 1101 1001 1001 - { }, // 9a: 0100 1101 1001 1010 - { }, // 9b: 0100 1101 1001 1011 - { }, // 9c: 0100 1101 1001 1100 - { }, // 9d: 0100 1101 1001 1101 - { }, // 9e: 0100 1101 1001 1110 - { }, // 9f: 0100 1101 1001 1111 + { }, // 90: 0100 1100 1001 0000 + { }, // 91: 0100 1100 1001 0001 + { }, // 92: 0100 1100 1001 0010 + { }, // 93: 0100 1100 1001 0011 + { }, // 94: 0100 1100 1001 0100 + { }, // 95: 0100 1100 1001 0101 + { }, // 96: 0100 1100 1001 0110 + { }, // 97: 0100 1100 1001 0111 + { }, // 98: 0100 1100 1001 1000 + { }, // 99: 0100 1100 1001 1001 + { }, // 9a: 0100 1100 1001 1010 + { }, // 9b: 0100 1100 1001 1011 + { }, // 9c: 0100 1100 1001 1100 + { }, // 9d: 0100 1100 1001 1101 + { }, // 9e: 0100 1100 1001 1110 + { }, // 9f: 0100 1100 1001 1111 - { }, // a0: 0100 1101 1010 0000 - { }, // a1: 0100 1101 1010 0001 - { }, // a2: 0100 1101 1010 0010 - { }, // a3: 0100 1101 1010 0011 - { }, // a4: 0100 1101 1010 0100 - { }, // a5: 0100 1101 1010 0101 - { }, // a6: 0100 1101 1010 0110 - { }, // a7: 0100 1101 1010 0111 - { }, // a8: 0100 1101 1010 1000 - { }, // a9: 0100 1101 1010 1001 - { }, // aa: 0100 1101 1010 1010 - { }, // ab: 0100 1101 1010 1011 - { }, // ac: 0100 1101 1010 1100 - { }, // ad: 0100 1101 1010 1101 - { }, // ae: 0100 1101 1010 1110 - { }, // af: 0100 1101 1010 1111 + { }, // a0: 0100 1100 1010 0000 + { }, // a1: 0100 1100 1010 0001 + { }, // a2: 0100 1100 1010 0010 + { }, // a3: 0100 1100 1010 0011 + { }, // a4: 0100 1100 1010 0100 + { }, // a5: 0100 1100 1010 0101 + { }, // a6: 0100 1100 1010 0110 + { }, // a7: 0100 1100 1010 0111 + { }, // a8: 0100 1100 1010 1000 + { }, // a9: 0100 1100 1010 1001 + { }, // aa: 0100 1100 1010 1010 + { }, // ab: 0100 1100 1010 1011 + { }, // ac: 0100 1100 1010 1100 + { }, // ad: 0100 1100 1010 1101 + { }, // ae: 0100 1100 1010 1110 + { }, // af: 0100 1100 1010 1111 - { }, // b0: 0100 1101 1011 0000 - { }, // b1: 0100 1101 1011 0001 - { }, // b2: 0100 1101 1011 0010 - { }, // b3: 0100 1101 1011 0011 - { }, // b4: 0100 1101 1011 0100 - { }, // b5: 0100 1101 1011 0101 - { }, // b6: 0100 1101 1011 0110 - { }, // b7: 0100 1101 1011 0111 - { }, // b8: 0100 1101 1011 1000 - { }, // b9: 0100 1101 1011 1001 - { }, // ba: 0100 1101 1011 1010 - { }, // bb: 0100 1101 1011 1011 - { }, // bc: 0100 1101 1011 1100 - { }, // bd: 0100 1101 1011 1101 - { }, // be: 0100 1101 1011 1110 - { }, // bf: 0100 1101 1011 1111 + { }, // b0: 0100 1100 1011 0000 + { }, // b1: 0100 1100 1011 0001 + { }, // b2: 0100 1100 1011 0010 + { }, // b3: 0100 1100 1011 0011 + { }, // b4: 0100 1100 1011 0100 + { }, // b5: 0100 1100 1011 0101 + { }, // b6: 0100 1100 1011 0110 + { }, // b7: 0100 1100 1011 0111 + { }, // b8: 0100 1100 1011 1000 + { }, // b9: 0100 1100 1011 1001 + { }, // ba: 0100 1100 1011 1010 + { }, // bb: 0100 1100 1011 1011 + { }, // bc: 0100 1100 1011 1100 + { }, // bd: 0100 1100 1011 1101 + { }, // be: 0100 1100 1011 1110 + { }, // bf: 0100 1100 1011 1111 - {MOV, "PA,A" }, // c0: 0100 1101 1100 0000 - {MOV, "PB,A" }, // c1: 0100 1101 1100 0001 - {MOV, "PC,A" }, // c2: 0100 1101 1100 0010 - {MOV, "PD,A" }, // c3: 0100 1101 1100 0011 - { }, // c4: 0100 1101 1100 0100 - {MOV, "PF,A" }, // c5: 0100 1101 1100 0101 - {MOV, "MKH,A" }, // c6: 0100 1101 1100 0110 - {MOV, "MKL,A" }, // c7: 0100 1101 1100 0111 - {MOV, "ANM,A" }, // c8: 0100 1101 1100 1000 7810 - {MOV, "SMH,A" }, // c9: 0100 1101 1100 1001 - {MOV, "SML,A" }, // ca: 0100 1101 1100 1010 - {MOV, "EOM,A" }, // cb: 0100 1101 1100 1011 - {MOV, "ETMM,A" }, // cc: 0100 1101 1100 1100 - {MOV, "TMM,A" }, // cd: 0100 1101 1100 1101 - { }, // ce: 0100 1101 1100 1110 - { }, // cf: 0100 1101 1100 1111 + {MOV, "A,PA" }, // c0: 0100 1100 1100 0000 + {MOV, "A,PB" }, // c1: 0100 1100 1100 0001 + {MOV, "A,PC" }, // c2: 0100 1100 1100 0010 + {MOV, "A,PD" }, // c3: 0100 1100 1100 0011 + { }, // c4: 0100 1100 1100 0100 + {MOV, "A,PF" }, // c5: 0100 1100 1100 0101 + {MOV, "A,MKH" }, // c6: 0100 1100 1100 0110 + {MOV, "A,MKL" }, // c7: 0100 1100 1100 0111 + {MOV, "A,ANM" }, // c8: 0100 1100 1100 1000 7810 + {MOV, "A,SMH" }, // c9: 0100 1100 1100 1001 + { }, // ca: 0100 1100 1100 1010 + {MOV, "A,EOM" }, // cb: 0100 1100 1100 1011 + { }, // cc: 0100 1100 1100 1100 + {MOV, "A,TMM" }, // cd: 0100 1100 1100 1101 + { }, // ce: 0100 1100 1100 1110 + { }, // cf: 0100 1100 1100 1111 - {MOV, "MM,A" }, // d0: 0100 1101 1101 0000 - {MOV, "MCC,A" }, // d1: 0100 1101 1101 0001 - {MOV, "MA,A" }, // d2: 0100 1101 1101 0010 - {MOV, "MB,A" }, // d3: 0100 1101 1101 0011 - {MOV, "MC,A" }, // d4: 0100 1101 1101 0100 - { }, // d5: 0100 1101 1101 0101 - { }, // d6: 0100 1101 1101 0110 - {MOV, "MF,A" }, // d7: 0100 1101 1101 0111 - {MOV, "TXB,A" }, // d8: 0100 1101 1101 1000 - { }, // d9: 0100 1101 1101 1001 - {MOV, "TM0,A" }, // da: 0100 1101 1101 1010 - {MOV, "TM1,A" }, // db: 0100 1101 1101 1011 - { }, // dc: 0100 1101 1101 1100 - { }, // dd: 0100 1101 1101 1101 - { }, // de: 0100 1101 1101 1110 - { }, // df: 0100 1101 1101 1111 + { }, // d0: 0100 1100 1101 0000 + { }, // d1: 0100 1100 1101 0001 + { }, // d2: 0100 1100 1101 0010 + { }, // d3: 0100 1100 1101 0011 + { }, // d4: 0100 1100 1101 0100 + { }, // d5: 0100 1100 1101 0101 + { }, // d6: 0100 1100 1101 0110 + { }, // d7: 0100 1100 1101 0111 + { }, // d8: 0100 1100 1101 1000 + {MOV, "A,RXB" }, // d9: 0100 1100 1101 1001 + { }, // da: 0100 1100 1101 1010 + { }, // db: 0100 1100 1101 1011 + { }, // dc: 0100 1100 1101 1100 + { }, // dd: 0100 1100 1101 1101 + { }, // de: 0100 1100 1101 1110 + { }, // df: 0100 1100 1101 1111 - { }, // e0: 0100 1101 1110 0000 - { }, // e1: 0100 1101 1110 0001 - { }, // e2: 0100 1101 1110 0010 - { }, // e3: 0100 1101 1110 0011 - { }, // e4: 0100 1101 1110 0100 - { }, // e5: 0100 1101 1110 0101 - { }, // e6: 0100 1101 1110 0110 - { }, // e7: 0100 1101 1110 0111 - {MOV, "ZCM,A" }, // e8: 0100 1101 1110 1000 7810 - { }, // e9: 0100 1101 1110 1001 - { }, // ea: 0100 1101 1110 1010 - { }, // eb: 0100 1101 1110 1011 - { }, // ec: 0100 1101 1110 1100 - { }, // ed: 0100 1101 1110 1101 - { }, // ee: 0100 1101 1110 1110 - { }, // ef: 0100 1101 1110 1111 + {MOV, "A,CR0" }, // e0: 0100 1100 1110 0000 7810 + {MOV, "A,CR1" }, // e1: 0100 1100 1110 0001 7810 + {MOV, "A,CR2" }, // e2: 0100 1100 1110 0010 7810 + {MOV, "A,CR3" }, // e3: 0100 1100 1110 0011 7810 + { }, // e4: 0100 1100 1110 0100 + { }, // e5: 0100 1100 1110 0101 + { }, // e6: 0100 1100 1110 0110 + { }, // e7: 0100 1100 1110 0111 + { }, // e8: 0100 1100 1110 1000 + { }, // e9: 0100 1100 1110 1001 + { }, // ea: 0100 1100 1110 1010 + { }, // eb: 0100 1100 1110 1011 + { }, // ec: 0100 1100 1110 1100 + { }, // ed: 0100 1100 1110 1101 + { }, // ee: 0100 1100 1110 1110 + { }, // ef: 0100 1100 1110 1111 - { }, // f0: 0100 1101 1111 0000 - { }, // f1: 0100 1101 1111 0001 - { }, // f2: 0100 1101 1111 0010 - { }, // f3: 0100 1101 1111 0011 - { }, // f4: 0100 1101 1111 0100 - { }, // f5: 0100 1101 1111 0101 - { }, // f6: 0100 1101 1111 0110 - { }, // f7: 0100 1101 1111 0111 - { }, // f8: 0100 1101 1111 1000 - { }, // f9: 0100 1101 1111 1001 - { }, // fa: 0100 1101 1111 1010 - { }, // fb: 0100 1101 1111 1011 - { }, // fc: 0100 1101 1111 1100 - { }, // fd: 0100 1101 1111 1101 - { }, // fe: 0100 1101 1111 1110 - { } // ff: 0100 1101 1111 1111 + { }, // f0: 0100 1100 1111 0000 + { }, // f1: 0100 1100 1111 0001 + { }, // f2: 0100 1100 1111 0010 + { }, // f3: 0100 1100 1111 0011 + { }, // f4: 0100 1100 1111 0100 + { }, // f5: 0100 1100 1111 0101 + { }, // f6: 0100 1100 1111 0110 + { }, // f7: 0100 1100 1111 0111 + { }, // f8: 0100 1100 1111 1000 + { }, // f9: 0100 1100 1111 1001 + { }, // fa: 0100 1100 1111 1010 + { }, // fb: 0100 1100 1111 1011 + { }, // fc: 0100 1100 1111 1100 + { }, // fd: 0100 1100 1111 1101 + { }, // fe: 0100 1100 1111 1110 + { } // ff: 0100 1100 1111 1111 }; -const dasm_s dasm_s::d4D_7807[256] = + +// prefix 4D +const upd7810_base_disassembler::dasm_s upd7810_disassembler::d4D_7810[256] = { { }, // 00: 0100 1101 0000 0000 { }, // 01: 0100 1101 0000 0001 @@ -2024,7 +1830,7 @@ const dasm_s dasm_s::d4D_7807[256] = {MOV, "PF,A" }, // c5: 0100 1101 1100 0101 {MOV, "MKH,A" }, // c6: 0100 1101 1100 0110 {MOV, "MKL,A" }, // c7: 0100 1101 1100 0111 - { }, // c8: 0100 1101 1100 1000 + {MOV, "ANM,A" }, // c8: 0100 1101 1100 1000 7810 {MOV, "SMH,A" }, // c9: 0100 1101 1100 1001 {MOV, "SML,A" }, // ca: 0100 1101 1100 1010 {MOV, "EOM,A" }, // cb: 0100 1101 1100 1011 @@ -2055,10 +1861,10 @@ const dasm_s dasm_s::d4D_7807[256] = { }, // e2: 0100 1101 1110 0010 { }, // e3: 0100 1101 1110 0011 { }, // e4: 0100 1101 1110 0100 - {MOV, "MT,A" }, // e5: 0100 1101 1110 0101 7807 + { }, // e5: 0100 1101 1110 0101 { }, // e6: 0100 1101 1110 0110 { }, // e7: 0100 1101 1110 0111 - { }, // e8: 0100 1101 1110 1000 + {MOV, "ZCM,A" }, // e8: 0100 1101 1110 1000 7810 { }, // e9: 0100 1101 1110 1001 { }, // ea: 0100 1101 1110 1010 { }, // eb: 0100 1101 1110 1011 @@ -2085,369 +1891,95 @@ const dasm_s dasm_s::d4D_7807[256] = { } // ff: 0100 1101 1111 1111 }; -// prefix 60 -const dasm_s dasm_s::d60[256] = -{ - { }, // 00: 0110 0000 0000 0000 - { }, // 01: 0110 0000 0000 0001 - { }, // 02: 0110 0000 0000 0010 - { }, // 03: 0110 0000 0000 0011 - { }, // 04: 0110 0000 0000 0100 - { }, // 05: 0110 0000 0000 0101 - { }, // 06: 0110 0000 0000 0110 - { }, // 07: 0110 0000 0000 0111 - {ANA, "V,A" }, // 08: 0110 0000 0000 1000 - {ANA, "A,A" }, // 09: 0110 0000 0000 1001 - {ANA, "B,A" }, // 0a: 0110 0000 0000 1010 - {ANA, "C,A" }, // 0b: 0110 0000 0000 1011 - {ANA, "D,A" }, // 0c: 0110 0000 0000 1100 - {ANA, "E,A" }, // 0d: 0110 0000 0000 1101 - {ANA, "H,A" }, // 0e: 0110 0000 0000 1110 - {ANA, "L,A" }, // 0f: 0110 0000 0000 1111 - - {XRA, "V,A" }, // 10: 0110 0000 0001 0000 - {XRA, "A,A" }, // 11: 0110 0000 0001 0001 - {XRA, "B,A" }, // 12: 0110 0000 0001 0010 - {XRA, "C,A" }, // 13: 0110 0000 0001 0011 - {XRA, "D,A" }, // 14: 0110 0000 0001 0100 - {XRA, "E,A" }, // 15: 0110 0000 0001 0101 - {XRA, "H,A" }, // 16: 0110 0000 0001 0110 - {XRA, "L,A" }, // 17: 0110 0000 0001 0111 - {ORA, "V,A" }, // 18: 0110 0000 0001 1000 - {ORA, "A,A" }, // 19: 0110 0000 0001 1001 - {ORA, "B,A" }, // 1a: 0110 0000 0001 1010 - {ORA, "C,A" }, // 1b: 0110 0000 0001 1011 - {ORA, "D,A" }, // 1c: 0110 0000 0001 1100 - {ORA, "E,A" }, // 1d: 0110 0000 0001 1101 - {ORA, "H,A" }, // 1e: 0110 0000 0001 1110 - {ORA, "L,A" }, // 1f: 0110 0000 0001 1111 - {ADDNC, "V,A" }, // 20: 0110 0000 0010 0000 - {ADDNC, "A,A" }, // 21: 0110 0000 0010 0001 - {ADDNC, "B,A" }, // 22: 0110 0000 0010 0010 - {ADDNC, "C,A" }, // 23: 0110 0000 0010 0011 - {ADDNC, "D,A" }, // 24: 0110 0000 0010 0100 - {ADDNC, "E,A" }, // 25: 0110 0000 0010 0101 - {ADDNC, "H,A" }, // 26: 0110 0000 0010 0110 - {ADDNC, "L,A" }, // 27: 0110 0000 0010 0111 - {GTA, "V,A" }, // 28: 0110 0000 0010 1000 - {GTA, "A,A" }, // 29: 0110 0000 0010 1001 - {GTA, "B,A" }, // 2a: 0110 0000 0010 1010 - {GTA, "C,A" }, // 2b: 0110 0000 0010 1011 - {GTA, "D,A" }, // 2c: 0110 0000 0010 1100 - {GTA, "E,A" }, // 2d: 0110 0000 0010 1101 - {GTA, "H,A" }, // 2e: 0110 0000 0010 1110 - {GTA, "L,A" }, // 2f: 0110 0000 0010 1111 - {SUBNB, "V,A" }, // 30: 0110 0000 0011 0000 - {SUBNB, "A,A" }, // 31: 0110 0000 0011 0001 - {SUBNB, "B,A" }, // 32: 0110 0000 0011 0010 - {SUBNB, "C,A" }, // 33: 0110 0000 0011 0011 - {SUBNB, "D,A" }, // 34: 0110 0000 0011 0100 - {SUBNB, "E,A" }, // 35: 0110 0000 0011 0101 - {SUBNB, "H,A" }, // 36: 0110 0000 0011 0110 - {SUBNB, "L,A" }, // 37: 0110 0000 0011 0111 - {LTA, "V,A" }, // 38: 0110 0000 0011 1000 - {LTA, "A,A" }, // 39: 0110 0000 0011 1001 - {LTA, "B,A" }, // 3a: 0110 0000 0011 1010 - {LTA, "C,A" }, // 3b: 0110 0000 0011 1011 - {LTA, "D,A" }, // 3c: 0110 0000 0011 1100 - {LTA, "E,A" }, // 3d: 0110 0000 0011 1101 - {LTA, "H,A" }, // 3e: 0110 0000 0011 1110 - {LTA, "L,A" }, // 3f: 0110 0000 0011 1111 +// prefix 64 +const upd7810_base_disassembler::dasm_s upd7810_disassembler::d64_7810[256] = +{ + {MVI, "PA,%b" }, // 00: 0110 0100 0000 0000 xxxx xxxx + {MVI, "PB,%b" }, // 01: 0110 0100 0000 0001 xxxx xxxx + {MVI, "PC,%b" }, // 02: 0110 0100 0000 0010 xxxx xxxx + {MVI, "PD,%b" }, // 03: 0110 0100 0000 0011 xxxx xxxx + { }, // 04: 0110 0100 0000 0100 xxxx xxxx + {MVI, "PF,%b" }, // 05: 0110 0100 0000 0101 xxxx xxxx + {MVI, "MKH,%b" }, // 06: 0110 0100 0000 0110 xxxx xxxx + {MVI, "MKL,%b" }, // 07: 0110 0100 0000 0111 xxxx xxxx + {ANI, "PA,%b" }, // 08: 0110 0100 0000 1000 xxxx xxxx + {ANI, "PB,%b" }, // 09: 0110 0100 0000 1001 xxxx xxxx + {ANI, "PC,%b" }, // 0a: 0110 0100 0000 1010 xxxx xxxx + {ANI, "PD,%b" }, // 0b: 0110 0100 0000 1011 xxxx xxxx + { }, // 0c: 0110 0100 0000 1100 xxxx xxxx + {ANI, "PF,%b" }, // 0d: 0110 0100 0000 1101 xxxx xxxx + {ANI, "MKH,%b" }, // 0e: 0110 0100 0000 1110 xxxx xxxx + {ANI, "MKL,%b" }, // 0f: 0110 0100 0000 1111 xxxx xxxx - {ADD, "V,A" }, // 40: 0110 0000 0100 0000 - {ADD, "A,A" }, // 41: 0110 0000 0100 0001 - {ADD, "B,A" }, // 42: 0110 0000 0100 0010 - {ADD, "C,A" }, // 43: 0110 0000 0100 0011 - {ADD, "D,A" }, // 44: 0110 0000 0100 0100 - {ADD, "E,A" }, // 45: 0110 0000 0100 0101 - {ADD, "H,A" }, // 46: 0110 0000 0100 0110 - {ADD, "L,A" }, // 47: 0110 0000 0100 0111 - { }, // 48: 0110 0000 0100 1000 - { }, // 49: 0110 0000 0100 1001 - { }, // 4a: 0110 0000 0100 1010 - { }, // 4b: 0110 0000 0100 1011 - { }, // 4c: 0110 0000 0100 1100 - { }, // 4d: 0110 0000 0100 1101 - { }, // 4e: 0110 0000 0100 1110 - { }, // 4f: 0110 0000 0100 1111 + {XRI, "PA,%b" }, // 10: 0110 0100 0001 0000 xxxx xxxx + {XRI, "PB,%b" }, // 11: 0110 0100 0001 0001 xxxx xxxx + {XRI, "PC,%b" }, // 12: 0110 0100 0001 0010 xxxx xxxx + {XRI, "PD,%b" }, // 13: 0110 0100 0001 0011 xxxx xxxx + { }, // 14: 0110 0100 0001 0100 xxxx xxxx + {XRI, "PF,%b" }, // 15: 0110 0100 0001 0101 xxxx xxxx + {XRI, "MKH,%b" }, // 16: 0110 0100 0001 0110 xxxx xxxx + {XRI, "MKL,%b" }, // 17: 0110 0100 0001 0111 xxxx xxxx + {ORI, "PA,%b" }, // 18: 0110 0100 0001 1000 xxxx xxxx + {ORI, "PB,%b" }, // 19: 0110 0100 0001 1001 xxxx xxxx + {ORI, "PC,%b" }, // 1a: 0110 0100 0001 1010 xxxx xxxx + {ORI, "PD,%b" }, // 1b: 0110 0100 0001 1011 xxxx xxxx + { }, // 1c: 0110 0100 0001 1100 xxxx xxxx + {ORI, "PF,%b" }, // 1d: 0110 0100 0001 1101 xxxx xxxx + {ORI, "MKH,%b" }, // 1e: 0110 0100 0001 1110 xxxx xxxx + {ORI, "MKL,%b" }, // 1f: 0110 0100 0001 1111 xxxx xxxx - {ADC, "V,A" }, // 50: 0110 0000 0101 0000 - {ADC, "A,A" }, // 51: 0110 0000 0101 0001 - {ADC, "B,A" }, // 52: 0110 0000 0101 0010 - {ADC, "C,A" }, // 53: 0110 0000 0101 0011 - {ADC, "D,A" }, // 54: 0110 0000 0101 0100 - {ADC, "E,A" }, // 55: 0110 0000 0101 0101 - {ADC, "H,A" }, // 56: 0110 0000 0101 0110 - {ADC, "L,A" }, // 57: 0110 0000 0101 0111 - { }, // 58: 0110 0000 0101 1000 - { }, // 59: 0110 0000 0101 1001 - { }, // 5a: 0110 0000 0101 1010 - { }, // 5b: 0110 0000 0101 1011 - { }, // 5c: 0110 0000 0101 1100 - { }, // 5d: 0110 0000 0101 1101 - { }, // 5e: 0110 0000 0101 1110 - { }, // 5f: 0110 0000 0101 1111 + {ADINC, "PA,%b" }, // 20: 0110 0100 0010 0000 xxxx xxxx + {ADINC, "PB,%b" }, // 21: 0110 0100 0010 0001 xxxx xxxx + {ADINC, "PC,%b" }, // 22: 0110 0100 0010 0010 xxxx xxxx + {ADINC, "PD,%b" }, // 23: 0110 0100 0010 0011 xxxx xxxx + { }, // 24: 0110 0100 0010 0100 xxxx xxxx + {ADINC, "PF,%b" }, // 25: 0110 0100 0010 0101 xxxx xxxx + {ADINC, "MKH,%b" }, // 26: 0110 0100 0010 0110 xxxx xxxx + {ADINC, "MKL,%b" }, // 27: 0110 0100 0010 0111 xxxx xxxx + {GTI, "PA,%b" }, // 28: 0110 0100 0010 1000 xxxx xxxx + {GTI, "PB,%b" }, // 29: 0110 0100 0010 1001 xxxx xxxx + {GTI, "PC,%b" }, // 2a: 0110 0100 0010 1010 xxxx xxxx + {GTI, "PD,%b" }, // 2b: 0110 0100 0010 1011 xxxx xxxx + { }, // 2c: 0110 0100 0010 1100 xxxx xxxx + {GTI, "PF,%b" }, // 2d: 0110 0100 0010 1101 xxxx xxxx + {GTI, "MKH,%b" }, // 2e: 0110 0100 0010 1110 xxxx xxxx + {GTI, "MKL,%b" }, // 2f: 0110 0100 0010 1111 xxxx xxxx - {SUB, "V,A" }, // 60: 0110 0000 0110 0000 - {SUB, "A,A" }, // 61: 0110 0000 0110 0001 - {SUB, "B,A" }, // 62: 0110 0000 0110 0010 - {SUB, "C,A" }, // 63: 0110 0000 0110 0011 - {SUB, "D,A" }, // 64: 0110 0000 0110 0100 - {SUB, "E,A" }, // 65: 0110 0000 0110 0101 - {SUB, "H,A" }, // 66: 0110 0000 0110 0110 - {SUB, "L,A" }, // 67: 0110 0000 0110 0111 - {NEA, "V,A" }, // 68: 0110 0000 0110 1000 - {NEA, "A,A" }, // 69: 0110 0000 0110 1001 - {NEA, "B,A" }, // 6a: 0110 0000 0110 1010 - {NEA, "C,A" }, // 6b: 0110 0000 0110 1011 - {NEA, "D,A" }, // 6c: 0110 0000 0110 1100 - {NEA, "E,A" }, // 6d: 0110 0000 0110 1101 - {NEA, "H,A" }, // 6e: 0110 0000 0110 1110 - {NEA, "L,A" }, // 6f: 0110 0000 0110 1111 + {SUINB, "PA,%b" }, // 30: 0110 0100 0011 0000 xxxx xxxx + {SUINB, "PB,%b" }, // 31: 0110 0100 0011 0001 xxxx xxxx + {SUINB, "PC,%b" }, // 32: 0110 0100 0011 0010 xxxx xxxx + {SUINB, "PD,%b" }, // 33: 0110 0100 0011 0011 xxxx xxxx + { }, // 34: 0110 0100 0011 0100 xxxx xxxx + {SUINB, "PF,%b" }, // 35: 0110 0100 0011 0101 xxxx xxxx + {SUINB, "MKH,%b" }, // 36: 0110 0100 0011 0110 xxxx xxxx + {SUINB, "MKL,%b" }, // 37: 0110 0100 0011 0111 xxxx xxxx + {LTI, "PA,%b" }, // 38: 0110 0100 0011 1000 xxxx xxxx + {LTI, "PB,%b" }, // 39: 0110 0100 0011 1001 xxxx xxxx + {LTI, "PC,%b" }, // 3a: 0110 0100 0011 1010 xxxx xxxx + {LTI, "PD,%b" }, // 3b: 0110 0100 0011 1011 xxxx xxxx + { }, // 3c: 0110 0100 0011 1100 xxxx xxxx + {LTI, "PF,%b" }, // 3d: 0110 0100 0011 1101 xxxx xxxx + {LTI, "MKH,%b" }, // 3e: 0110 0100 0011 1110 xxxx xxxx + {LTI, "MKL,%b" }, // 3f: 0110 0100 0011 1111 xxxx xxxx - {SBB, "V,A" }, // 70: 0110 0000 0111 0000 - {SBB, "A,A" }, // 71: 0110 0000 0111 0001 - {SBB, "B,A" }, // 72: 0110 0000 0111 0010 - {SBB, "C,A" }, // 73: 0110 0000 0111 0011 - {SBB, "D,A" }, // 74: 0110 0000 0111 0100 - {SBB, "E,A" }, // 75: 0110 0000 0111 0101 - {SBB, "H,A" }, // 76: 0110 0000 0111 0110 - {SBB, "L,A" }, // 77: 0110 0000 0111 0111 - {EQA, "V,A" }, // 78: 0110 0000 0111 1000 - {EQA, "A,A" }, // 79: 0110 0000 0111 1001 - {EQA, "B,A" }, // 7a: 0110 0000 0111 1010 - {EQA, "C,A" }, // 7b: 0110 0000 0111 1011 - {EQA, "D,A" }, // 7c: 0110 0000 0111 1100 - {EQA, "E,A" }, // 7d: 0110 0000 0111 1101 - {EQA, "H,A" }, // 7e: 0110 0000 0111 1110 - {EQA, "L,A" }, // 7f: 0110 0000 0111 1111 - - { }, // 80: 0110 0000 1000 0000 - { }, // 81: 0110 0000 1000 0001 - { }, // 82: 0110 0000 1000 0010 - { }, // 83: 0110 0000 1000 0011 - { }, // 84: 0110 0000 1000 0100 - { }, // 85: 0110 0000 1000 0101 - { }, // 86: 0110 0000 1000 0110 - { }, // 87: 0110 0000 1000 0111 - {ANA, "A,V" }, // 88: 0110 0000 1000 1000 - {ANA, "A,A" }, // 89: 0110 0000 1000 1001 - {ANA, "A,B" }, // 8a: 0110 0000 1000 1010 - {ANA, "A,C" }, // 8b: 0110 0000 1000 1011 - {ANA, "A,D" }, // 8c: 0110 0000 1000 1100 - {ANA, "A,E" }, // 8d: 0110 0000 1000 1101 - {ANA, "A,H" }, // 8e: 0110 0000 1000 1110 - {ANA, "A,L" }, // 8f: 0110 0000 1000 1111 - - {XRA, "A,V" }, // 90: 0110 0000 1001 0000 - {XRA, "A,A" }, // 91: 0110 0000 1001 0001 - {XRA, "A,B" }, // 92: 0110 0000 1001 0010 - {XRA, "A,C" }, // 93: 0110 0000 1001 0011 - {XRA, "A,D" }, // 94: 0110 0000 1001 0100 - {XRA, "A,E" }, // 95: 0110 0000 1001 0101 - {XRA, "A,H" }, // 96: 0110 0000 1001 0110 - {XRA, "A,L" }, // 97: 0110 0000 1001 0111 - {ORA, "A,V" }, // 98: 0110 0000 1001 1000 - {ORA, "A,A" }, // 99: 0110 0000 1001 1001 - {ORA, "A,B" }, // 9a: 0110 0000 1001 1010 - {ORA, "A,C" }, // 9b: 0110 0000 1001 1011 - {ORA, "A,D" }, // 9c: 0110 0000 1001 1100 - {ORA, "A,E" }, // 9d: 0110 0000 1001 1101 - {ORA, "A,H" }, // 9e: 0110 0000 1001 1110 - {ORA, "A,L" }, // 9f: 0110 0000 1001 1111 - - {ADDNC, "A,V" }, // a0: 0110 0000 1010 0000 - {ADDNC, "A,A" }, // a1: 0110 0000 1010 0001 - {ADDNC, "A,B" }, // a2: 0110 0000 1010 0010 - {ADDNC, "A,C" }, // a3: 0110 0000 1010 0011 - {ADDNC, "A,D" }, // a4: 0110 0000 1010 0100 - {ADDNC, "A,E" }, // a5: 0110 0000 1010 0101 - {ADDNC, "A,H" }, // a6: 0110 0000 1010 0110 - {ADDNC, "A,L" }, // a7: 0110 0000 1010 0111 - {GTA, "A,V" }, // a8: 0110 0000 1010 1000 - {GTA, "A,A" }, // a9: 0110 0000 1010 1001 - {GTA, "A,B" }, // aa: 0110 0000 1010 1010 - {GTA, "A,C" }, // ab: 0110 0000 1010 1011 - {GTA, "A,D" }, // ac: 0110 0000 1010 1100 - {GTA, "A,E" }, // ad: 0110 0000 1010 1101 - {GTA, "A,H" }, // ae: 0110 0000 1010 1110 - {GTA, "A,L" }, // af: 0110 0000 1010 1111 - - {SUBNB, "A,V" }, // b0: 0110 0000 1011 0000 - {SUBNB, "A,A" }, // b1: 0110 0000 1011 0001 - {SUBNB, "A,B" }, // b2: 0110 0000 1011 0010 - {SUBNB, "A,C" }, // b3: 0110 0000 1011 0011 - {SUBNB, "A,D" }, // b4: 0110 0000 1011 0100 - {SUBNB, "A,E" }, // b5: 0110 0000 1011 0101 - {SUBNB, "A,H" }, // b6: 0110 0000 1011 0110 - {SUBNB, "A,L" }, // b7: 0110 0000 1011 0111 - {LTA, "A,V" }, // b8: 0110 0000 1011 1000 - {LTA, "A,A" }, // b9: 0110 0000 1011 1001 - {LTA, "A,B" }, // ba: 0110 0000 1011 1010 - {LTA, "A,C" }, // bb: 0110 0000 1011 1011 - {LTA, "A,D" }, // bc: 0110 0000 1011 1100 - {LTA, "A,E" }, // bd: 0110 0000 1011 1101 - {LTA, "A,H" }, // be: 0110 0000 1011 1110 - {LTA, "A,L" }, // bf: 0110 0000 1011 1111 - - {ADD, "A,V" }, // c0: 0110 0000 1100 0000 - {ADD, "A,A" }, // c1: 0110 0000 1100 0001 - {ADD, "A,B" }, // c2: 0110 0000 1100 0010 - {ADD, "A,C" }, // c3: 0110 0000 1100 0011 - {ADD, "A,D" }, // c4: 0110 0000 1100 0100 - {ADD, "A,E" }, // c5: 0110 0000 1100 0101 - {ADD, "A,H" }, // c6: 0110 0000 1100 0110 - {ADD, "A,L" }, // c7: 0110 0000 1100 0111 - {ONA, "A,V" }, // c8: 0110 0000 1100 1000 - {ONA, "A,A" }, // c9: 0110 0000 1100 1001 - {ONA, "A,B" }, // ca: 0110 0000 1100 1010 - {ONA, "A,C" }, // cb: 0110 0000 1100 1011 - {ONA, "A,D" }, // cc: 0110 0000 1100 1100 - {ONA, "A,E" }, // cd: 0110 0000 1100 1101 - {ONA, "A,H" }, // ce: 0110 0000 1100 1110 - {ONA, "A,L" }, // cf: 0110 0000 1100 1111 - - {ADC, "A,V" }, // d0: 0110 0000 1101 0000 - {ADC, "A,A" }, // d1: 0110 0000 1101 0001 - {ADC, "A,B" }, // d2: 0110 0000 1101 0010 - {ADC, "A,C" }, // d3: 0110 0000 1101 0011 - {ADC, "A,D" }, // d4: 0110 0000 1101 0100 - {ADC, "A,E" }, // d5: 0110 0000 1101 0101 - {ADC, "A,H" }, // d6: 0110 0000 1101 0110 - {ADC, "A,L" }, // d7: 0110 0000 1101 0111 - {OFFA, "A,V" }, // d8: 0110 0000 1101 1000 - {OFFA, "A,A" }, // d9: 0110 0000 1101 1001 - {OFFA, "A,B" }, // da: 0110 0000 1101 1010 - {OFFA, "A,C" }, // db: 0110 0000 1101 1011 - {OFFA, "A,D" }, // dc: 0110 0000 1101 1100 - {OFFA, "A,E" }, // dd: 0110 0000 1101 1101 - {OFFA, "A,H" }, // de: 0110 0000 1101 1110 - {OFFA, "A,L" }, // df: 0110 0000 1101 1111 - - {SUB, "A,V" }, // e0: 0110 0000 1110 0000 - {SUB, "A,A" }, // e1: 0110 0000 1110 0001 - {SUB, "A,B" }, // e2: 0110 0000 1110 0010 - {SUB, "A,C" }, // e3: 0110 0000 1110 0011 - {SUB, "A,D" }, // e4: 0110 0000 1110 0100 - {SUB, "A,E" }, // e5: 0110 0000 1110 0101 - {SUB, "A,H" }, // e6: 0110 0000 1110 0110 - {SUB, "A,L" }, // e7: 0110 0000 1110 0111 - {NEA, "A,V" }, // e8: 0110 0000 1110 1000 - {NEA, "A,A" }, // e9: 0110 0000 1110 1001 - {NEA, "A,B" }, // ea: 0110 0000 1110 1010 - {NEA, "A,C" }, // eb: 0110 0000 1110 1011 - {NEA, "A,D" }, // ec: 0110 0000 1110 1100 - {NEA, "A,E" }, // ed: 0110 0000 1110 1101 - {NEA, "A,H" }, // ee: 0110 0000 1110 1110 - {NEA, "A,L" }, // ef: 0110 0000 1110 1111 - - {SBB, "A,V" }, // f0: 0110 0000 1111 0000 - {SBB, "A,A" }, // f1: 0110 0000 1111 0001 - {SBB, "A,B" }, // f2: 0110 0000 1111 0010 - {SBB, "A,C" }, // f3: 0110 0000 1111 0011 - {SBB, "A,D" }, // f4: 0110 0000 1111 0100 - {SBB, "A,E" }, // f5: 0110 0000 1111 0101 - {SBB, "A,H" }, // f6: 0110 0000 1111 0110 - {SBB, "A,L" }, // f7: 0110 0000 1111 0111 - {EQA, "A,V" }, // f8: 0110 0000 1111 1000 - {EQA, "A,A" }, // f9: 0110 0000 1111 1001 - {EQA, "A,B" }, // fa: 0110 0000 1111 1010 - {EQA, "A,C" }, // fb: 0110 0000 1111 1011 - {EQA, "A,D" }, // fc: 0110 0000 1111 1100 - {EQA, "A,E" }, // fd: 0110 0000 1111 1101 - {EQA, "A,H" }, // fe: 0110 0000 1111 1110 - {EQA, "A,L" } // ff: 0110 0000 1111 1111 -}; - -// prefix 64 -const dasm_s dasm_s::d64_7810[256] = -{ - {MVI, "PA,%b" }, // 00: 0110 0100 0000 0000 xxxx xxxx - {MVI, "PB,%b" }, // 01: 0110 0100 0000 0001 xxxx xxxx - {MVI, "PC,%b" }, // 02: 0110 0100 0000 0010 xxxx xxxx - {MVI, "PD,%b" }, // 03: 0110 0100 0000 0011 xxxx xxxx - { }, // 04: 0110 0100 0000 0100 xxxx xxxx - {MVI, "PF,%b" }, // 05: 0110 0100 0000 0101 xxxx xxxx - {MVI, "MKH,%b" }, // 06: 0110 0100 0000 0110 xxxx xxxx - {MVI, "MKL,%b" }, // 07: 0110 0100 0000 0111 xxxx xxxx - {ANI, "PA,%b" }, // 08: 0110 0100 0000 1000 xxxx xxxx - {ANI, "PB,%b" }, // 09: 0110 0100 0000 1001 xxxx xxxx - {ANI, "PC,%b" }, // 0a: 0110 0100 0000 1010 xxxx xxxx - {ANI, "PD,%b" }, // 0b: 0110 0100 0000 1011 xxxx xxxx - { }, // 0c: 0110 0100 0000 1100 xxxx xxxx - {ANI, "PF,%b" }, // 0d: 0110 0100 0000 1101 xxxx xxxx - {ANI, "MKH,%b" }, // 0e: 0110 0100 0000 1110 xxxx xxxx - {ANI, "MKL,%b" }, // 0f: 0110 0100 0000 1111 xxxx xxxx - - {XRI, "PA,%b" }, // 10: 0110 0100 0001 0000 xxxx xxxx - {XRI, "PB,%b" }, // 11: 0110 0100 0001 0001 xxxx xxxx - {XRI, "PC,%b" }, // 12: 0110 0100 0001 0010 xxxx xxxx - {XRI, "PD,%b" }, // 13: 0110 0100 0001 0011 xxxx xxxx - { }, // 14: 0110 0100 0001 0100 xxxx xxxx - {XRI, "PF,%b" }, // 15: 0110 0100 0001 0101 xxxx xxxx - {XRI, "MKH,%b" }, // 16: 0110 0100 0001 0110 xxxx xxxx - {XRI, "MKL,%b" }, // 17: 0110 0100 0001 0111 xxxx xxxx - {ORI, "PA,%b" }, // 18: 0110 0100 0001 1000 xxxx xxxx - {ORI, "PB,%b" }, // 19: 0110 0100 0001 1001 xxxx xxxx - {ORI, "PC,%b" }, // 1a: 0110 0100 0001 1010 xxxx xxxx - {ORI, "PD,%b" }, // 1b: 0110 0100 0001 1011 xxxx xxxx - { }, // 1c: 0110 0100 0001 1100 xxxx xxxx - {ORI, "PF,%b" }, // 1d: 0110 0100 0001 1101 xxxx xxxx - {ORI, "MKH,%b" }, // 1e: 0110 0100 0001 1110 xxxx xxxx - {ORI, "MKL,%b" }, // 1f: 0110 0100 0001 1111 xxxx xxxx - - {ADINC, "PA,%b" }, // 20: 0110 0100 0010 0000 xxxx xxxx - {ADINC, "PB,%b" }, // 21: 0110 0100 0010 0001 xxxx xxxx - {ADINC, "PC,%b" }, // 22: 0110 0100 0010 0010 xxxx xxxx - {ADINC, "PD,%b" }, // 23: 0110 0100 0010 0011 xxxx xxxx - { }, // 24: 0110 0100 0010 0100 xxxx xxxx - {ADINC, "PF,%b" }, // 25: 0110 0100 0010 0101 xxxx xxxx - {ADINC, "MKH,%b" }, // 26: 0110 0100 0010 0110 xxxx xxxx - {ADINC, "MKL,%b" }, // 27: 0110 0100 0010 0111 xxxx xxxx - {GTI, "PA,%b" }, // 28: 0110 0100 0010 1000 xxxx xxxx - {GTI, "PB,%b" }, // 29: 0110 0100 0010 1001 xxxx xxxx - {GTI, "PC,%b" }, // 2a: 0110 0100 0010 1010 xxxx xxxx - {GTI, "PD,%b" }, // 2b: 0110 0100 0010 1011 xxxx xxxx - { }, // 2c: 0110 0100 0010 1100 xxxx xxxx - {GTI, "PF,%b" }, // 2d: 0110 0100 0010 1101 xxxx xxxx - {GTI, "MKH,%b" }, // 2e: 0110 0100 0010 1110 xxxx xxxx - {GTI, "MKL,%b" }, // 2f: 0110 0100 0010 1111 xxxx xxxx - - {SUINB, "PA,%b" }, // 30: 0110 0100 0011 0000 xxxx xxxx - {SUINB, "PB,%b" }, // 31: 0110 0100 0011 0001 xxxx xxxx - {SUINB, "PC,%b" }, // 32: 0110 0100 0011 0010 xxxx xxxx - {SUINB, "PD,%b" }, // 33: 0110 0100 0011 0011 xxxx xxxx - { }, // 34: 0110 0100 0011 0100 xxxx xxxx - {SUINB, "PF,%b" }, // 35: 0110 0100 0011 0101 xxxx xxxx - {SUINB, "MKH,%b" }, // 36: 0110 0100 0011 0110 xxxx xxxx - {SUINB, "MKL,%b" }, // 37: 0110 0100 0011 0111 xxxx xxxx - {LTI, "PA,%b" }, // 38: 0110 0100 0011 1000 xxxx xxxx - {LTI, "PB,%b" }, // 39: 0110 0100 0011 1001 xxxx xxxx - {LTI, "PC,%b" }, // 3a: 0110 0100 0011 1010 xxxx xxxx - {LTI, "PD,%b" }, // 3b: 0110 0100 0011 1011 xxxx xxxx - { }, // 3c: 0110 0100 0011 1100 xxxx xxxx - {LTI, "PF,%b" }, // 3d: 0110 0100 0011 1101 xxxx xxxx - {LTI, "MKH,%b" }, // 3e: 0110 0100 0011 1110 xxxx xxxx - {LTI, "MKL,%b" }, // 3f: 0110 0100 0011 1111 xxxx xxxx - - {ADI, "PA,%b" }, // 40: 0110 0100 0100 0000 xxxx xxxx - {ADI, "PB,%b" }, // 41: 0110 0100 0100 0001 xxxx xxxx - {ADI, "PC,%b" }, // 42: 0110 0100 0100 0010 xxxx xxxx - {ADI, "PD,%b" }, // 43: 0110 0100 0100 0011 xxxx xxxx - { }, // 44: 0110 0100 0100 0100 xxxx xxxx - {ADI, "PF,%b" }, // 45: 0110 0100 0100 0101 xxxx xxxx - {ADI, "MKH,%b" }, // 46: 0110 0100 0100 0110 xxxx xxxx - {ADI, "MKL,%b" }, // 47: 0110 0100 0100 0111 xxxx xxxx - {ONI, "PA,%b" }, // 48: 0110 0100 0100 1000 xxxx xxxx - {ONI, "PB,%b" }, // 49: 0110 0100 0100 1001 xxxx xxxx - {ONI, "PC,%b" }, // 4a: 0110 0100 0100 1010 xxxx xxxx - {ONI, "PD,%b" }, // 4b: 0110 0100 0100 1011 xxxx xxxx - { }, // 4c: 0110 0100 0100 1100 xxxx xxxx - {ONI, "PF,%b" }, // 4d: 0110 0100 0100 1101 xxxx xxxx - {ONI, "MKH,%b" }, // 4e: 0110 0100 0100 1110 xxxx xxxx - {ONI, "MKL,%b" }, // 4f: 0110 0100 0100 1111 xxxx xxxx + {ADI, "PA,%b" }, // 40: 0110 0100 0100 0000 xxxx xxxx + {ADI, "PB,%b" }, // 41: 0110 0100 0100 0001 xxxx xxxx + {ADI, "PC,%b" }, // 42: 0110 0100 0100 0010 xxxx xxxx + {ADI, "PD,%b" }, // 43: 0110 0100 0100 0011 xxxx xxxx + { }, // 44: 0110 0100 0100 0100 xxxx xxxx + {ADI, "PF,%b" }, // 45: 0110 0100 0100 0101 xxxx xxxx + {ADI, "MKH,%b" }, // 46: 0110 0100 0100 0110 xxxx xxxx + {ADI, "MKL,%b" }, // 47: 0110 0100 0100 0111 xxxx xxxx + {ONI, "PA,%b" }, // 48: 0110 0100 0100 1000 xxxx xxxx + {ONI, "PB,%b" }, // 49: 0110 0100 0100 1001 xxxx xxxx + {ONI, "PC,%b" }, // 4a: 0110 0100 0100 1010 xxxx xxxx + {ONI, "PD,%b" }, // 4b: 0110 0100 0100 1011 xxxx xxxx + { }, // 4c: 0110 0100 0100 1100 xxxx xxxx + {ONI, "PF,%b" }, // 4d: 0110 0100 0100 1101 xxxx xxxx + {ONI, "MKH,%b" }, // 4e: 0110 0100 0100 1110 xxxx xxxx + {ONI, "MKL,%b" }, // 4f: 0110 0100 0100 1111 xxxx xxxx {ACI, "PA,%b" }, // 50: 0110 0100 0101 0000 xxxx xxxx {ACI, "PB,%b" }, // 51: 0110 0100 0101 0001 xxxx xxxx @@ -2637,1110 +2169,1385 @@ const dasm_s dasm_s::d64_7810[256] = { } // ff: 0110 0100 1111 1111 xxxx xxxx }; -const dasm_s dasm_s::d64_7807[256] = -{ - {MVI, "PA,%b" }, // 00: 0110 0100 0000 0000 xxxx xxxx - {MVI, "PB,%b" }, // 01: 0110 0100 0000 0001 xxxx xxxx - {MVI, "PC,%b" }, // 02: 0110 0100 0000 0010 xxxx xxxx - {MVI, "PD,%b" }, // 03: 0110 0100 0000 0011 xxxx xxxx - { }, // 04: 0110 0100 0000 0100 xxxx xxxx - {MVI, "PF,%b" }, // 05: 0110 0100 0000 0101 xxxx xxxx - {MVI, "MKH,%b" }, // 06: 0110 0100 0000 0110 xxxx xxxx - {MVI, "MKL,%b" }, // 07: 0110 0100 0000 0111 xxxx xxxx - {ANI, "PA,%b" }, // 08: 0110 0100 0000 1000 xxxx xxxx - {ANI, "PB,%b" }, // 09: 0110 0100 0000 1001 xxxx xxxx - {ANI, "PC,%b" }, // 0a: 0110 0100 0000 1010 xxxx xxxx - {ANI, "PD,%b" }, // 0b: 0110 0100 0000 1011 xxxx xxxx - { }, // 0c: 0110 0100 0000 1100 xxxx xxxx - {ANI, "PF,%b" }, // 0d: 0110 0100 0000 1101 xxxx xxxx - {ANI, "MKH,%b" }, // 0e: 0110 0100 0000 1110 xxxx xxxx - {ANI, "MKL,%b" }, // 0f: 0110 0100 0000 1111 xxxx xxxx - {XRI, "PA,%b" }, // 10: 0110 0100 0001 0000 xxxx xxxx - {XRI, "PB,%b" }, // 11: 0110 0100 0001 0001 xxxx xxxx - {XRI, "PC,%b" }, // 12: 0110 0100 0001 0010 xxxx xxxx - {XRI, "PD,%b" }, // 13: 0110 0100 0001 0011 xxxx xxxx - { }, // 14: 0110 0100 0001 0100 xxxx xxxx - {XRI, "PF,%b" }, // 15: 0110 0100 0001 0101 xxxx xxxx - {XRI, "MKH,%b" }, // 16: 0110 0100 0001 0110 xxxx xxxx - {XRI, "MKL,%b" }, // 17: 0110 0100 0001 0111 xxxx xxxx - {ORI, "PA,%b" }, // 18: 0110 0100 0001 1000 xxxx xxxx - {ORI, "PB,%b" }, // 19: 0110 0100 0001 1001 xxxx xxxx - {ORI, "PC,%b" }, // 1a: 0110 0100 0001 1010 xxxx xxxx - {ORI, "PD,%b" }, // 1b: 0110 0100 0001 1011 xxxx xxxx - { }, // 1c: 0110 0100 0001 1100 xxxx xxxx - {ORI, "PF,%b" }, // 1d: 0110 0100 0001 1101 xxxx xxxx - {ORI, "MKH,%b" }, // 1e: 0110 0100 0001 1110 xxxx xxxx - {ORI, "MKL,%b" }, // 1f: 0110 0100 0001 1111 xxxx xxxx - {ADINC, "PA,%b" }, // 20: 0110 0100 0010 0000 xxxx xxxx - {ADINC, "PB,%b" }, // 21: 0110 0100 0010 0001 xxxx xxxx - {ADINC, "PC,%b" }, // 22: 0110 0100 0010 0010 xxxx xxxx - {ADINC, "PD,%b" }, // 23: 0110 0100 0010 0011 xxxx xxxx - { }, // 24: 0110 0100 0010 0100 xxxx xxxx - {ADINC, "PF,%b" }, // 25: 0110 0100 0010 0101 xxxx xxxx - {ADINC, "MKH,%b" }, // 26: 0110 0100 0010 0110 xxxx xxxx - {ADINC, "MKL,%b" }, // 27: 0110 0100 0010 0111 xxxx xxxx - {GTI, "PA,%b" }, // 28: 0110 0100 0010 1000 xxxx xxxx - {GTI, "PB,%b" }, // 29: 0110 0100 0010 1001 xxxx xxxx - {GTI, "PC,%b" }, // 2a: 0110 0100 0010 1010 xxxx xxxx - {GTI, "PD,%b" }, // 2b: 0110 0100 0010 1011 xxxx xxxx - { }, // 2c: 0110 0100 0010 1100 xxxx xxxx - {GTI, "PF,%b" }, // 2d: 0110 0100 0010 1101 xxxx xxxx - {GTI, "MKH,%b" }, // 2e: 0110 0100 0010 1110 xxxx xxxx - {GTI, "MKL,%b" }, // 2f: 0110 0100 0010 1111 xxxx xxxx +// main opcodes +const upd7810_base_disassembler::dasm_s upd7810_disassembler::XX_7810[256] = +{ + {NOP, nullptr }, // 00: 0000 0000 + {LDAW, "%a" }, // 01: 0000 0001 oooo oooo + {INX, "SP" }, // 02: 0000 0010 + {DCX, "SP" }, // 03: 0000 0011 + {LXI, "SP,%w" }, // 04: 0000 0100 llll llll hhhh hhhh + {ANIW, "%a,%b" }, // 05: 0000 0101 oooo oooo xxxx xxxx + { }, // 06: + {ANI, "A,%b" }, // 07: 0000 0111 xxxx xxxx + {MOV, "A,EAH" }, // 08: 0000 1000 + {MOV, "A,EAL" }, // 09: 0000 1001 + {MOV, "A,B" }, // 0a: 0000 1010 + {MOV, "A,C" }, // 0b: 0000 1011 + {MOV, "A,D" }, // 0c: 0000 1100 + {MOV, "A,E" }, // 0d: 0000 1101 + {MOV, "A,H" }, // 0e: 0000 1110 + {MOV, "A,L" }, // 0f: 0000 1111 - {SUINB, "PA,%b" }, // 30: 0110 0100 0011 0000 xxxx xxxx - {SUINB, "PB,%b" }, // 31: 0110 0100 0011 0001 xxxx xxxx - {SUINB, "PC,%b" }, // 32: 0110 0100 0011 0010 xxxx xxxx - {SUINB, "PD,%b" }, // 33: 0110 0100 0011 0011 xxxx xxxx - { }, // 34: 0110 0100 0011 0100 xxxx xxxx - {SUINB, "PF,%b" }, // 35: 0110 0100 0011 0101 xxxx xxxx - {SUINB, "MKH,%b" }, // 36: 0110 0100 0011 0110 xxxx xxxx - {SUINB, "MKL,%b" }, // 37: 0110 0100 0011 0111 xxxx xxxx - {LTI, "PA,%b" }, // 38: 0110 0100 0011 1000 xxxx xxxx - {LTI, "PB,%b" }, // 39: 0110 0100 0011 1001 xxxx xxxx - {LTI, "PC,%b" }, // 3a: 0110 0100 0011 1010 xxxx xxxx - {LTI, "PD,%b" }, // 3b: 0110 0100 0011 1011 xxxx xxxx - { }, // 3c: 0110 0100 0011 1100 xxxx xxxx - {LTI, "PF,%b" }, // 3d: 0110 0100 0011 1101 xxxx xxxx - {LTI, "MKH,%b" }, // 3e: 0110 0100 0011 1110 xxxx xxxx - {LTI, "MKL,%b" }, // 3f: 0110 0100 0011 1111 xxxx xxxx + {EXA, nullptr }, // 10: 0001 0000 7810 + {EXX, nullptr }, // 11: 0001 0001 7810 + {INX, "BC" }, // 12: 0001 0010 + {DCX, "BC" }, // 13: 0001 0011 + {LXI, "BC,%w" }, // 14: 0001 0100 llll llll hhhh hhhh + {ORIW, "%a,%b" }, // 15: 0001 0101 oooo oooo xxxx xxxx + {XRI, "A,%b" }, // 16: 0001 0110 xxxx xxxx + {ORI, "A,%b" }, // 17: 0001 0111 xxxx xxxx + {MOV, "EAH,A" }, // 18: 0001 1000 + {MOV, "EAL,A" }, // 19: 0001 1001 + {MOV, "B,A" }, // 1a: 0001 1010 + {MOV, "C,A" }, // 1b: 0001 1011 + {MOV, "D,A" }, // 1c: 0001 1100 + {MOV, "E,A" }, // 1d: 0001 1101 + {MOV, "H,A" }, // 1e: 0001 1110 + {MOV, "L,A" }, // 1f: 0001 1111 - {ADI, "PA,%b" }, // 40: 0110 0100 0100 0000 xxxx xxxx - {ADI, "PB,%b" }, // 41: 0110 0100 0100 0001 xxxx xxxx - {ADI, "PC,%b" }, // 42: 0110 0100 0100 0010 xxxx xxxx - {ADI, "PD,%b" }, // 43: 0110 0100 0100 0011 xxxx xxxx - { }, // 44: 0110 0100 0100 0100 xxxx xxxx - {ADI, "PF,%b" }, // 45: 0110 0100 0100 0101 xxxx xxxx - {ADI, "MKH,%b" }, // 46: 0110 0100 0100 0110 xxxx xxxx - {ADI, "MKL,%b" }, // 47: 0110 0100 0100 0111 xxxx xxxx - {ONI, "PA,%b" }, // 48: 0110 0100 0100 1000 xxxx xxxx - {ONI, "PB,%b" }, // 49: 0110 0100 0100 1001 xxxx xxxx - {ONI, "PC,%b" }, // 4a: 0110 0100 0100 1010 xxxx xxxx - {ONI, "PD,%b" }, // 4b: 0110 0100 0100 1011 xxxx xxxx - { }, // 4c: 0110 0100 0100 1100 xxxx xxxx - {ONI, "PF,%b" }, // 4d: 0110 0100 0100 1101 xxxx xxxx - {ONI, "MKH,%b" }, // 4e: 0110 0100 0100 1110 xxxx xxxx - {ONI, "MKL,%b" }, // 4f: 0110 0100 0100 1111 xxxx xxxx + {INRW, "%a" }, // 20: 0010 0000 oooo oooo + {JB, nullptr }, // 21: 0010 0001 + {INX, "DE" }, // 22: 0010 0010 + {DCX, "DE" }, // 23: 0010 0011 + {LXI, "DE,%w" }, // 24: 0010 0100 llll llll hhhh hhhh + {GTIW, "%a,%b" }, // 25: 0010 0101 oooo oooo xxxx xxxx + {ADINC, "A,%b" }, // 26: 0010 0110 xxxx xxxx + {GTI, "A,%b" }, // 27: 0010 0111 xxxx xxxx + { }, // 28: 0010 1000 + {LDAX, "(BC)" }, // 29: 0010 1001 + {LDAX, "(DE)" }, // 2a: 0010 1010 + {LDAX, "(HL)" }, // 2b: 0010 1011 + {LDAX, "(DE+)" }, // 2c: 0010 1100 + {LDAX, "(HL+)" }, // 2d: 0010 1101 + {LDAX, "(DE-)" }, // 2e: 0010 1110 + {LDAX, "(HL-)" }, // 2f: 0010 1111 - {ACI, "PA,%b" }, // 50: 0110 0100 0101 0000 xxxx xxxx - {ACI, "PB,%b" }, // 51: 0110 0100 0101 0001 xxxx xxxx - {ACI, "PC,%b" }, // 52: 0110 0100 0101 0010 xxxx xxxx - {ACI, "PD,%b" }, // 53: 0110 0100 0101 0011 xxxx xxxx - { }, // 54: 0110 0100 0101 0100 xxxx xxxx - {ACI, "PF,%b" }, // 55: 0110 0100 0101 0101 xxxx xxxx - {ACI, "MKH,%b" }, // 56: 0110 0100 0101 0110 xxxx xxxx - {ACI, "MKL,%b" }, // 57: 0110 0100 0101 0111 xxxx xxxx - {OFFI, "PA,%b" }, // 58: 0110 0100 0101 1000 xxxx xxxx - {OFFI, "PB,%b" }, // 59: 0110 0100 0101 1001 xxxx xxxx - {OFFI, "PC,%b" }, // 5a: 0110 0100 0101 1010 xxxx xxxx - {OFFI, "PD,%b" }, // 5b: 0110 0100 0101 1011 xxxx xxxx - { }, // 5c: 0110 0100 0101 1100 xxxx xxxx - {OFFI, "PF,%b" }, // 5d: 0110 0100 0101 1101 xxxx xxxx - {OFFI, "MKH,%b" }, // 5e: 0110 0100 0101 1110 xxxx xxxx - {OFFI, "MKL,%b" }, // 5f: 0110 0100 0101 1111 xxxx xxxx + {DCRW, "%a" }, // 30: 0011 0000 oooo oooo + {BLOCK, nullptr }, // 31: 0011 0001 7810 + {INX, "HL", }, // 32: 0011 0010 + {DCX, "HL", }, // 33: 0011 0011 + {LXI, "HL,%w" }, // 34: 0011 0100 llll llll hhhh hhhh + {LTIW, "%a,%b" }, // 35: 0011 0101 oooo oooo xxxx xxxx + {SUINB, "A,%b" }, // 36: 0011 0110 xxxx xxxx + {LTI, "A,%b" }, // 37: 0011 0111 xxxx xxxx + { }, // 38: + {STAX, "(BC)" }, // 39: 0011 1001 + {STAX, "(DE)" }, // 3a: 0011 1010 + {STAX, "(HL)" }, // 3b: 0011 1011 + {STAX, "(DE+)" }, // 3c: 0011 1100 + {STAX, "(HL+)" }, // 3d: 0011 1101 + {STAX, "(DE-)" }, // 3e: 0011 1110 + {STAX, "(HL-)" }, // 3f: 0011 1111 - {SUI, "PA,%b" }, // 60: 0110 0100 0110 0000 xxxx xxxx - {SUI, "PB,%b" }, // 61: 0110 0100 0110 0001 xxxx xxxx - {SUI, "PC,%b" }, // 62: 0110 0100 0110 0010 xxxx xxxx - {SUI, "PD,%b" }, // 63: 0110 0100 0110 0011 xxxx xxxx - { }, // 64: 0110 0100 0110 0100 xxxx xxxx - {SUI, "PF,%b" }, // 65: 0110 0100 0110 0101 xxxx xxxx - {SUI, "MKH,%b" }, // 66: 0110 0100 0110 0110 xxxx xxxx - {SUI, "MKL,%b" }, // 67: 0110 0100 0110 0111 xxxx xxxx - {NEI, "PA,%b" }, // 68: 0110 0100 0110 1000 xxxx xxxx - {NEI, "PB,%b" }, // 69: 0110 0100 0110 1001 xxxx xxxx - {NEI, "PC,%b" }, // 6a: 0110 0100 0110 1010 xxxx xxxx - {NEI, "PD,%b" }, // 6b: 0110 0100 0110 1011 xxxx xxxx - { }, // 6c: 0110 0100 0110 1100 xxxx xxxx - {NEI, "PF,%b" }, // 6d: 0110 0100 0110 1101 xxxx xxxx - {NEI, "MKH,%b" }, // 6e: 0110 0100 0110 1110 xxxx xxxx - {NEI, "MKL,%b" }, // 6f: 0110 0100 0110 1111 xxxx xxxx + {CALL, "%w" }, // 40: 0100 0000 llll llll hhhh hhhh + {INR, "A" }, // 41: 0100 0001 + {INR, "B" }, // 42: 0100 0010 + {INR, "C" }, // 43: 0100 0011 + {LXI, "EA,%w" }, // 44: 0100 0100 llll llll hhhh hhhh + {ONIW, "%a,%b" }, // 45: 0100 0101 oooo oooo xxxx xxxx + {ADI, "A,%b" }, // 46: 0100 0110 xxxx xxxx + {ONI, "A,%b" }, // 47: 0100 0111 xxxx xxxx + {d48_7810 }, // 48: prefix + {MVIX, "BC,%b" }, // 49: 0100 1001 xxxx xxxx + {MVIX, "DE,%b" }, // 4a: 0100 1010 xxxx xxxx + {MVIX, "HL,%b" }, // 4b: 0100 1011 xxxx xxxx + {d4C_7810 }, // 4c: prefix + {d4D_7810 }, // 4d: prefix + {JRE, "%d" }, // 4e: 0100 111d dddd dddd + {JRE, "%d" }, // 4f: 0100 111d dddd dddd - {SBI, "PA,%b" }, // 70: 0110 0100 0111 0000 xxxx xxxx - {SBI, "PB,%b" }, // 71: 0110 0100 0111 0001 xxxx xxxx - {SBI, "PC,%b" }, // 72: 0110 0100 0111 0010 xxxx xxxx - {SBI, "PD,%b" }, // 73: 0110 0100 0111 0011 xxxx xxxx - { }, // 74: 0110 0100 0111 0100 xxxx xxxx - {SBI, "PF,%b" }, // 75: 0110 0100 0111 0101 xxxx xxxx - {SBI, "MKH,%b" }, // 76: 0110 0100 0111 0110 xxxx xxxx - {SBI, "MKL,%b" }, // 77: 0110 0100 0111 0111 xxxx xxxx - {EQI, "PA,%b" }, // 78: 0110 0100 0111 1000 xxxx xxxx - {EQI, "PB,%b" }, // 79: 0110 0100 0111 1001 xxxx xxxx - {EQI, "PC,%b" }, // 7a: 0110 0100 0111 1010 xxxx xxxx - {EQI, "PD,%b" }, // 7b: 0110 0100 0111 1011 xxxx xxxx - { }, // 7c: 0110 0100 0111 1100 xxxx xxxx - {EQI, "PF,%b" }, // 7d: 0110 0100 0111 1101 xxxx xxxx - {EQI, "MKH,%b" }, // 7e: 0110 0100 0111 1110 xxxx xxxx - {EQI, "MKL,%b" }, // 7f: 0110 0100 0111 1111 xxxx xxxx + {EXH, nullptr }, // 50: 0101 0000 7810 + {DCR, "A" }, // 51: 0101 0001 + {DCR, "B" }, // 52: 0101 0010 + {DCR, "C" }, // 53: 0101 0011 + {JMP, "%w" }, // 54: 0101 0100 llll llll hhhh hhhh + {OFFIW, "%a,%b" }, // 55: 0101 0101 oooo oooo xxxx xxx + {ACI, "A,%b" }, // 56: 0101 0110 xxxx xxxx + {OFFI, "A,%b" }, // 57: 0101 0111 xxxx xxxx + {BIT, "0,%a", }, // 58: 0101 1000 oooo oooo 7810 + {BIT, "1,%a", }, // 59: 0101 1001 oooo oooo 7810 + {BIT, "2,%a", }, // 5a: 0101 1010 oooo oooo 7810 + {BIT, "3,%a", }, // 5b: 0101 1011 oooo oooo 7810 + {BIT, "4,%a", }, // 5c: 0101 1100 oooo oooo 7810 + {BIT, "5,%a", }, // 5d: 0101 1101 oooo oooo 7810 + {BIT, "6,%a", }, // 5e: 0101 1110 oooo oooo 7810 + {BIT, "7,%a", }, // 5f: 0101 1111 oooo oooo 7810 - { }, // 80: 0110 0100 1000 0000 xxxx xxxx - {MVI, "SMH,%b" }, // 81: 0110 0100 1000 0001 xxxx xxxx - { }, // 82: 0110 0100 1000 0010 xxxx xxxx - {MVI, "EOM,%b" }, // 83: 0110 0100 1000 0011 xxxx xxxx - { }, // 84: 0110 0100 1000 0100 xxxx xxxx - {MVI, "TMM,%b" }, // 85: 0110 0100 1000 0101 xxxx xxxx - { }, // 86: 0110 0100 1000 0110 xxxx xxxx - { }, // 87: 0110 0100 1000 0111 xxxx xxxx - { }, // 88: 0110 0100 1000 1000 xxxx xxxx - {ANI, "SMH,%b" }, // 89: 0110 0100 1000 1001 xxxx xxxx - { }, // 8a: 0110 0100 1000 1010 xxxx xxxx - {ANI, "EOM,%b" }, // 8b: 0110 0100 1000 1011 xxxx xxxx - { }, // 8c: 0110 0100 1000 1100 xxxx xxxx - {ANI, "TMM,%b" }, // 8d: 0110 0100 1000 1101 xxxx xxxx - { }, // 8e: 0110 0100 1000 1110 xxxx xxxx - { }, // 8f: 0110 0100 1000 1111 xxxx xxxx + {d60 }, // 60: prefix + {DAA, nullptr }, // 61: 0110 0001 + {RETI, nullptr }, // 62: 0110 0010 + {STAW, "%a" }, // 63: 0110 0011 oooo oooo + {d64_7810 }, // 64: prefix + {NEIW, "%a,%b" }, // 65: 0110 0101 oooo oooo xxxx xxxx + {SUI, "A,%b" }, // 66: 0110 0110 xxxx xxxx + {NEI, "A,%b" }, // 67: 0110 0111 xxxx xxxx + {MVI, "V,%b" }, // 68: 0110 1000 xxxx xxxx + {MVI, "A,%b" }, // 69: 0110 1001 xxxx xxxx + {MVI, "B,%b" }, // 6a: 0110 1010 xxxx xxxx + {MVI, "C,%b" }, // 6b: 0110 1011 xxxx xxxx + {MVI, "D,%b" }, // 6c: 0110 1100 xxxx xxxx + {MVI, "E,%b" }, // 6d: 0110 1101 xxxx xxxx + {MVI, "H,%b" }, // 6e: 0110 1110 xxxx xxxx + {MVI, "L,%b" }, // 6f: 0110 1111 xxxx xxxx - { }, // 90: 0110 0100 1001 0000 xxxx xxxx - {XRI, "SMH,%b" }, // 91: 0110 0100 1001 0001 xxxx xxxx - { }, // 92: 0110 0100 1001 0010 xxxx xxxx - {XRI, "EOM,%b" }, // 93: 0110 0100 1001 0011 xxxx xxxx - { }, // 94: 0110 0100 1001 0100 xxxx xxxx - {XRI, "TMM,%b" }, // 95: 0110 0100 1001 0101 xxxx xxxx - { }, // 96: 0110 0100 1001 0110 xxxx xxxx - { }, // 97: 0110 0100 1001 0111 xxxx xxxx - { }, // 98: 0110 0100 1001 1000 xxxx xxxx - {ORI, "SMH,%b" }, // 99: 0110 0100 1001 1001 xxxx xxxx - { }, // 9a: 0110 0100 1001 1010 xxxx xxxx - {ORI, "EOM,%b" }, // 9b: 0110 0100 1001 1011 xxxx xxxx - { }, // 9c: 0110 0100 1001 1100 xxxx xxxx - {ORI, "TMM,%b" }, // 9d: 0110 0100 1001 1101 xxxx xxxx - { }, // 9e: 0110 0100 1001 1110 xxxx xxxx - { }, // 9f: 0110 0100 1001 1111 xxxx xxxx + {d70 }, // 70: prefix + {MVIW, "%a,%b" }, // 71: 0111 0001 oooo oooo xxxx xxxx + {SOFTI, nullptr }, // 72: 0111 0010 + { }, // 73: + {d74 }, // 74: prefix + {EQIW, "%a,%b" }, // 75: 0111 0101 oooo oooo xxxx xxxx + {SBI, "A,%b" }, // 76: 0111 0110 xxxx xxxx + {EQI, "A,%b" }, // 77: 0111 0111 xxxx xxxx + {CALF, "%f" }, // 78: 0111 1ddd dddd dddd + {CALF, "%f" }, // 79: 0111 1ddd dddd dddd + {CALF, "%f" }, // 7a: 0111 1ddd dddd dddd + {CALF, "%f" }, // 7b: 0111 1ddd dddd dddd + {CALF, "%f" }, // 7c: 0111 1ddd dddd dddd + {CALF, "%f" }, // 7d: 0111 1ddd dddd dddd + {CALF, "%f" }, // 7e: 0111 1ddd dddd dddd + {CALF, "%f" }, // 7f: 0111 1ddd dddd dddd - { }, // a0: 0110 0100 1010 0000 xxxx xxxx - {ADINC, "SMH,%b" }, // a1: 0110 0100 1010 0001 xxxx xxxx - { }, // a2: 0110 0100 1010 0010 xxxx xxxx - {ADINC, "EOM,%b" }, // a3: 0110 0100 1010 0011 xxxx xxxx - { }, // a4: 0110 0100 1010 0100 xxxx xxxx - {ADINC, "TMM,%b" }, // a5: 0110 0100 1010 0101 xxxx xxxx - { }, // a6: 0110 0100 1010 0110 xxxx xxxx - { }, // a7: 0110 0100 1010 0111 xxxx xxxx - { }, // a8: 0110 0100 1010 1000 xxxx xxxx - {GTI, "SMH,%b" }, // a9: 0110 0100 1010 1001 xxxx xxxx - { }, // aa: 0110 0100 1010 1010 xxxx xxxx - {GTI, "EOM,%b" }, // ab: 0110 0100 1010 1011 xxxx xxxx - { }, // ac: 0110 0100 1010 1100 xxxx xxxx - {GTI, "TMM,%b" }, // ad: 0110 0100 1010 1101 xxxx xxxx - {GTI, "PT,%b" }, // ae: 0110 0100 1010 1110 xxxx xxxx - { }, // af: 0110 0100 1010 1111 xxxx xxxx + {CALT, "%t" }, // 80: 100t tttt + {CALT, "%t" }, // 81: 100t tttt + {CALT, "%t" }, // 82: 100t tttt + {CALT, "%t" }, // 83: 100t tttt + {CALT, "%t" }, // 84: 100t tttt + {CALT, "%t" }, // 85: 100t tttt + {CALT, "%t" }, // 86: 100t tttt + {CALT, "%t" }, // 87: 100t tttt + {CALT, "%t" }, // 88: 100t tttt + {CALT, "%t" }, // 89: 100t tttt + {CALT, "%t" }, // 8a: 100t tttt + {CALT, "%t" }, // 8b: 100t tttt + {CALT, "%t" }, // 8c: 100t tttt + {CALT, "%t" }, // 8d: 100t tttt + {CALT, "%t" }, // 8e: 100t tttt + {CALT, "%t" }, // 8f: 100t tttt - { }, // b0: 0110 0100 1011 0000 xxxx xxxx - {SUINB, "SMH,%b" }, // b1: 0110 0100 1011 0001 xxxx xxxx - { }, // b2: 0110 0100 1011 0010 xxxx xxxx - {SUINB, "EOM,%b" }, // b3: 0110 0100 1011 0011 xxxx xxxx - { }, // b4: 0110 0100 1011 0100 xxxx xxxx - {SUINB, "TMM,%b" }, // b5: 0110 0100 1011 0101 xxxx xxxx - { }, // b6: 0110 0100 1011 0110 xxxx xxxx - { }, // b7: 0110 0100 1011 0111 xxxx xxxx - { }, // b8: 0110 0100 1011 1000 xxxx xxxx - {LTI, "SMH,%b" }, // b9: 0110 0100 1011 1001 xxxx xxxx - { }, // ba: 0110 0100 1011 1010 xxxx xxxx - {LTI, "EOM,%b" }, // bb: 0110 0100 1011 1011 xxxx xxxx - { }, // bc: 0110 0100 1011 1100 xxxx xxxx - {LTI, "TMM,%b" }, // bd: 0110 0100 1011 1101 xxxx xxxx - {LTI, "PT,%b" }, // be: 0110 0100 1011 1110 xxxx xxxx - { }, // bf: 0110 0100 1011 1111 xxxx xxxx + {CALT, "%t" }, // 90: 100t tttt + {CALT, "%t" }, // 91: 100t tttt + {CALT, "%t" }, // 92: 100t tttt + {CALT, "%t" }, // 93: 100t tttt + {CALT, "%t" }, // 94: 100t tttt + {CALT, "%t" }, // 95: 100t tttt + {CALT, "%t" }, // 96: 100t tttt + {CALT, "%t" }, // 97: 100t tttt + {CALT, "%t" }, // 98: 100t tttt + {CALT, "%t" }, // 99: 100t tttt + {CALT, "%t" }, // 9a: 100t tttt + {CALT, "%t" }, // 9b: 100t tttt + {CALT, "%t" }, // 9c: 100t tttt + {CALT, "%t" }, // 9d: 100t tttt + {CALT, "%t" }, // 9e: 100t tttt + {CALT, "%t" }, // 9f: 100t tttt - { }, // c0: 0110 0100 1100 0000 xxxx xxxx - {ADI, "SMH,%b" }, // c1: 0110 0100 1100 0001 xxxx xxxx - { }, // c2: 0110 0100 1100 0010 xxxx xxxx - {ADI, "EOM,%b" }, // c3: 0110 0100 1100 0011 xxxx xxxx - { }, // c4: 0110 0100 1100 0100 xxxx xxxx - {ADI, "TMM,%b" }, // c5: 0110 0100 1100 0101 xxxx xxxx - { }, // c6: 0110 0100 1100 0110 xxxx xxxx - { }, // c7: 0110 0100 1100 0111 xxxx xxxx - { }, // c8: 0110 0100 1100 1000 xxxx xxxx - {ONI, "SMH,%b" }, // c9: 0110 0100 1100 1001 xxxx xxxx - { }, // ca: 0110 0100 1100 1010 xxxx xxxx - {ONI, "EOM,%b" }, // cb: 0110 0100 1100 1011 xxxx xxxx - { }, // cc: 0110 0100 1100 1100 xxxx xxxx - {ONI, "TMM,%b" }, // cd: 0110 0100 1100 1101 xxxx xxxx - {ONI, "PT,%b" }, // ce: 0110 0100 1100 1110 xxxx xxxx - { }, // cf: 0110 0100 1100 1111 xxxx xxxx + {POP, "VA" }, // a0: 1010 0000 + {POP, "BC" }, // a1: 1010 0001 + {POP, "DE" }, // a2: 1010 0010 + {POP, "HL", }, // a3: 1010 0011 + {POP, "EA" }, // a4: 1010 0100 + {DMOV, "EA,BC" }, // a5: 1010 0101 + {DMOV, "EA,DE" }, // a6: 1010 0110 + {DMOV, "EA,HL" }, // a7: 1010 0111 + {INX, "EA" }, // a8: 1010 1000 + {DCX, "EA" }, // a9: 1010 1001 + {EI, nullptr }, // aa: 1010 1010 + {LDAX, "(DE+%b)" }, // ab: 1010 1011 dddd dddd + {LDAX, "(HL+A)" }, // ac: 1010 1100 + {LDAX, "(HL+B)" }, // ad: 1010 1101 + {LDAX, "(HL+EA)" }, // ae: 1010 1110 + {LDAX, "(HL+%b)" }, // af: 1010 1111 dddd dddd - { }, // d0: 0110 0100 1101 0000 xxxx xxxx - {ACI, "SMH,%b" }, // d1: 0110 0100 1101 0001 xxxx xxxx - { }, // d2: 0110 0100 1101 0010 xxxx xxxx - {ACI, "EOM,%b" }, // d3: 0110 0100 1101 0011 xxxx xxxx - { }, // d4: 0110 0100 1101 0100 xxxx xxxx - {ACI, "TMM,%b" }, // d5: 0110 0100 1101 0101 xxxx xxxx - { }, // d6: 0110 0100 1101 0110 xxxx xxxx - { }, // d7: 0110 0100 1101 0111 xxxx xxxx - { }, // d8: 0110 0100 1101 1000 xxxx xxxx - {OFFI, "SMH,%b" }, // d9: 0110 0100 1101 1001 xxxx xxxx - { }, // da: 0110 0100 1101 1010 xxxx xxxx - {OFFI, "EOM,%b" }, // db: 0110 0100 1101 1011 xxxx xxxx - { }, // dc: 0110 0100 1101 1100 xxxx xxxx - {OFFI, "TMM,%b" }, // dd: 0110 0100 1101 1101 xxxx xxxx - {OFFI, "PT,%b" }, // de: 0110 0100 1101 1110 xxxx xxxx - { }, // df: 0110 0100 1101 1111 xxxx xxxx + {PUSH, "VA" }, // b0: 1011 0000 + {PUSH, "BC" }, // b1: 1011 0001 + {PUSH, "DE" }, // b2: 1011 0010 + {PUSH, "HL", }, // b3: 1011 0011 + {PUSH, "EA" }, // b4: 1011 0100 + {DMOV, "BC,EA" }, // b5: 1011 0101 + {DMOV, "DE,EA" }, // b6: 1011 0110 + {DMOV, "HL,EA" }, // b7: 1011 0111 + {RET, nullptr }, // b8: 1011 1000 + {RETS, nullptr }, // b9: 1011 1001 + {DI, nullptr }, // ba: 1011 1010 + {STAX, "(DE+%b)" }, // bb: 1011 1011 dddd dddd + {STAX, "(HL+A)" }, // bc: 1011 1100 + {STAX, "(HL+B)" }, // bd: 1011 1101 + {STAX, "(HL+EA)" }, // be: 1011 1110 + {STAX, "(HL+%b)" }, // bf: 1011 1111 dddd dddd - { }, // e0: 0110 0100 1110 0000 xxxx xxxx - {SUI, "SMH,%b" }, // e1: 0110 0100 1110 0001 xxxx xxxx - { }, // e2: 0110 0100 1110 0010 xxxx xxxx - {SUI, "EOM,%b" }, // e3: 0110 0100 1110 0011 xxxx xxxx - { }, // e4: 0110 0100 1110 0100 xxxx xxxx - {SUI, "TMM,%b" }, // e5: 0110 0100 1110 0101 xxxx xxxx - { }, // e6: 0110 0100 1110 0110 xxxx xxxx - { }, // e7: 0110 0100 1110 0111 xxxx xxxx - { }, // e8: 0110 0100 1110 1000 xxxx xxxx - {NEI, "SMH,%b" }, // e9: 0110 0100 1110 1001 xxxx xxxx - { }, // ea: 0110 0100 1110 1010 xxxx xxxx - {NEI, "EOM,%b" }, // eb: 0110 0100 1110 1011 xxxx xxxx - { }, // ec: 0110 0100 1110 1100 xxxx xxxx - {NEI, "TMM,%b" }, // ed: 0110 0100 1110 1101 xxxx xxxx - {NEI, "PT,%b" }, // ee: 0110 0100 1110 1110 xxxx xxxx - { }, // ef: 0110 0100 1110 1111 xxxx xxxx + {JR, "%o" }, // c0: 11oo oooo + {JR, "%o" }, // c1: 11oo oooo + {JR, "%o" }, // c2: 11oo oooo + {JR, "%o" }, // c3: 11oo oooo + {JR, "%o" }, // c4: 11oo oooo + {JR, "%o" }, // c5: 11oo oooo + {JR, "%o" }, // c6: 11oo oooo + {JR, "%o" }, // c7: 11oo oooo + {JR, "%o" }, // c8: 11oo oooo + {JR, "%o" }, // c9: 11oo oooo + {JR, "%o" }, // ca: 11oo oooo + {JR, "%o" }, // cb: 11oo oooo + {JR, "%o" }, // cc: 11oo oooo + {JR, "%o" }, // cd: 11oo oooo + {JR, "%o" }, // ce: 11oo oooo + {JR, "%o" }, // cf: 11oo oooo - { }, // f0: 0110 0100 1111 0000 xxxx xxxx - {SBI, "SMH,%b" }, // f1: 0110 0100 1111 0001 xxxx xxxx - { }, // f2: 0110 0100 1111 0010 xxxx xxxx - {SBI, "EOM,%b" }, // f3: 0110 0100 1111 0011 xxxx xxxx - { }, // f4: 0110 0100 1111 0100 xxxx xxxx - {SBI, "TMM,%b" }, // f5: 0110 0100 1111 0101 xxxx xxxx - { }, // f6: 0110 0100 1111 0110 xxxx xxxx - { }, // f7: 0110 0100 1111 0111 xxxx xxxx - { }, // f8: 0110 0100 1111 1000 xxxx xxxx - {EQI, "SMH,%b" }, // f9: 0110 0100 1111 1001 xxxx xxxx - { }, // fa: 0110 0100 1111 1010 xxxx xxxx - {EQI, "EOM,%b" }, // fb: 0110 0100 1111 1011 xxxx xxxx - { }, // fc: 0110 0100 1111 1100 xxxx xxxx - {EQI, "TMM,%b" }, // fd: 0110 0100 1111 1101 xxxx xxxx - {EQI, "PT,%b" }, // fe: 0110 0100 1111 1110 xxxx xxxx - { } // ff: 0110 0100 1111 1111 xxxx xxxx + {JR, "%o" }, // d0: 11oo oooo + {JR, "%o" }, // d1: 11oo oooo + {JR, "%o" }, // d2: 11oo oooo + {JR, "%o" }, // d3: 11oo oooo + {JR, "%o" }, // d4: 11oo oooo + {JR, "%o" }, // d5: 11oo oooo + {JR, "%o" }, // d6: 11oo oooo + {JR, "%o" }, // d7: 11oo oooo + {JR, "%o" }, // d8: 11oo oooo + {JR, "%o" }, // d9: 11oo oooo + {JR, "%o" }, // da: 11oo oooo + {JR, "%o" }, // db: 11oo oooo + {JR, "%o" }, // dc: 11oo oooo + {JR, "%o" }, // dd: 11oo oooo + {JR, "%o" }, // de: 11oo oooo + {JR, "%o" }, // df: 11oo oooo + + {JR, "%o" }, // e0: 11oo oooo + {JR, "%o" }, // e1: 11oo oooo + {JR, "%o" }, // e2: 11oo oooo + {JR, "%o" }, // e3: 11oo oooo + {JR, "%o" }, // e4: 11oo oooo + {JR, "%o" }, // e5: 11oo oooo + {JR, "%o" }, // e6: 11oo oooo + {JR, "%o" }, // e7: 11oo oooo + {JR, "%o" }, // e8: 11oo oooo + {JR, "%o" }, // e9: 11oo oooo + {JR, "%o" }, // ea: 11oo oooo + {JR, "%o" }, // eb: 11oo oooo + {JR, "%o" }, // ec: 11oo oooo + {JR, "%o" }, // ed: 11oo oooo + {JR, "%o" }, // ee: 11oo oooo + {JR, "%o" }, // ef: 11oo oooo + + {JR, "%o" }, // f0: 11oo oooo + {JR, "%o" }, // f1: 11oo oooo + {JR, "%o" }, // f2: 11oo oooo + {JR, "%o" }, // f3: 11oo oooo + {JR, "%o" }, // f4: 11oo oooo + {JR, "%o" }, // f5: 11oo oooo + {JR, "%o" }, // f6: 11oo oooo + {JR, "%o" }, // f7: 11oo oooo + {JR, "%o" }, // f8: 11oo oooo + {JR, "%o" }, // f9: 11oo oooo + {JR, "%o" }, // fa: 11oo oooo + {JR, "%o" }, // fb: 11oo oooo + {JR, "%o" }, // fc: 11oo oooo + {JR, "%o" }, // fd: 11oo oooo + {JR, "%o" }, // fe: 11oo oooo + {JR, "%o" } // ff: 11oo oooo }; -// prefix 70 -const dasm_s dasm_s::d70[256] = +const upd7810_base_disassembler::dasm_s upd7807_disassembler::d48_7807[256] = { - { }, // 00: 0111 0000 0000 0000 - { }, // 01: 0111 0000 0000 0001 - { }, // 02: 0111 0000 0000 0010 - { }, // 03: 0111 0000 0000 0011 - { }, // 04: 0111 0000 0000 0100 - { }, // 05: 0111 0000 0000 0101 - { }, // 06: 0111 0000 0000 0110 - { }, // 07: 0111 0000 0000 0111 - { }, // 08: 0111 0000 0000 1000 - { }, // 09: 0111 0000 0000 1001 - { }, // 0a: 0111 0000 0000 1010 - { }, // 0b: 0111 0000 0000 1011 - { }, // 0c: 0111 0000 0000 1100 - { }, // 0d: 0111 0000 0000 1101 - {SSPD, "%w" }, // 0e: 0111 0000 0000 1110 llll llll hhhh hhhh - {LSPD, "%w" }, // 0f: 0111 0000 0000 1111 llll llll hhhh hhhh - - { }, // 10: 0111 0000 0001 0000 - { }, // 11: 0111 0000 0001 0001 - { }, // 12: 0111 0000 0001 0010 - { }, // 13: 0111 0000 0001 0011 - { }, // 14: 0111 0000 0001 0100 - { }, // 15: 0111 0000 0001 0101 - { }, // 16: 0111 0000 0001 0110 - { }, // 17: 0111 0000 0001 0111 - { }, // 18: 0111 0000 0001 1000 - { }, // 19: 0111 0000 0001 1001 - { }, // 1a: 0111 0000 0001 1010 - { }, // 1b: 0111 0000 0001 1011 - { }, // 1c: 0111 0000 0001 1100 - { }, // 1d: 0111 0000 0001 1101 - {SBCD, "%w" }, // 1e: 0111 0000 0001 1110 llll llll hhhh hhhh - {LBCD, "%w" }, // 1f: 0111 0000 0001 1111 llll llll hhhh hhhh + { }, // 00: 0100 1000 0000 0000 + {SLRC, "A" }, // 01: 0100 1000 0000 0001 + {SLRC, "B" }, // 02: 0100 1000 0000 0010 + {SLRC, "C" }, // 03: 0100 1000 0000 0011 + { }, // 04: 0100 1000 0000 0100 + {SLLC, "A" }, // 05: 0100 1000 0000 0101 + {SLLC, "B" }, // 06: 0100 1000 0000 0110 + {SLLC, "C" }, // 07: 0100 1000 0000 0111 + {SK, "NV" }, // 08: 0100 1000 0000 1000 + { }, // 09: 0100 1000 0000 1001 + {SK, "CY" }, // 0a: 0100 1000 0000 1010 + {SK, "HC" }, // 0b: 0100 1000 0000 1011 + {SK, "Z" }, // 0c: 0100 1000 0000 1100 + { }, // 0d: 0100 1000 0000 1101 + { }, // 0e: 0100 1000 0000 1110 + { }, // 0f: 0100 1000 0000 1111 + + { }, // 10: 0100 1000 0001 0000 + { }, // 11: 0100 1000 0001 0001 + { }, // 12: 0100 1000 0001 0010 + { }, // 13: 0100 1000 0001 0011 + { }, // 14: 0100 1000 0001 0100 + { }, // 15: 0100 1000 0001 0101 + { }, // 16: 0100 1000 0001 0110 + { }, // 17: 0100 1000 0001 0111 + {SKN, "NV" }, // 18: 0100 1000 0001 1000 + { }, // 19: 0100 1000 0001 1001 + {SKN, "CY" }, // 1a: 0100 1000 0001 1010 + {SKN, "HC" }, // 1b: 0100 1000 0001 1011 + {SKN, "Z" }, // 1c: 0100 1000 0001 1100 + { }, // 1d: 0100 1000 0001 1101 + { }, // 1e: 0100 1000 0001 1110 + { }, // 1f: 0100 1000 0001 1111 + + { }, // 20: 0100 1000 0010 0000 + {SLR, "A" }, // 21: 0100 1000 0010 0001 + {SLR, "B" }, // 22: 0100 1000 0010 0010 + {SLR, "C" }, // 23: 0100 1000 0010 0011 + { }, // 24: 0100 1000 0010 0100 + {SLL, "A" }, // 25: 0100 1000 0010 0101 + {SLL, "B" }, // 26: 0100 1000 0010 0110 + {SLL, "C" }, // 27: 0100 1000 0010 0111 + {JEA, nullptr }, // 28: 0100 1000 0010 1000 + {CALB, nullptr }, // 29: 0100 1000 0010 1001 + {CLC, nullptr }, // 2a: 0100 1000 0010 1010 + {STC, nullptr }, // 2b: 0100 1000 0010 1011 + { }, // 2c: 0100 1000 0010 1100 + {MUL, "A" }, // 2d: 0100 1000 0010 1101 + {MUL, "B" }, // 2e: 0100 1000 0010 1110 + {MUL, "C" }, // 2f: 0100 1000 0010 1111 + + { }, // 30: 0100 1000 0011 0000 + {RLR, "A" }, // 31: 0100 1000 0011 0001 + {RLR, "B" }, // 32: 0100 1000 0011 0010 + {RLR, "C" }, // 33: 0100 1000 0011 0011 + { }, // 34: 0100 1000 0011 0100 + {RLL, "A" }, // 35: 0100 1000 0011 0101 + {RLL, "B" }, // 36: 0100 1000 0011 0110 + {RLL, "C" }, // 37: 0100 1000 0011 0111 + {RLD, nullptr }, // 38: 0100 1000 0011 1000 + {RRD, nullptr }, // 39: 0100 1000 0011 1001 + {NEGA, nullptr }, // 3a: 0100 1000 0011 1010 + {HALT, nullptr }, // 3b: 0100 1000 0011 1011 + { }, // 3c: 0100 1000 0011 1100 + {DIV, "A" }, // 3d: 0100 1000 0011 1101 + {DIV, "B" }, // 3e: 0100 1000 0011 1110 + {DIV, "C" }, // 3f: 0100 1000 0011 1111 + + {SKIT, "NMI" }, // 40: 0100 1000 0100 0000 + {SKIT, "FT0" }, // 41: 0100 1000 0100 0001 + {SKIT, "FT1" }, // 42: 0100 1000 0100 0010 + {SKIT, "F1" }, // 43: 0100 1000 0100 0011 + {SKIT, "F2" }, // 44: 0100 1000 0100 0100 + {SKIT, "FE0" }, // 45: 0100 1000 0100 0101 + {SKIT, "FE1" }, // 46: 0100 1000 0100 0110 + {SKIT, "FEIN" }, // 47: 0100 1000 0100 0111 + {SKIT, "FAD" }, // 48: 0100 1000 0100 1000 + {SKIT, "FSR" }, // 49: 0100 1000 0100 1001 + {SKIT, "FST" }, // 4a: 0100 1000 0100 1010 + {SKIT, "ER" }, // 4b: 0100 1000 0100 1011 + {SKIT, "OV" }, // 4c: 0100 1000 0100 1100 + { }, // 4d: 0100 1000 0100 1101 + { }, // 4e: 0100 1000 0100 1110 + { }, // 4f: 0100 1000 0100 1111 + + {SKIT, "AN4" }, // 50: 0100 1000 0101 0000 + {SKIT, "AN5" }, // 51: 0100 1000 0101 0001 + {SKIT, "AN6" }, // 52: 0100 1000 0101 0010 + {SKIT, "AN7" }, // 53: 0100 1000 0101 0011 + {SKIT, "SB" }, // 54: 0100 1000 0101 0100 + { }, // 55: 0100 1000 0101 0101 + { }, // 56: 0100 1000 0101 0110 + { }, // 57: 0100 1000 0101 0111 + { }, // 58: 0100 1000 0101 1000 + { }, // 59: 0100 1000 0101 1001 + { }, // 5a: 0100 1000 0101 1010 + { }, // 5b: 0100 1000 0101 1011 + { }, // 5c: 0100 1000 0101 1100 + { }, // 5d: 0100 1000 0101 1101 + { }, // 5e: 0100 1000 0101 1110 + { }, // 5f: 0100 1000 0101 1111 + + {SKNIT, "NMI" }, // 60: 0100 1000 0110 0000 + {SKNIT, "FT0" }, // 61: 0100 1000 0110 0001 + {SKNIT, "FT1" }, // 62: 0100 1000 0110 0010 + {SKNIT, "F1" }, // 63: 0100 1000 0110 0011 + {SKNIT, "F2" }, // 64: 0100 1000 0110 0100 + {SKNIT, "FE0" }, // 65: 0100 1000 0110 0101 + {SKNIT, "FE1" }, // 66: 0100 1000 0110 0110 + {SKNIT, "FEIN" }, // 67: 0100 1000 0110 0111 + {SKNIT, "FAD" }, // 68: 0100 1000 0110 1000 + {SKNIT, "FSR" }, // 69: 0100 1000 0110 1001 + {SKNIT, "FST" }, // 6a: 0100 1000 0110 1010 + {SKNIT, "ER" }, // 6b: 0100 1000 0110 1011 + {SKNIT, "OV" }, // 6c: 0100 1000 0110 1100 + { }, // 6d: 0100 1000 0110 1101 + { }, // 6e: 0100 1000 0110 1110 + { }, // 6f: 0100 1000 0110 1111 + + {SKNIT, "AN4" }, // 70: 0100 1000 0111 0000 + {SKNIT, "AN5" }, // 71: 0100 1000 0111 0001 + {SKNIT, "AN6" }, // 72: 0100 1000 0111 0010 + {SKNIT, "AN7" }, // 73: 0100 1000 0111 0011 + {SKNIT, "SB" }, // 74: 0100 1000 0111 0100 + { }, // 75: 0100 1000 0111 0101 + { }, // 76: 0100 1000 0111 0110 + { }, // 77: 0100 1000 0111 0111 + { }, // 78: 0100 1000 0111 1000 + { }, // 79: 0100 1000 0111 1001 + { }, // 7a: 0100 1000 0111 1010 + { }, // 7b: 0100 1000 0111 1011 + { }, // 7c: 0100 1000 0111 1100 + { }, // 7d: 0100 1000 0111 1101 + { }, // 7e: 0100 1000 0111 1110 + { }, // 7f: 0100 1000 0111 1111 + + { }, // 80: 0100 1000 1000 0000 + { }, // 81: 0100 1000 1000 0001 + {LDEAX, "(DE)" }, // 82: 0100 1000 1000 0010 + {LDEAX, "(HL)" }, // 83: 0100 1000 1000 0011 + {LDEAX, "(DE++)" }, // 84: 0100 1000 1000 0100 + {LDEAX, "(HL++)" }, // 85: 0100 1000 1000 0101 + { }, // 86: 0100 1000 1000 0110 + { }, // 87: 0100 1000 1000 0111 + { }, // 88: 0100 1000 1000 1000 + { }, // 89: 0100 1000 1000 1001 + { }, // 8a: 0100 1000 1000 1010 + {LDEAX, "(DE+%b)" }, // 8b: 0100 1000 1000 1011 xxxx xxxx + {LDEAX, "(HL+A)" }, // 8c: 0100 1000 1000 1100 + {LDEAX, "(HL+B)" }, // 8d: 0100 1000 1000 1101 + {LDEAX, "(HL+EA)" }, // 8e: 0100 1000 1000 1110 + {LDEAX, "(HL+%b)" }, // 8f: 0100 1000 1000 1111 xxxx xxxx + + { }, // 90: 0100 1000 1000 0000 + { }, // 91: 0100 1000 1000 0001 + {STEAX, "(DE)" }, // 92: 0100 1000 1000 0010 + {STEAX, "(HL)" }, // 93: 0100 1000 1000 0011 + {STEAX, "(DE++)" }, // 94: 0100 1000 1000 0100 + {STEAX, "(HL++)" }, // 95: 0100 1000 1000 0101 + { }, // 96: 0100 1000 1000 0110 + { }, // 97: 0100 1000 1000 0111 + { }, // 98: 0100 1000 1000 1000 + { }, // 99: 0100 1000 1000 1001 + { }, // 9a: 0100 1000 1000 1010 + {STEAX, "(DE+%b)" }, // 9b: 0100 1000 1000 1011 xxxx xxxx + {STEAX, "(HL+A)" }, // 9c: 0100 1000 1000 1100 + {STEAX, "(HL+B)" }, // 9d: 0100 1000 1000 1101 + {STEAX, "(HL+EA)" }, // 9e: 0100 1000 1000 1110 + {STEAX, "(HL+%b)" }, // 9f: 0100 1000 1000 1111 xxxx xxxx + + {DSLR, "EA" }, // a0: 0100 1000 1010 0000 + { }, // a1: 0100 1000 1010 0001 + { }, // a2: 0100 1000 1010 0010 + { }, // a3: 0100 1000 1010 0011 + {DSLL, "EA" }, // a4: 0100 1000 1010 0100 + { }, // a5: 0100 1000 1010 0101 + { }, // a6: 0100 1000 1010 0110 + { }, // a7: 0100 1000 1010 0111 + {TABLE, nullptr }, // a8: 0100 1000 1010 1000 + { }, // a9: 0100 1000 1010 1001 + {CMC, nullptr }, // aa: 0100 1000 1010 1010 7807 + { }, // ab: 0100 1000 1010 1011 + {EXA, nullptr }, // ac: 0100 1000 1010 1100 7807 + {EXR, nullptr }, // ad: 0100 1000 1010 1101 7807 + {EXH, nullptr }, // ae: 0100 1000 1010 1110 7807 + {EXX, nullptr }, // af: 0100 1000 1010 1111 7807 + + {DRLR, "EA" }, // b0: 0100 1000 1011 0000 + { }, // b1: 0100 1000 1011 0001 + { }, // b2: 0100 1000 1011 0010 + { }, // b3: 0100 1000 1011 0011 + {DRLL, "EA" }, // b4: 0100 1000 1011 0100 + { }, // b5: 0100 1000 1011 0101 + { }, // b6: 0100 1000 1011 0110 + { }, // b7: 0100 1000 1011 0111 + { }, // b8: 0100 1000 1011 1000 + { }, // b9: 0100 1000 1011 1001 + { }, // ba: 0100 1000 1011 1010 + { }, // bb: 0100 1000 1011 1011 + { }, // bc: 0100 1000 1011 1100 + { }, // bd: 0100 1000 1011 1101 + { }, // be: 0100 1000 1011 1110 + { }, // bf: 0100 1000 1011 1111 + + {DMOV, "EA,ECNT" }, // c0: 0100 1000 1100 0000 + {DMOV, "EA,ECPT0"}, // c1: 0100 1000 1100 0001 7807 + {DMOV, "EA,ECPT1"}, // c2: 0100 1000 1100 0010 7807 + { }, // c3: 0100 1000 1100 0011 + { }, // c4: 0100 1000 1100 0100 + { }, // c5: 0100 1000 1100 0101 + { }, // c6: 0100 1000 1100 0110 + { }, // c7: 0100 1000 1100 0111 + { }, // c8: 0100 1000 1100 1000 + { }, // c9: 0100 1000 1100 1001 + { }, // ca: 0100 1000 1100 1010 + { }, // cb: 0100 1000 1100 1011 + { }, // cc: 0100 1000 1100 1100 + { }, // cd: 0100 1000 1100 1101 + { }, // ce: 0100 1000 1100 1110 + { }, // cf: 0100 1000 1100 1111 + + { }, // d0: 0100 1000 1101 0000 + { }, // d1: 0100 1000 1101 0001 + {DMOV, "ETM0,EA" }, // d2: 0100 1000 1101 0010 + {DMOV, "ETM1,EA" }, // d3: 0100 1000 1101 0011 + { }, // d4: 0100 1000 1101 0100 + { }, // d5: 0100 1000 1101 0101 + { }, // d6: 0100 1000 1101 0110 + { }, // d7: 0100 1000 1101 0111 + { }, // d8: 0100 1000 1101 1000 + { }, // d9: 0100 1000 1101 1001 + { }, // da: 0100 1000 1101 1010 + { }, // db: 0100 1000 1101 1011 + { }, // dc: 0100 1000 1101 1100 + { }, // dd: 0100 1000 1101 1101 + { }, // de: 0100 1000 1101 1110 + { }, // df: 0100 1000 1101 1111 + + { }, // e0: 0100 1000 1110 0000 + { }, // e1: 0100 1000 1110 0001 + { }, // e2: 0100 1000 1110 0010 + { }, // e3: 0100 1000 1110 0011 + { }, // e4: 0100 1000 1110 0100 + { }, // e5: 0100 1000 1110 0101 + { }, // e6: 0100 1000 1110 0110 + { }, // e7: 0100 1000 1110 0111 + { }, // e8: 0100 1000 1110 1000 + { }, // e9: 0100 1000 1110 1001 + { }, // ea: 0100 1000 1110 1010 + { }, // eb: 0100 1000 1110 1011 + { }, // ec: 0100 1000 1110 1100 + { }, // ed: 0100 1000 1110 1101 + { }, // ee: 0100 1000 1110 1110 + { }, // ef: 0100 1000 1110 1111 + + { }, // f0: 0100 1000 1111 0000 + { }, // f1: 0100 1000 1111 0001 + { }, // f2: 0100 1000 1111 0010 + { }, // f3: 0100 1000 1111 0011 + { }, // f4: 0100 1000 1111 0100 + { }, // f5: 0100 1000 1111 0101 + { }, // f6: 0100 1000 1111 0110 + { }, // f7: 0100 1000 1111 0111 + { }, // f8: 0100 1000 1111 1000 + { }, // f9: 0100 1000 1111 1001 + { }, // fa: 0100 1000 1111 1010 + { }, // fb: 0100 1000 1111 1011 + { }, // fc: 0100 1000 1111 1100 + { }, // fd: 0100 1000 1111 1101 + { }, // fe: 0100 1000 1111 1110 + { } // ff: 0100 1000 1111 1111 +}; - { }, // 20: 0111 0000 0010 0000 - { }, // 21: 0111 0000 0010 0001 - { }, // 22: 0111 0000 0010 0010 - { }, // 23: 0111 0000 0010 0011 - { }, // 24: 0111 0000 0010 0100 - { }, // 25: 0111 0000 0010 0101 - { }, // 26: 0111 0000 0010 0110 - { }, // 27: 0111 0000 0010 0111 - { }, // 28: 0111 0000 0010 1000 - { }, // 29: 0111 0000 0010 1001 - { }, // 2a: 0111 0000 0010 1010 - { }, // 2b: 0111 0000 0010 1011 - { }, // 2c: 0111 0000 0010 1100 - { }, // 2d: 0111 0000 0010 1101 - {SDED, "%w" }, // 2e: 0111 0000 0010 1110 llll llll hhhh hhhh - {LDED, "%w" }, // 2f: 0111 0000 0010 1111 llll llll hhhh hhhh +const upd7810_base_disassembler::dasm_s upd7807_disassembler::d4C_7807[256] = +{ + { }, // 00: 0100 1100 0000 0000 + { }, // 01: 0100 1100 0000 0001 + { }, // 02: 0100 1100 0000 0010 + { }, // 03: 0100 1100 0000 0011 + { }, // 04: 0100 1100 0000 0100 + { }, // 05: 0100 1100 0000 0101 + { }, // 06: 0100 1100 0000 0110 + { }, // 07: 0100 1100 0000 0111 + { }, // 08: 0100 1100 0000 1000 + { }, // 09: 0100 1100 0000 1001 + { }, // 0a: 0100 1100 0000 1010 + { }, // 0b: 0100 1100 0000 1011 + { }, // 0c: 0100 1100 0000 1100 + { }, // 0d: 0100 1100 0000 1101 + { }, // 0e: 0100 1100 0000 1110 + { }, // 0f: 0100 1100 0000 1111 - { }, // 30: 0111 0000 0011 0000 - { }, // 31: 0111 0000 0011 0001 - { }, // 32: 0111 0000 0011 0010 - { }, // 33: 0111 0000 0011 0011 - { }, // 34: 0111 0000 0011 0100 - { }, // 35: 0111 0000 0011 0101 - { }, // 36: 0111 0000 0011 0110 - { }, // 37: 0111 0000 0011 0111 - { }, // 38: 0111 0000 0011 1000 - { }, // 39: 0111 0000 0011 1001 - { }, // 3a: 0111 0000 0011 1010 - { }, // 3b: 0111 0000 0011 1011 - { }, // 3c: 0111 0000 0011 1100 - { }, // 3d: 0111 0000 0011 1101 - {SHLD, "%w" }, // 3e: 0111 0000 0011 1110 llll llll hhhh hhhh - {LHLD, "%w" }, // 3f: 0111 0000 0011 1111 llll llll hhhh hhhh + { }, // 10: 0100 1100 0001 0000 + { }, // 11: 0100 1100 0001 0001 + { }, // 12: 0100 1100 0001 0010 + { }, // 13: 0100 1100 0001 0011 + { }, // 14: 0100 1100 0001 0100 + { }, // 15: 0100 1100 0001 0101 + { }, // 16: 0100 1100 0001 0110 + { }, // 17: 0100 1100 0001 0111 + { }, // 18: 0100 1100 0001 1000 + { }, // 19: 0100 1100 0001 1001 + { }, // 1a: 0100 1100 0001 1010 + { }, // 1b: 0100 1100 0001 1011 + { }, // 1c: 0100 1100 0001 1100 + { }, // 1d: 0100 1100 0001 1101 + { }, // 1e: 0100 1100 0001 1110 + { }, // 1f: 0100 1100 0001 1111 - {EADD, "EA,V" }, // 40: 0111 0000 0100 0000 - {EADD, "EA,A" }, // 41: 0111 0000 0100 0001 - {EADD, "EA,B" }, // 42: 0111 0000 0100 0010 - {EADD, "EA,C" }, // 43: 0111 0000 0100 0011 - { }, // 44: 0111 0000 0100 0100 - { }, // 45: 0111 0000 0100 0101 - { }, // 46: 0111 0000 0100 0110 - { }, // 47: 0111 0000 0100 0111 - { }, // 48: 0111 0000 0100 1000 - { }, // 49: 0111 0000 0100 1001 - { }, // 4a: 0111 0000 0100 1010 - { }, // 4b: 0111 0000 0100 1011 - { }, // 4c: 0111 0000 0100 1100 - { }, // 4d: 0111 0000 0100 1101 - { }, // 4e: 0111 0000 0100 1110 - { }, // 4f: 0111 0000 0100 1111 + { }, // 20: 0100 1100 0010 0000 + { }, // 21: 0100 1100 0010 0001 + { }, // 22: 0100 1100 0010 0010 + { }, // 23: 0100 1100 0010 0011 + { }, // 24: 0100 1100 0010 0100 + { }, // 25: 0100 1100 0010 0101 + { }, // 26: 0100 1100 0010 0110 + { }, // 27: 0100 1100 0010 0111 + { }, // 28: 0100 1100 0010 1000 + { }, // 29: 0100 1100 0010 1001 + { }, // 2a: 0100 1100 0010 1010 + { }, // 2b: 0100 1100 0010 1011 + { }, // 2c: 0100 1100 0010 1100 + { }, // 2d: 0100 1100 0010 1101 + { }, // 2e: 0100 1100 0010 1110 + { }, // 2f: 0100 1100 0010 1111 - { }, // 50: 0111 0000 0101 0000 - { }, // 51: 0111 0000 0101 0001 - { }, // 52: 0111 0000 0101 0010 - { }, // 53: 0111 0000 0101 0011 - { }, // 54: 0111 0000 0101 0100 - { }, // 55: 0111 0000 0101 0101 - { }, // 56: 0111 0000 0101 0110 - { }, // 57: 0111 0000 0101 0111 - { }, // 58: 0111 0000 0101 1000 - { }, // 59: 0111 0000 0101 1001 - { }, // 5a: 0111 0000 0101 1010 - { }, // 5b: 0111 0000 0101 1011 - { }, // 5c: 0111 0000 0101 1100 - { }, // 5d: 0111 0000 0101 1101 - { }, // 5e: 0111 0000 0101 1110 - { }, // 5f: 0111 0000 0101 1111 + { }, // 30: 0100 1100 0011 0000 + { }, // 31: 0100 1100 0011 0001 + { }, // 32: 0100 1100 0011 0010 + { }, // 33: 0100 1100 0011 0011 + { }, // 34: 0100 1100 0011 0100 + { }, // 35: 0100 1100 0011 0101 + { }, // 36: 0100 1100 0011 0110 + { }, // 37: 0100 1100 0011 0111 + { }, // 38: 0100 1100 0011 1000 + { }, // 39: 0100 1100 0011 1001 + { }, // 3a: 0100 1100 0011 1010 + { }, // 3b: 0100 1100 0011 1011 + { }, // 3c: 0100 1100 0011 1100 + { }, // 3d: 0100 1100 0011 1101 + { }, // 3e: 0100 1100 0011 1110 + { }, // 3f: 0100 1100 0011 1111 - {ESUB, "EA,V" }, // 60: 0111 0000 0110 0000 - {ESUB, "EA,A" }, // 61: 0111 0000 0110 0001 - {ESUB, "EA,B" }, // 62: 0111 0000 0110 0010 - {ESUB, "EA,C" }, // 63: 0111 0000 0110 0011 - { }, // 64: 0111 0000 0110 0100 - { }, // 65: 0111 0000 0110 0101 - { }, // 66: 0111 0000 0110 0110 - { }, // 67: 0111 0000 0110 0111 - {MOV, "V,(%w)" }, // 68: 0111 0000 0110 1000 llll llll hhhh hhhh - {MOV, "A,(%w)" }, // 69: 0111 0000 0110 1001 llll llll hhhh hhhh - {MOV, "B,(%w)" }, // 6a: 0111 0000 0110 1010 llll llll hhhh hhhh - {MOV, "C,(%w)" }, // 6b: 0111 0000 0110 1011 llll llll hhhh hhhh - {MOV, "D,(%w)" }, // 6c: 0111 0000 0110 1100 llll llll hhhh hhhh - {MOV, "E,(%w)" }, // 6d: 0111 0000 0110 1101 llll llll hhhh hhhh - {MOV, "H,(%w)" }, // 6e: 0111 0000 0110 1110 llll llll hhhh hhhh - {MOV, "L,(%w)" }, // 6f: 0111 0000 0110 1111 llll llll hhhh hhhh + { }, // 40: 0100 1100 0100 0000 + { }, // 41: 0100 1100 0100 0001 + { }, // 42: 0100 1100 0100 0010 + { }, // 43: 0100 1100 0100 0011 + { }, // 44: 0100 1100 0100 0100 + { }, // 45: 0100 1100 0100 0101 + { }, // 46: 0100 1100 0100 0110 + { }, // 47: 0100 1100 0100 0111 + { }, // 48: 0100 1100 0100 1000 + { }, // 49: 0100 1100 0100 1001 + { }, // 4a: 0100 1100 0100 1010 + { }, // 4b: 0100 1100 0100 1011 + { }, // 4c: 0100 1100 0100 1100 + { }, // 4d: 0100 1100 0100 1101 + { }, // 4e: 0100 1100 0100 1110 + { }, // 4f: 0100 1100 0100 1111 - { }, // 70: 0111 0000 0111 0000 - { }, // 71: 0111 0000 0111 0001 - { }, // 72: 0111 0000 0111 0010 - { }, // 73: 0111 0000 0111 0011 - { }, // 74: 0111 0000 0111 0100 - { }, // 75: 0111 0000 0111 0101 - { }, // 76: 0111 0000 0111 0110 - { }, // 77: 0111 0000 0111 0111 - {MOV, "(%w),V" }, // 78: 0111 0000 0111 1000 llll llll hhhh hhhh - {MOV, "(%w),A" }, // 79: 0111 0000 0111 1001 llll llll hhhh hhhh - {MOV, "(%w),B" }, // 7a: 0111 0000 0111 1010 llll llll hhhh hhhh - {MOV, "(%w),C" }, // 7b: 0111 0000 0111 1011 llll llll hhhh hhhh - {MOV, "(%w),D" }, // 7c: 0111 0000 0111 1100 llll llll hhhh hhhh - {MOV, "(%w),E" }, // 7d: 0111 0000 0111 1101 llll llll hhhh hhhh - {MOV, "(%w),H" }, // 7e: 0111 0000 0111 1110 llll llll hhhh hhhh - {MOV, "(%w),L" }, // 7f: 0111 0000 0111 1111 llll llll hhhh hhhh + { }, // 50: 0100 1100 0101 0000 + { }, // 51: 0100 1100 0101 0001 + { }, // 52: 0100 1100 0101 0010 + { }, // 53: 0100 1100 0101 0011 + { }, // 54: 0100 1100 0101 0100 + { }, // 55: 0100 1100 0101 0101 + { }, // 56: 0100 1100 0101 0110 + { }, // 57: 0100 1100 0101 0111 + { }, // 58: 0100 1100 0101 1000 + { }, // 59: 0100 1100 0101 1001 + { }, // 5a: 0100 1100 0101 1010 + { }, // 5b: 0100 1100 0101 1011 + { }, // 5c: 0100 1100 0101 1100 + { }, // 5d: 0100 1100 0101 1101 + { }, // 5e: 0100 1100 0101 1110 + { }, // 5f: 0100 1100 0101 1111 - { }, // 80: 0111 0000 1000 0000 - { }, // 81: 0111 0000 1000 0001 - { }, // 82: 0111 0000 1000 0010 - { }, // 83: 0111 0000 1000 0011 - { }, // 84: 0111 0000 1000 0100 - { }, // 85: 0111 0000 1000 0101 - { }, // 86: 0111 0000 1000 0110 - { }, // 87: 0111 0000 1000 0111 - { }, // 88: 0111 0000 1000 1000 - {ANAX, "(BC)" }, // 89: 0111 0000 1000 1001 - {ANAX, "(DE)" }, // 8a: 0111 0000 1000 1010 - {ANAX, "(HL)" }, // 8b: 0111 0000 1000 1011 - {ANAX, "(DE+)" }, // 8c: 0111 0000 1000 1100 - {ANAX, "(HL+)" }, // 8d: 0111 0000 1000 1101 - {ANAX, "(DE-)" }, // 8e: 0111 0000 1000 1110 - {ANAX, "(HL-)" }, // 8f: 0111 0000 1000 1111 + { }, // 60: 0100 1100 0110 0000 + { }, // 61: 0100 1100 0110 0001 + { }, // 62: 0100 1100 0110 0010 + { }, // 63: 0100 1100 0110 0011 + { }, // 64: 0100 1100 0110 0100 + { }, // 65: 0100 1100 0110 0101 + { }, // 66: 0100 1100 0110 0110 + { }, // 67: 0100 1100 0110 0111 + { }, // 68: 0100 1100 0110 1000 + { }, // 69: 0100 1100 0110 1001 + { }, // 6a: 0100 1100 0110 1010 + { }, // 6b: 0100 1100 0110 1011 + { }, // 6c: 0100 1100 0110 1100 + { }, // 6d: 0100 1100 0110 1101 + { }, // 6e: 0100 1100 0110 1110 + { }, // 6f: 0100 1100 0110 1111 + + { }, // 70: 0100 1100 0111 0000 + { }, // 71: 0100 1100 0111 0001 + { }, // 72: 0100 1100 0111 0010 + { }, // 73: 0100 1100 0111 0011 + { }, // 74: 0100 1100 0111 0100 + { }, // 75: 0100 1100 0111 0101 + { }, // 76: 0100 1100 0111 0110 + { }, // 77: 0100 1100 0111 0111 + { }, // 78: 0100 1100 0111 1000 + { }, // 79: 0100 1100 0111 1001 + { }, // 7a: 0100 1100 0111 1010 + { }, // 7b: 0100 1100 0111 1011 + { }, // 7c: 0100 1100 0111 1100 + { }, // 7d: 0100 1100 0111 1101 + { }, // 7e: 0100 1100 0111 1110 + { }, // 7f: 0100 1100 0111 1111 - { }, // 90: 0111 0000 1001 0000 - {XRAX, "(BC)" }, // 91: 0111 0000 1001 0001 - {XRAX, "(DE)" }, // 92: 0111 0000 1001 0010 - {XRAX, "(HL)" }, // 93: 0111 0000 1001 0011 - {XRAX, "(DE+)" }, // 94: 0111 0000 1001 0100 - {XRAX, "(HL+)" }, // 95: 0111 0000 1001 0101 - {XRAX, "(DE-)" }, // 96: 0111 0000 1001 0110 - {XRAX, "(HL-)" }, // 97: 0111 0000 1001 0111 - { }, // 98: 0111 0000 1001 1000 - {ORAX, "(BC)" }, // 99: 0111 0000 1001 1001 - {ORAX, "(DE)" }, // 9a: 0111 0000 1001 1010 - {ORAX, "(HL)" }, // 9b: 0111 0000 1001 1011 - {ORAX, "(DE+)" }, // 9c: 0111 0000 1001 1100 - {ORAX, "(HL+)" }, // 9d: 0111 0000 1001 1101 - {ORAX, "(DE-)" }, // 9e: 0111 0000 1001 1110 - {ORAX, "(HL-)" }, // 9f: 0111 0000 1001 1111 + { }, // 80: 0100 1100 1000 0000 + { }, // 81: 0100 1100 1000 0001 + { }, // 82: 0100 1100 1000 0010 + { }, // 83: 0100 1100 1000 0011 + { }, // 84: 0100 1100 1000 0100 + { }, // 85: 0100 1100 1000 0101 + { }, // 86: 0100 1100 1000 0110 + { }, // 87: 0100 1100 1000 0111 + { }, // 88: 0100 1100 1000 1000 + { }, // 89: 0100 1100 1000 1001 + { }, // 8a: 0100 1100 1000 1010 + { }, // 8b: 0100 1100 1000 1011 + { }, // 8c: 0100 1100 1000 1100 + { }, // 8d: 0100 1100 1000 1101 + { }, // 8e: 0100 1100 1000 1110 + { }, // 8f: 0100 1100 1000 1111 - { }, // a0: 0111 0000 1010 0000 - {ADDNCX, "(BC)" }, // a1: 0111 0000 1010 0001 - {ADDNCX, "(DE)" }, // a2: 0111 0000 1010 0010 - {ADDNCX, "(HL)" }, // a3: 0111 0000 1010 0011 - {ADDNCX, "(DE+)" }, // a4: 0111 0000 1010 0100 - {ADDNCX, "(HL+)" }, // a5: 0111 0000 1010 0101 - {ADDNCX, "(DE-)" }, // a6: 0111 0000 1010 0110 - {ADDNCX, "(HL-)" }, // a7: 0111 0000 1010 0111 - { }, // a8: 0111 0000 1010 1000 - {GTAX, "(BC)" }, // a9: 0111 0000 1010 1001 - {GTAX, "(DE)" }, // aa: 0111 0000 1010 1010 - {GTAX, "(HL)" }, // ab: 0111 0000 1010 1011 - {GTAX, "(DE+)" }, // ac: 0111 0000 1010 1100 - {GTAX, "(HL+)" }, // ad: 0111 0000 1010 1101 - {GTAX, "(DE-)" }, // ae: 0111 0000 1010 1110 - {GTAX, "(HL-)" }, // af: 0111 0000 1010 1111 + { }, // 90: 0100 1100 1001 0000 + { }, // 91: 0100 1100 1001 0001 + { }, // 92: 0100 1100 1001 0010 + { }, // 93: 0100 1100 1001 0011 + { }, // 94: 0100 1100 1001 0100 + { }, // 95: 0100 1100 1001 0101 + { }, // 96: 0100 1100 1001 0110 + { }, // 97: 0100 1100 1001 0111 + { }, // 98: 0100 1100 1001 1000 + { }, // 99: 0100 1100 1001 1001 + { }, // 9a: 0100 1100 1001 1010 + { }, // 9b: 0100 1100 1001 1011 + { }, // 9c: 0100 1100 1001 1100 + { }, // 9d: 0100 1100 1001 1101 + { }, // 9e: 0100 1100 1001 1110 + { }, // 9f: 0100 1100 1001 1111 - { }, // b0: 0111 0000 1011 0000 - {SUBNBX, "(BC)" }, // b1: 0111 0000 1011 0001 - {SUBNBX, "(DE)" }, // b2: 0111 0000 1011 0010 - {SUBNBX, "(HL)" }, // b3: 0111 0000 1011 0011 - {SUBNBX, "(DE+)" }, // b4: 0111 0000 1011 0100 - {SUBNBX, "(HL+)" }, // b5: 0111 0000 1011 0101 - {SUBNBX, "(DE-)" }, // b6: 0111 0000 1011 0110 - {SUBNBX, "(HL-)" }, // b7: 0111 0000 1011 0111 - { }, // b8: 0111 0000 1011 1000 - {LTAX, "(BC)" }, // b9: 0111 0000 1011 1001 - {LTAX, "(DE)" }, // ba: 0111 0000 1011 1010 - {LTAX, "(HL)" }, // bb: 0111 0000 1011 1011 - {LTAX, "(DE+)" }, // bc: 0111 0000 1011 1100 - {LTAX, "(HL+)" }, // bd: 0111 0000 1011 1101 - {LTAX, "(DE-)" }, // be: 0111 0000 1011 1110 - {LTAX, "(HL-)" }, // bf: 0111 0000 1011 1111 + { }, // a0: 0100 1100 1010 0000 + { }, // a1: 0100 1100 1010 0001 + { }, // a2: 0100 1100 1010 0010 + { }, // a3: 0100 1100 1010 0011 + { }, // a4: 0100 1100 1010 0100 + { }, // a5: 0100 1100 1010 0101 + { }, // a6: 0100 1100 1010 0110 + { }, // a7: 0100 1100 1010 0111 + { }, // a8: 0100 1100 1010 1000 + { }, // a9: 0100 1100 1010 1001 + { }, // aa: 0100 1100 1010 1010 + { }, // ab: 0100 1100 1010 1011 + { }, // ac: 0100 1100 1010 1100 + { }, // ad: 0100 1100 1010 1101 + { }, // ae: 0100 1100 1010 1110 + { }, // af: 0100 1100 1010 1111 - { }, // c0: 0111 0000 1100 0000 - {ADDX, "(BC)" }, // c1: 0111 0000 1100 0001 - {ADDX, "(DE)" }, // c2: 0111 0000 1100 0010 - {ADDX, "(HL)" }, // c3: 0111 0000 1100 0011 - {ADDX, "(DE+)" }, // c4: 0111 0000 1100 0100 - {ADDX, "(HL+)" }, // c5: 0111 0000 1100 0101 - {ADDX, "(DE-)" }, // c6: 0111 0000 1100 0110 - {ADDX, "(HL-)" }, // c7: 0111 0000 1100 0111 - { }, // c8: 0111 0000 1100 1000 - {ONAX, "(BC)" }, // c9: 0111 0000 1100 1001 - {ONAX, "(DE)" }, // ca: 0111 0000 1100 1010 - {ONAX, "(HL)" }, // cb: 0111 0000 1100 1011 - {ONAX, "(DE+)" }, // cc: 0111 0000 1100 1100 - {ONAX, "(HL+)" }, // cd: 0111 0000 1100 1101 - {ONAX, "(DE-)" }, // ce: 0111 0000 1100 1110 - {ONAX, "(HL-)" }, // cf: 0111 0000 1100 1111 + { }, // b0: 0100 1100 1011 0000 + { }, // b1: 0100 1100 1011 0001 + { }, // b2: 0100 1100 1011 0010 + { }, // b3: 0100 1100 1011 0011 + { }, // b4: 0100 1100 1011 0100 + { }, // b5: 0100 1100 1011 0101 + { }, // b6: 0100 1100 1011 0110 + { }, // b7: 0100 1100 1011 0111 + { }, // b8: 0100 1100 1011 1000 + { }, // b9: 0100 1100 1011 1001 + { }, // ba: 0100 1100 1011 1010 + { }, // bb: 0100 1100 1011 1011 + { }, // bc: 0100 1100 1011 1100 + { }, // bd: 0100 1100 1011 1101 + { }, // be: 0100 1100 1011 1110 + { }, // bf: 0100 1100 1011 1111 - { }, // d0: 0111 0000 1101 0000 - {ADCX, "(BC)" }, // d1: 0111 0000 1101 0001 - {ADCX, "(DE)" }, // d2: 0111 0000 1101 0010 - {ADCX, "(HL)" }, // d3: 0111 0000 1101 0011 - {ADCX, "(DE+)" }, // d4: 0111 0000 1101 0100 - {ADCX, "(HL+)" }, // d5: 0111 0000 1101 0101 - {ADCX, "(DE-)" }, // d6: 0111 0000 1101 0110 - {ADCX, "(HL-)" }, // d7: 0111 0000 1101 0111 - { }, // d8: 0111 0000 1101 1000 - {OFFAX, "(BC)" }, // d9: 0111 0000 1101 1001 - {OFFAX, "(DE)" }, // da: 0111 0000 1101 1010 - {OFFAX, "(HL)" }, // db: 0111 0000 1101 1011 - {OFFAX, "(DE+)" }, // dc: 0111 0000 1101 1100 - {OFFAX, "(HL+)" }, // dd: 0111 0000 1101 1101 - {OFFAX, "(DE-)" }, // de: 0111 0000 1101 1110 - {OFFAX, "(HL-)" }, // df: 0111 0000 1101 1111 + {MOV, "A,PA" }, // c0: 0100 1100 1100 0000 + {MOV, "A,PB" }, // c1: 0100 1100 1100 0001 + {MOV, "A,PC" }, // c2: 0100 1100 1100 0010 + {MOV, "A,PD" }, // c3: 0100 1100 1100 0011 + { }, // c4: 0100 1100 1100 0100 + {MOV, "A,PF" }, // c5: 0100 1100 1100 0101 + {MOV, "A,MKH" }, // c6: 0100 1100 1100 0110 + {MOV, "A,MKL" }, // c7: 0100 1100 1100 0111 + { }, // c8: 0100 1100 1100 1000 + {MOV, "A,SMH" }, // c9: 0100 1100 1100 1001 + { }, // ca: 0100 1100 1100 1010 + {MOV, "A,EOM" }, // cb: 0100 1100 1100 1011 + { }, // cc: 0100 1100 1100 1100 + {MOV, "A,TMM" }, // cd: 0100 1100 1100 1101 + {MOV, "A,PT" }, // ce: 0100 1100 1100 1110 7807 + { }, // cf: 0100 1100 1100 1111 - { }, // e0: 0111 0000 1110 0000 - {SUBX, "(BC)" }, // e1: 0111 0000 1110 0001 - {SUBX, "(DE)" }, // e2: 0111 0000 1110 0010 - {SUBX, "(HL)" }, // e3: 0111 0000 1110 0011 - {SUBX, "(DE+)" }, // e4: 0111 0000 1110 0100 - {SUBX, "(HL+)" }, // e5: 0111 0000 1110 0101 - {SUBX, "(DE-)" }, // e6: 0111 0000 1110 0110 - {SUBX, "(HL-)" }, // e7: 0111 0000 1110 0111 - { }, // e8: 0111 0000 1110 1000 - {NEAX, "(BC)" }, // e9: 0111 0000 1110 1001 - {NEAX, "(DE)" }, // ea: 0111 0000 1110 1010 - {NEAX, "(HL)" }, // eb: 0111 0000 1110 1011 - {NEAX, "(DE+)" }, // ec: 0111 0000 1110 1100 - {NEAX, "(HL+)" }, // ed: 0111 0000 1110 1101 - {NEAX, "(DE-)" }, // ee: 0111 0000 1110 1110 - {NEAX, "(HL-)" }, // ef: 0111 0000 1110 1111 + { }, // d0: 0100 1100 1101 0000 + { }, // d1: 0100 1100 1101 0001 + { }, // d2: 0100 1100 1101 0010 + { }, // d3: 0100 1100 1101 0011 + { }, // d4: 0100 1100 1101 0100 + { }, // d5: 0100 1100 1101 0101 + { }, // d6: 0100 1100 1101 0110 + { }, // d7: 0100 1100 1101 0111 + { }, // d8: 0100 1100 1101 1000 + {MOV, "A,RXB" }, // d9: 0100 1100 1101 1001 + { }, // da: 0100 1100 1101 1010 + { }, // db: 0100 1100 1101 1011 + { }, // dc: 0100 1100 1101 1100 + { }, // dd: 0100 1100 1101 1101 + { }, // de: 0100 1100 1101 1110 + { }, // df: 0100 1100 1101 1111 - { }, // f0: 0111 0000 1111 0000 - {SBBX, "(BC)" }, // f1: 0111 0000 1111 0001 - {SBBX, "(DE)" }, // f2: 0111 0000 1111 0010 - {SBBX, "(HL)" }, // f3: 0111 0000 1111 0011 - {SBBX, "(DE+)" }, // f4: 0111 0000 1111 0100 - {SBBX, "(HL+)" }, // f5: 0111 0000 1111 0101 - {SBBX, "(DE-)" }, // f6: 0111 0000 1111 0110 - {SBBX, "(HL-)" }, // f7: 0111 0000 1111 0111 - { }, // f8: 0111 0000 1111 1000 - {EQAX, "(BC)" }, // f9: 0111 0000 1111 1001 - {EQAX, "(DE)" }, // fa: 0111 0000 1111 1010 - {EQAX, "(HL)" }, // fb: 0111 0000 1111 1011 - {EQAX, "(DE+)" }, // fc: 0111 0000 1111 1100 - {EQAX, "(HL+)" }, // fd: 0111 0000 1111 1101 - {EQAX, "(DE-)" }, // fe: 0111 0000 1111 1110 - {EQAX, "(HL-)" } // ff: 0111 0000 1111 1111 -}; + { }, // e0: 0100 1100 1110 0000 + { }, // e1: 0100 1100 1110 0001 + { }, // e2: 0100 1100 1110 0010 + { }, // e3: 0100 1100 1110 0011 + { }, // e4: 0100 1100 1110 0100 + { }, // e5: 0100 1100 1110 0101 + { }, // e6: 0100 1100 1110 0110 + { }, // e7: 0100 1100 1110 0111 + { }, // e8: 0100 1100 1110 1000 + { }, // e9: 0100 1100 1110 1001 + { }, // ea: 0100 1100 1110 1010 + { }, // eb: 0100 1100 1110 1011 + { }, // ec: 0100 1100 1110 1100 + { }, // ed: 0100 1100 1110 1101 + { }, // ee: 0100 1100 1110 1110 + { }, // ef: 0100 1100 1110 1111 -// prefix 74 -const dasm_s dasm_s::d74[256] = -{ - { }, // 00: 0111 0100 0000 0000 - { }, // 01: 0111 0100 0000 0001 - { }, // 02: 0111 0100 0000 0010 - { }, // 03: 0111 0100 0000 0011 - { }, // 04: 0111 0100 0000 0100 - { }, // 05: 0111 0100 0000 0101 - { }, // 06: 0111 0100 0000 0110 - { }, // 07: 0111 0100 0000 0111 - {ANI, "V,%b" }, // 08: 0111 0100 0000 1000 xxxx xxxx - {ANI, "A,%b" }, // 09: 0111 0100 0000 1001 xxxx xxxx - {ANI, "B,%b" }, // 0a: 0111 0100 0000 1010 xxxx xxxx - {ANI, "C,%b" }, // 0b: 0111 0100 0000 1011 xxxx xxxx - {ANI, "D,%b" }, // 0c: 0111 0100 0000 1100 xxxx xxxx - {ANI, "E,%b" }, // 0d: 0111 0100 0000 1101 xxxx xxxx - {ANI, "H,%b" }, // 0e: 0111 0100 0000 1110 xxxx xxxx - {ANI, "L,%b" }, // 0f: 0111 0100 0000 1111 xxxx xxxx + { }, // f0: 0100 1100 1111 0000 + { }, // f1: 0100 1100 1111 0001 + { }, // f2: 0100 1100 1111 0010 + { }, // f3: 0100 1100 1111 0011 + { }, // f4: 0100 1100 1111 0100 + { }, // f5: 0100 1100 1111 0101 + { }, // f6: 0100 1100 1111 0110 + { }, // f7: 0100 1100 1111 0111 + { }, // f8: 0100 1100 1111 1000 + { }, // f9: 0100 1100 1111 1001 + { }, // fa: 0100 1100 1111 1010 + { }, // fb: 0100 1100 1111 1011 + { }, // fc: 0100 1100 1111 1100 + { }, // fd: 0100 1100 1111 1101 + { }, // fe: 0100 1100 1111 1110 + { } // ff: 0100 1100 1111 1111 +}; - {XRI, "V,%b" }, // 10: 0111 0100 0001 0000 xxxx xxxx - {XRI, "A,%b" }, // 11: 0111 0100 0001 0001 xxxx xxxx - {XRI, "B,%b" }, // 12: 0111 0100 0001 0010 xxxx xxxx - {XRI, "C,%b" }, // 13: 0111 0100 0001 0011 xxxx xxxx - {XRI, "D,%b" }, // 14: 0111 0100 0001 0100 xxxx xxxx - {XRI, "E,%b" }, // 15: 0111 0100 0001 0101 xxxx xxxx - {XRI, "H,%b" }, // 16: 0111 0100 0001 0110 xxxx xxxx - {XRI, "L,%b" }, // 17: 0111 0100 0001 0111 xxxx xxxx - {ORI, "V,%b" }, // 18: 0111 0100 0001 1000 xxxx xxxx - {ORI, "A,%b" }, // 19: 0111 0100 0001 1001 xxxx xxxx - {ORI, "B,%b" }, // 1a: 0111 0100 0001 1010 xxxx xxxx - {ORI, "C,%b" }, // 1b: 0111 0100 0001 1011 xxxx xxxx - {ORI, "D,%b" }, // 1c: 0111 0100 0001 1100 xxxx xxxx - {ORI, "E,%b" }, // 1d: 0111 0100 0001 1101 xxxx xxxx - {ORI, "H,%b" }, // 1e: 0111 0100 0001 1110 xxxx xxxx - {ORI, "L,%b" }, // 1f: 0111 0100 0001 1111 xxxx xxxx +const upd7810_base_disassembler::dasm_s upd7807_disassembler::d4D_7807[256] = +{ + { }, // 00: 0100 1101 0000 0000 + { }, // 01: 0100 1101 0000 0001 + { }, // 02: 0100 1101 0000 0010 + { }, // 03: 0100 1101 0000 0011 + { }, // 04: 0100 1101 0000 0100 + { }, // 05: 0100 1101 0000 0101 + { }, // 06: 0100 1101 0000 0110 + { }, // 07: 0100 1101 0000 0111 + { }, // 08: 0100 1101 0000 1000 + { }, // 09: 0100 1101 0000 1001 + { }, // 0a: 0100 1101 0000 1010 + { }, // 0b: 0100 1101 0000 1011 + { }, // 0c: 0100 1101 0000 1100 + { }, // 0d: 0100 1101 0000 1101 + { }, // 0e: 0100 1101 0000 1110 + { }, // 0f: 0100 1101 0000 1111 - {ADINC, "V,%b" }, // 20: 0111 0100 0010 0000 xxxx xxxx - {ADINC, "A,%b" }, // 21: 0111 0100 0010 0001 xxxx xxxx - {ADINC, "B,%b" }, // 22: 0111 0100 0010 0010 xxxx xxxx - {ADINC, "C,%b" }, // 23: 0111 0100 0010 0011 xxxx xxxx - {ADINC, "D,%b" }, // 24: 0111 0100 0010 0100 xxxx xxxx - {ADINC, "E,%b" }, // 25: 0111 0100 0010 0101 xxxx xxxx - {ADINC, "H,%b" }, // 26: 0111 0100 0010 0110 xxxx xxxx - {ADINC, "L,%b" }, // 27: 0111 0100 0010 0111 xxxx xxxx - {GTI, "V,%b" }, // 28: 0111 0100 0010 1000 xxxx xxxx - {GTI, "A,%b" }, // 29: 0111 0100 0010 1001 xxxx xxxx - {GTI, "B,%b" }, // 2a: 0111 0100 0010 1010 xxxx xxxx - {GTI, "C,%b" }, // 2b: 0111 0100 0010 1011 xxxx xxxx - {GTI, "D,%b" }, // 2c: 0111 0100 0010 1100 xxxx xxxx - {GTI, "E,%b" }, // 2d: 0111 0100 0010 1101 xxxx xxxx - {GTI, "H,%b" }, // 2e: 0111 0100 0010 1110 xxxx xxxx - {GTI, "L,%b" }, // 2f: 0111 0100 0010 1111 xxxx xxxx + { }, // 10: 0100 1101 0001 0000 + { }, // 11: 0100 1101 0001 0001 + { }, // 12: 0100 1101 0001 0010 + { }, // 13: 0100 1101 0001 0011 + { }, // 14: 0100 1101 0001 0100 + { }, // 15: 0100 1101 0001 0101 + { }, // 16: 0100 1101 0001 0110 + { }, // 17: 0100 1101 0001 0111 + { }, // 18: 0100 1101 0001 1000 + { }, // 19: 0100 1101 0001 1001 + { }, // 1a: 0100 1101 0001 1010 + { }, // 1b: 0100 1101 0001 1011 + { }, // 1c: 0100 1101 0001 1100 + { }, // 1d: 0100 1101 0001 1101 + { }, // 1e: 0100 1101 0001 1110 + { }, // 1f: 0100 1101 0001 1111 - {SUINB, "V,%b" }, // 30: 0111 0100 0011 0000 xxxx xxxx - {SUINB, "A,%b" }, // 31: 0111 0100 0011 0001 xxxx xxxx - {SUINB, "B,%b" }, // 32: 0111 0100 0011 0010 xxxx xxxx - {SUINB, "C,%b" }, // 33: 0111 0100 0011 0011 xxxx xxxx - {SUINB, "D,%b" }, // 34: 0111 0100 0011 0100 xxxx xxxx - {SUINB, "E,%b" }, // 35: 0111 0100 0011 0101 xxxx xxxx - {SUINB, "H,%b" }, // 36: 0111 0100 0011 0110 xxxx xxxx - {SUINB, "L,%b" }, // 37: 0111 0100 0011 0111 xxxx xxxx - {LTI, "V,%b" }, // 37: 0111 0100 0011 1000 xxxx xxxx - {LTI, "A,%b" }, // 39: 0111 0100 0011 1001 xxxx xxxx - {LTI, "B,%b" }, // 3a: 0111 0100 0011 1010 xxxx xxxx - {LTI, "C,%b" }, // 3b: 0111 0100 0011 1011 xxxx xxxx - {LTI, "D,%b" }, // 3c: 0111 0100 0011 1100 xxxx xxxx - {LTI, "E,%b" }, // 3d: 0111 0100 0011 1101 xxxx xxxx - {LTI, "H,%b" }, // 3e: 0111 0100 0011 1110 xxxx xxxx - {LTI, "L,%b" }, // 3f: 0111 0100 0011 1111 xxxx xxxx + { }, // 20: 0100 1101 0010 0000 + { }, // 21: 0100 1101 0010 0001 + { }, // 22: 0100 1101 0010 0010 + { }, // 23: 0100 1101 0010 0011 + { }, // 24: 0100 1101 0010 0100 + { }, // 25: 0100 1101 0010 0101 + { }, // 26: 0100 1101 0010 0110 + { }, // 27: 0100 1101 0010 0111 + { }, // 28: 0100 1101 0010 1000 + { }, // 29: 0100 1101 0010 1001 + { }, // 2a: 0100 1101 0010 1010 + { }, // 2b: 0100 1101 0010 1011 + { }, // 2c: 0100 1101 0010 1100 + { }, // 2d: 0100 1101 0010 1101 + { }, // 2e: 0100 1101 0010 1110 + { }, // 2f: 0100 1101 0010 1111 - {ADI, "V,%b" }, // 40: 0111 0100 0100 0000 xxxx xxxx - {ADI, "A,%b" }, // 41: 0111 0100 0100 0001 xxxx xxxx - {ADI, "B,%b" }, // 42: 0111 0100 0100 0010 xxxx xxxx - {ADI, "C,%b" }, // 43: 0111 0100 0100 0011 xxxx xxxx - {ADI, "D,%b" }, // 44: 0111 0100 0100 0100 xxxx xxxx - {ADI, "E,%b" }, // 45: 0111 0100 0100 0101 xxxx xxxx - {ADI, "H,%b" }, // 46: 0111 0100 0100 0110 xxxx xxxx - {ADI, "L,%b" }, // 47: 0111 0100 0100 0111 xxxx xxxx - {ONI, "V,%b" }, // 48: 0111 0100 0100 1000 xxxx xxxx - {ONI, "A,%b" }, // 49: 0111 0100 0100 1001 xxxx xxxx - {ONI, "B,%b" }, // 4a: 0111 0100 0100 1010 xxxx xxxx - {ONI, "C,%b" }, // 4b: 0111 0100 0100 1011 xxxx xxxx - {ONI, "D,%b" }, // 4c: 0111 0100 0100 1100 xxxx xxxx - {ONI, "E,%b" }, // 4d: 0111 0100 0100 1101 xxxx xxxx - {ONI, "H,%b" }, // 4e: 0111 0100 0100 1110 xxxx xxxx - {ONI, "L,%b" }, // 4f: 0111 0100 0100 1111 xxxx xxxx + { }, // 30: 0100 1101 0011 0000 + { }, // 31: 0100 1101 0011 0001 + { }, // 32: 0100 1101 0011 0010 + { }, // 33: 0100 1101 0011 0011 + { }, // 34: 0100 1101 0011 0100 + { }, // 35: 0100 1101 0011 0101 + { }, // 36: 0100 1101 0011 0110 + { }, // 37: 0100 1101 0011 0111 + { }, // 38: 0100 1101 0011 1000 + { }, // 39: 0100 1101 0011 1001 + { }, // 3a: 0100 1101 0011 1010 + { }, // 3b: 0100 1101 0011 1011 + { }, // 3c: 0100 1101 0011 1100 + { }, // 3d: 0100 1101 0011 1101 + { }, // 3e: 0100 1101 0011 1110 + { }, // 3f: 0100 1101 0011 1111 - {ACI, "V,%b" }, // 50: 0111 0100 0101 0000 xxxx xxxx - {ACI, "A,%b" }, // 51: 0111 0100 0101 0001 xxxx xxxx - {ACI, "B,%b" }, // 52: 0111 0100 0101 0010 xxxx xxxx - {ACI, "C,%b" }, // 53: 0111 0100 0101 0011 xxxx xxxx - {ACI, "D,%b" }, // 54: 0111 0100 0101 0100 xxxx xxxx - {ACI, "E,%b" }, // 55: 0111 0100 0101 0101 xxxx xxxx - {ACI, "H,%b" }, // 56: 0111 0100 0101 0110 xxxx xxxx - {ACI, "L,%b" }, // 57: 0111 0100 0101 0111 xxxx xxxx - {OFFI, "V,%b" }, // 58: 0111 0100 0101 1000 xxxx xxxx - {OFFI, "A,%b" }, // 59: 0111 0100 0101 1001 xxxx xxxx - {OFFI, "B,%b" }, // 5a: 0111 0100 0101 1010 xxxx xxxx - {OFFI, "C,%b" }, // 5b: 0111 0100 0101 1011 xxxx xxxx - {OFFI, "D,%b" }, // 5c: 0111 0100 0101 1100 xxxx xxxx - {OFFI, "E,%b" }, // 5d: 0111 0100 0101 1101 xxxx xxxx - {OFFI, "H,%b" }, // 5e: 0111 0100 0101 1110 xxxx xxxx - {OFFI, "L,%b" }, // 5f: 0111 0100 0101 1111 xxxx xxxx + { }, // 40: 0100 1101 0100 0000 + { }, // 41: 0100 1101 0100 0001 + { }, // 42: 0100 1101 0100 0010 + { }, // 43: 0100 1101 0100 0011 + { }, // 44: 0100 1101 0100 0100 + { }, // 45: 0100 1101 0100 0101 + { }, // 46: 0100 1101 0100 0110 + { }, // 47: 0100 1101 0100 0111 + { }, // 48: 0100 1101 0100 1000 + { }, // 49: 0100 1101 0100 1001 + { }, // 4a: 0100 1101 0100 1010 + { }, // 4b: 0100 1101 0100 1011 + { }, // 4c: 0100 1101 0100 1100 + { }, // 4d: 0100 1101 0100 1101 + { }, // 4e: 0100 1101 0100 1110 + { }, // 4f: 0100 1101 0100 1111 - {SUI, "V,%b" }, // 60: 0111 0100 0110 0000 xxxx xxxx - {SUI, "A,%b" }, // 61: 0111 0100 0110 0001 xxxx xxxx - {SUI, "B,%b" }, // 62: 0111 0100 0110 0010 xxxx xxxx - {SUI, "C,%b" }, // 63: 0111 0100 0110 0011 xxxx xxxx - {SUI, "D,%b" }, // 64: 0111 0100 0110 0100 xxxx xxxx - {SUI, "E,%b" }, // 65: 0111 0100 0110 0101 xxxx xxxx - {SUI, "H,%b" }, // 66: 0111 0100 0110 0110 xxxx xxxx - {SUI, "L,%b" }, // 67: 0111 0100 0110 0111 xxxx xxxx - {NEI, "V,%b" }, // 68: 0111 0100 0110 1000 xxxx xxxx - {NEI, "A,%b" }, // 69: 0111 0100 0110 1001 xxxx xxxx - {NEI, "B,%b" }, // 6a: 0111 0100 0110 1010 xxxx xxxx - {NEI, "C,%b" }, // 6b: 0111 0100 0110 1011 xxxx xxxx - {NEI, "D,%b" }, // 6c: 0111 0100 0110 1100 xxxx xxxx - {NEI, "E,%b" }, // 6d: 0111 0100 0110 1101 xxxx xxxx - {NEI, "H,%b" }, // 6e: 0111 0100 0110 1110 xxxx xxxx - {NEI, "L,%b" }, // 6f: 0111 0100 0110 1111 xxxx xxxx + { }, // 50: 0100 1101 0101 0000 + { }, // 51: 0100 1101 0101 0001 + { }, // 52: 0100 1101 0101 0010 + { }, // 53: 0100 1101 0101 0011 + { }, // 54: 0100 1101 0101 0100 + { }, // 55: 0100 1101 0101 0101 + { }, // 56: 0100 1101 0101 0110 + { }, // 57: 0100 1101 0101 0111 + { }, // 58: 0100 1101 0101 1000 + { }, // 59: 0100 1101 0101 1001 + { }, // 5a: 0100 1101 0101 1010 + { }, // 5b: 0100 1101 0101 1011 + { }, // 5c: 0100 1101 0101 1100 + { }, // 5d: 0100 1101 0101 1101 + { }, // 5e: 0100 1101 0101 1110 + { }, // 5f: 0100 1101 0101 1111 - {SBI, "V,%b" }, // 70: 0111 0100 0111 0000 xxxx xxxx - {SBI, "A,%b" }, // 71: 0111 0100 0111 0001 xxxx xxxx - {SBI, "B,%b" }, // 72: 0111 0100 0111 0010 xxxx xxxx - {SBI, "C,%b" }, // 73: 0111 0100 0111 0011 xxxx xxxx - {SBI, "D,%b" }, // 74: 0111 0100 0111 0100 xxxx xxxx - {SBI, "E,%b" }, // 75: 0111 0100 0111 0101 xxxx xxxx - {SBI, "H,%b" }, // 76: 0111 0100 0111 0110 xxxx xxxx - {SBI, "L,%b" }, // 77: 0111 0100 0111 0111 xxxx xxxx - {EQI, "V,%b" }, // 78: 0111 0100 0111 1000 xxxx xxxx - {EQI, "A,%b" }, // 79: 0111 0100 0111 1001 xxxx xxxx - {EQI, "B,%b" }, // 7a: 0111 0100 0111 1010 xxxx xxxx - {EQI, "C,%b" }, // 7b: 0111 0100 0111 1011 xxxx xxxx - {EQI, "D,%b" }, // 7c: 0111 0100 0111 1100 xxxx xxxx - {EQI, "E,%b" }, // 7d: 0111 0100 0111 1101 xxxx xxxx - {EQI, "H,%b" }, // 7e: 0111 0100 0111 1110 xxxx xxxx - {EQI, "L,%b" }, // 7f: 0111 0100 0111 1111 xxxx xxxx + { }, // 60: 0100 1101 0110 0000 + { }, // 61: 0100 1101 0110 0001 + { }, // 62: 0100 1101 0110 0010 + { }, // 63: 0100 1101 0110 0011 + { }, // 64: 0100 1101 0110 0100 + { }, // 65: 0100 1101 0110 0101 + { }, // 66: 0100 1101 0110 0110 + { }, // 67: 0100 1101 0110 0111 + { }, // 68: 0100 1101 0110 1000 + { }, // 69: 0100 1101 0110 1001 + { }, // 6a: 0100 1101 0110 1010 + { }, // 6b: 0100 1101 0110 1011 + { }, // 6c: 0100 1101 0110 1100 + { }, // 6d: 0100 1101 0110 1101 + { }, // 6e: 0100 1101 0110 1110 + { }, // 6f: 0100 1101 0110 1111 - { }, // 80: 0111 0100 1000 0000 - { }, // 81: 0111 0100 1000 0001 - { }, // 82: 0111 0100 1000 0010 - { }, // 83: 0111 0100 1000 0011 - { }, // 84: 0111 0100 1000 0100 - { }, // 85: 0111 0100 1000 0101 - { }, // 86: 0111 0100 1000 0110 - { }, // 87: 0111 0100 1000 0111 - {ANAW, "%a" }, // 88: 0111 0100 1000 1000 oooo oooo - { }, // 89: 0111 0100 1000 1001 - { }, // 8a: 0111 0100 1000 1010 - { }, // 8b: 0111 0100 1000 1011 - { }, // 8c: 0111 0100 1000 1100 - {DAN, "EA,BC" }, // 8d: 0111 0100 1000 1101 - {DAN, "EA,DE" }, // 8e: 0111 0100 1000 1110 - {DAN, "EA,HL" }, // 8f: 0111 0100 1000 1111 + { }, // 70: 0100 1101 0111 0000 + { }, // 71: 0100 1101 0111 0001 + { }, // 72: 0100 1101 0111 0010 + { }, // 73: 0100 1101 0111 0011 + { }, // 74: 0100 1101 0111 0100 + { }, // 75: 0100 1101 0111 0101 + { }, // 76: 0100 1101 0111 0110 + { }, // 77: 0100 1101 0111 0111 + { }, // 78: 0100 1101 0111 1000 + { }, // 79: 0100 1101 0111 1001 + { }, // 7a: 0100 1101 0111 1010 + { }, // 7b: 0100 1101 0111 1011 + { }, // 7c: 0100 1101 0111 1100 + { }, // 7d: 0100 1101 0111 1101 + { }, // 7e: 0100 1101 0111 1110 + { }, // 7f: 0100 1101 0111 1111 - {XRAW, "%a" }, // 90: 0111 0100 1001 0000 oooo oooo - { }, // 91: 0111 0100 1001 0001 - { }, // 92: 0111 0100 1001 0010 - { }, // 93: 0111 0100 1001 0011 - { }, // 94: 0111 0100 1001 0100 - {DXR, "EA,BC" }, // 95: 0111 0100 1001 0101 - {DXR, "EA,DE" }, // 96: 0111 0100 1001 0110 - {DXR, "EA,HL" }, // 97: 0111 0100 1001 0111 - {ORAW, "%a" }, // 98: 0111 0100 1001 1000 oooo oooo - { }, // 99: 0111 0100 1001 1001 - { }, // 9a: 0111 0100 1001 1010 - { }, // 9b: 0111 0100 1001 1011 - { }, // 9c: 0111 0100 1001 1100 - {DOR, "EA,BC" }, // 9d: 0111 0100 1001 1101 - {DOR, "EA,DE" }, // 9e: 0111 0100 1001 1110 - {DOR, "EA,HL" }, // 9f: 0111 0100 1001 1111 + { }, // 80: 0100 1101 1000 0000 + { }, // 81: 0100 1101 1000 0001 + { }, // 82: 0100 1101 1000 0010 + { }, // 83: 0100 1101 1000 0011 + { }, // 84: 0100 1101 1000 0100 + { }, // 85: 0100 1101 1000 0101 + { }, // 86: 0100 1101 1000 0110 + { }, // 87: 0100 1101 1000 0111 + { }, // 88: 0100 1101 1000 1000 + { }, // 89: 0100 1101 1000 1001 + { }, // 8a: 0100 1101 1000 1010 + { }, // 8b: 0100 1101 1000 1011 + { }, // 8c: 0100 1101 1000 1100 + { }, // 8d: 0100 1101 1000 1101 + { }, // 8e: 0100 1101 1000 1110 + { }, // 8f: 0100 1101 1000 1111 - {ADDNCW, "%a" }, // a0: 0111 0100 1010 0000 oooo oooo - { }, // a1: 0111 0100 1010 0001 - { }, // a2: 0111 0100 1010 0010 - { }, // a3: 0111 0100 1010 0011 - { }, // a4: 0111 0100 1010 0100 - {DADDNC, "EA,BC" }, // a5: 0111 0100 1010 0101 - {DADDNC, "EA,DE" }, // a6: 0111 0100 1010 0110 - {DADDNC, "EA,HL" }, // a7: 0111 0100 1010 0111 - {GTAW, "%a" }, // a8: 0111 0100 1010 1000 oooo oooo - { }, // a9: 0111 0100 1010 1001 - { }, // aa: 0111 0100 1010 1010 - { }, // ab: 0111 0100 1010 1011 - { }, // ac: 0111 0100 1010 1100 - {DGT, "EA,BC" }, // ad: 0111 0100 1010 1101 - {DGT, "EA,DE" }, // ae: 0111 0100 1010 1110 - {DGT, "EA,HL" }, // af: 0111 0100 1010 1111 + { }, // 90: 0100 1101 1001 0000 + { }, // 91: 0100 1101 1001 0001 + { }, // 92: 0100 1101 1001 0010 + { }, // 93: 0100 1101 1001 0011 + { }, // 94: 0100 1101 1001 0100 + { }, // 95: 0100 1101 1001 0101 + { }, // 96: 0100 1101 1001 0110 + { }, // 97: 0100 1101 1001 0111 + { }, // 98: 0100 1101 1001 1000 + { }, // 99: 0100 1101 1001 1001 + { }, // 9a: 0100 1101 1001 1010 + { }, // 9b: 0100 1101 1001 1011 + { }, // 9c: 0100 1101 1001 1100 + { }, // 9d: 0100 1101 1001 1101 + { }, // 9e: 0100 1101 1001 1110 + { }, // 9f: 0100 1101 1001 1111 - {SUBNBW, "%a" }, // b0: 0111 0100 1011 0000 oooo oooo - { }, // b1: 0111 0100 1011 0001 - { }, // b2: 0111 0100 1011 0010 - { }, // b3: 0111 0100 1011 0011 - { }, // b4: 0111 0100 1011 0100 - {DSUBNB, "EA,BC" }, // b5: 0111 0100 1011 0101 - {DSUBNB, "EA,DE" }, // b6: 0111 0100 1011 0110 - {DSUBNB, "EA,HL" }, // b7: 0111 0100 1011 0111 - {LTAW, "%a" }, // b8: 0111 0100 1011 1000 oooo oooo - { }, // b9: 0111 0100 1011 1001 - { }, // ba: 0111 0100 1011 1010 - { }, // bb: 0111 0100 1011 1011 - { }, // bc: 0111 0100 1011 1100 - {DLT, "EA,BC" }, // bd: 0111 0100 1011 1101 - {DLT, "EA,DE" }, // be: 0111 0100 1011 1110 - {DLT, "EA,HL" }, // bf: 0111 0100 1011 1111 + { }, // a0: 0100 1101 1010 0000 + { }, // a1: 0100 1101 1010 0001 + { }, // a2: 0100 1101 1010 0010 + { }, // a3: 0100 1101 1010 0011 + { }, // a4: 0100 1101 1010 0100 + { }, // a5: 0100 1101 1010 0101 + { }, // a6: 0100 1101 1010 0110 + { }, // a7: 0100 1101 1010 0111 + { }, // a8: 0100 1101 1010 1000 + { }, // a9: 0100 1101 1010 1001 + { }, // aa: 0100 1101 1010 1010 + { }, // ab: 0100 1101 1010 1011 + { }, // ac: 0100 1101 1010 1100 + { }, // ad: 0100 1101 1010 1101 + { }, // ae: 0100 1101 1010 1110 + { }, // af: 0100 1101 1010 1111 - {ADDW, "%a" }, // c0: 0111 0100 1100 0000 oooo oooo - { }, // c1: 0111 0100 1100 0001 - { }, // c2: 0111 0100 1100 0010 - { }, // c3: 0111 0100 1100 0011 - { }, // c4: 0111 0100 1100 0100 - {DADD, "EA,BC" }, // c5: 0111 0100 1100 0101 - {DADD, "EA,DE" }, // c6: 0111 0100 1100 0110 - {DADD, "EA,HL" }, // c7: 0111 0100 1100 0111 - {ONAW, "%a" }, // c8: 0111 0100 1100 1000 oooo oooo - { }, // c9: 0111 0100 1100 1001 - { }, // ca: 0111 0100 1100 1010 - { }, // cb: 0111 0100 1100 1011 - { }, // cc: 0111 0100 1100 1100 - {DON, "EA,BC" }, // cd: 0111 0100 1100 1101 - {DON, "EA,DE" }, // ce: 0111 0100 1100 1110 - {DON, "EA,HL" }, // cf: 0111 0100 1100 1111 + { }, // b0: 0100 1101 1011 0000 + { }, // b1: 0100 1101 1011 0001 + { }, // b2: 0100 1101 1011 0010 + { }, // b3: 0100 1101 1011 0011 + { }, // b4: 0100 1101 1011 0100 + { }, // b5: 0100 1101 1011 0101 + { }, // b6: 0100 1101 1011 0110 + { }, // b7: 0100 1101 1011 0111 + { }, // b8: 0100 1101 1011 1000 + { }, // b9: 0100 1101 1011 1001 + { }, // ba: 0100 1101 1011 1010 + { }, // bb: 0100 1101 1011 1011 + { }, // bc: 0100 1101 1011 1100 + { }, // bd: 0100 1101 1011 1101 + { }, // be: 0100 1101 1011 1110 + { }, // bf: 0100 1101 1011 1111 - {ADCW, "%a" }, // d0: 0111 0100 1101 0000 oooo oooo - { }, // d1: 0111 0100 1101 0001 - { }, // d2: 0111 0100 1101 0010 - { }, // d3: 0111 0100 1101 0011 - { }, // d4: 0111 0100 1101 0100 - {DADC, "EA,BC" }, // d5: 0111 0100 1101 0101 - {DADC, "EA,DE" }, // d6: 0111 0100 1101 0110 - {DADC, "EA,HL" }, // d7: 0111 0100 1101 0111 - {OFFAW, "%a" }, // d8: 0111 0100 1101 1000 oooo oooo - { }, // d9: 0111 0100 1101 1001 - { }, // da: 0111 0100 1101 1010 - { }, // db: 0111 0100 1101 1011 - { }, // dc: 0111 0100 1101 1100 - {DOFF, "EA,BC" }, // dd: 0111 0100 1101 1101 - {DOFF, "EA,DE" }, // de: 0111 0100 1101 1110 - {DOFF, "EA,HL" }, // df: 0111 0100 1101 1111 + {MOV, "PA,A" }, // c0: 0100 1101 1100 0000 + {MOV, "PB,A" }, // c1: 0100 1101 1100 0001 + {MOV, "PC,A" }, // c2: 0100 1101 1100 0010 + {MOV, "PD,A" }, // c3: 0100 1101 1100 0011 + { }, // c4: 0100 1101 1100 0100 + {MOV, "PF,A" }, // c5: 0100 1101 1100 0101 + {MOV, "MKH,A" }, // c6: 0100 1101 1100 0110 + {MOV, "MKL,A" }, // c7: 0100 1101 1100 0111 + { }, // c8: 0100 1101 1100 1000 + {MOV, "SMH,A" }, // c9: 0100 1101 1100 1001 + {MOV, "SML,A" }, // ca: 0100 1101 1100 1010 + {MOV, "EOM,A" }, // cb: 0100 1101 1100 1011 + {MOV, "ETMM,A" }, // cc: 0100 1101 1100 1100 + {MOV, "TMM,A" }, // cd: 0100 1101 1100 1101 + { }, // ce: 0100 1101 1100 1110 + { }, // cf: 0100 1101 1100 1111 - {SUBW, "%a" }, // e0: 0111 0100 1110 0000 oooo oooo - { }, // e1: 0111 0100 1110 0001 - { }, // e2: 0111 0100 1110 0010 - { }, // e3: 0111 0100 1110 0011 - { }, // e4: 0111 0100 1110 0100 - {DSUB, "EA,BC" }, // e5: 0111 0100 1110 0101 - {DSUB, "EA,DE" }, // e6: 0111 0100 1110 0110 - {DSUB, "EA,HL" }, // e7: 0111 0100 1110 0111 - {NEAW, "%a" }, // e8: 0111 0100 1110 1000 oooo oooo - { }, // e9: 0111 0100 1110 1001 - { }, // ea: 0111 0100 1110 1010 - { }, // eb: 0111 0100 1110 1011 - { }, // ec: 0111 0100 1110 1100 - {DNE, "EA,BC" }, // ed: 0111 0100 1110 1101 - {DNE, "EA,DE" }, // ee: 0111 0100 1110 1110 - {DNE, "EA,HL" }, // ef: 0111 0100 1110 1111 + {MOV, "MM,A" }, // d0: 0100 1101 1101 0000 + {MOV, "MCC,A" }, // d1: 0100 1101 1101 0001 + {MOV, "MA,A" }, // d2: 0100 1101 1101 0010 + {MOV, "MB,A" }, // d3: 0100 1101 1101 0011 + {MOV, "MC,A" }, // d4: 0100 1101 1101 0100 + { }, // d5: 0100 1101 1101 0101 + { }, // d6: 0100 1101 1101 0110 + {MOV, "MF,A" }, // d7: 0100 1101 1101 0111 + {MOV, "TXB,A" }, // d8: 0100 1101 1101 1000 + { }, // d9: 0100 1101 1101 1001 + {MOV, "TM0,A" }, // da: 0100 1101 1101 1010 + {MOV, "TM1,A" }, // db: 0100 1101 1101 1011 + { }, // dc: 0100 1101 1101 1100 + { }, // dd: 0100 1101 1101 1101 + { }, // de: 0100 1101 1101 1110 + { }, // df: 0100 1101 1101 1111 - {SBBW, "%a" }, // f0: 0111 0100 1111 0000 oooo oooo - { }, // f1: 0111 0100 1111 0001 - { }, // f2: 0111 0100 1111 0010 - { }, // f3: 0111 0100 1111 0011 - { }, // f4: 0111 0100 1111 0100 - {DSBB, "EA,BC" }, // f5: 0111 0100 1111 0101 - {DSBB, "EA,DE" }, // f6: 0111 0100 1111 0110 - {DSBB, "EA,HL" }, // f7: 0111 0100 1111 0111 - {EQAW, "%a" }, // f8: 0111 0100 1111 1000 oooo oooo - { }, // f9: 0111 0100 1111 1001 - { }, // fa: 0111 0100 1111 1010 - { }, // fb: 0111 0100 1111 1011 - { }, // fc: 0111 0100 1111 1100 - {DEQ, "EA,BC" }, // fd: 0111 0100 1111 1101 - {DEQ, "EA,DE" }, // fe: 0111 0100 1111 1110 - {DEQ, "EA,HL" } // ff: 0111 0100 1111 1111 -}; + { }, // e0: 0100 1101 1110 0000 + { }, // e1: 0100 1101 1110 0001 + { }, // e2: 0100 1101 1110 0010 + { }, // e3: 0100 1101 1110 0011 + { }, // e4: 0100 1101 1110 0100 + {MOV, "MT,A" }, // e5: 0100 1101 1110 0101 7807 + { }, // e6: 0100 1101 1110 0110 + { }, // e7: 0100 1101 1110 0111 + { }, // e8: 0100 1101 1110 1000 + { }, // e9: 0100 1101 1110 1001 + { }, // ea: 0100 1101 1110 1010 + { }, // eb: 0100 1101 1110 1011 + { }, // ec: 0100 1101 1110 1100 + { }, // ed: 0100 1101 1110 1101 + { }, // ee: 0100 1101 1110 1110 + { }, // ef: 0100 1101 1110 1111 -// main opcodes -const dasm_s dasm_s::XX_7810[256] = -{ - {NOP, nullptr }, // 00: 0000 0000 - {LDAW, "%a" }, // 01: 0000 0001 oooo oooo - {INX, "SP" }, // 02: 0000 0010 - {DCX, "SP" }, // 03: 0000 0011 - {LXI, "SP,%w" }, // 04: 0000 0100 llll llll hhhh hhhh - {ANIW, "%a,%b" }, // 05: 0000 0101 oooo oooo xxxx xxxx - { }, // 06: - {ANI, "A,%b" }, // 07: 0000 0111 xxxx xxxx - {MOV, "A,EAH" }, // 08: 0000 1000 - {MOV, "A,EAL" }, // 09: 0000 1001 - {MOV, "A,B" }, // 0a: 0000 1010 - {MOV, "A,C" }, // 0b: 0000 1011 - {MOV, "A,D" }, // 0c: 0000 1100 - {MOV, "A,E" }, // 0d: 0000 1101 - {MOV, "A,H" }, // 0e: 0000 1110 - {MOV, "A,L" }, // 0f: 0000 1111 + { }, // f0: 0100 1101 1111 0000 + { }, // f1: 0100 1101 1111 0001 + { }, // f2: 0100 1101 1111 0010 + { }, // f3: 0100 1101 1111 0011 + { }, // f4: 0100 1101 1111 0100 + { }, // f5: 0100 1101 1111 0101 + { }, // f6: 0100 1101 1111 0110 + { }, // f7: 0100 1101 1111 0111 + { }, // f8: 0100 1101 1111 1000 + { }, // f9: 0100 1101 1111 1001 + { }, // fa: 0100 1101 1111 1010 + { }, // fb: 0100 1101 1111 1011 + { }, // fc: 0100 1101 1111 1100 + { }, // fd: 0100 1101 1111 1101 + { }, // fe: 0100 1101 1111 1110 + { } // ff: 0100 1101 1111 1111 +}; - {EXA, nullptr }, // 10: 0001 0000 7810 - {EXX, nullptr }, // 11: 0001 0001 7810 - {INX, "BC" }, // 12: 0001 0010 - {DCX, "BC" }, // 13: 0001 0011 - {LXI, "BC,%w" }, // 14: 0001 0100 llll llll hhhh hhhh - {ORIW, "%a,%b" }, // 15: 0001 0101 oooo oooo xxxx xxxx - {XRI, "A,%b" }, // 16: 0001 0110 xxxx xxxx - {ORI, "A,%b" }, // 17: 0001 0111 xxxx xxxx - {MOV, "EAH,A" }, // 18: 0001 1000 - {MOV, "EAL,A" }, // 19: 0001 1001 - {MOV, "B,A" }, // 1a: 0001 1010 - {MOV, "C,A" }, // 1b: 0001 1011 - {MOV, "D,A" }, // 1c: 0001 1100 - {MOV, "E,A" }, // 1d: 0001 1101 - {MOV, "H,A" }, // 1e: 0001 1110 - {MOV, "L,A" }, // 1f: 0001 1111 +const upd7810_base_disassembler::dasm_s upd7807_disassembler::d64_7807[256] = +{ + {MVI, "PA,%b" }, // 00: 0110 0100 0000 0000 xxxx xxxx + {MVI, "PB,%b" }, // 01: 0110 0100 0000 0001 xxxx xxxx + {MVI, "PC,%b" }, // 02: 0110 0100 0000 0010 xxxx xxxx + {MVI, "PD,%b" }, // 03: 0110 0100 0000 0011 xxxx xxxx + { }, // 04: 0110 0100 0000 0100 xxxx xxxx + {MVI, "PF,%b" }, // 05: 0110 0100 0000 0101 xxxx xxxx + {MVI, "MKH,%b" }, // 06: 0110 0100 0000 0110 xxxx xxxx + {MVI, "MKL,%b" }, // 07: 0110 0100 0000 0111 xxxx xxxx + {ANI, "PA,%b" }, // 08: 0110 0100 0000 1000 xxxx xxxx + {ANI, "PB,%b" }, // 09: 0110 0100 0000 1001 xxxx xxxx + {ANI, "PC,%b" }, // 0a: 0110 0100 0000 1010 xxxx xxxx + {ANI, "PD,%b" }, // 0b: 0110 0100 0000 1011 xxxx xxxx + { }, // 0c: 0110 0100 0000 1100 xxxx xxxx + {ANI, "PF,%b" }, // 0d: 0110 0100 0000 1101 xxxx xxxx + {ANI, "MKH,%b" }, // 0e: 0110 0100 0000 1110 xxxx xxxx + {ANI, "MKL,%b" }, // 0f: 0110 0100 0000 1111 xxxx xxxx - {INRW, "%a" }, // 20: 0010 0000 oooo oooo - {JB, nullptr }, // 21: 0010 0001 - {INX, "DE" }, // 22: 0010 0010 - {DCX, "DE" }, // 23: 0010 0011 - {LXI, "DE,%w" }, // 24: 0010 0100 llll llll hhhh hhhh - {GTIW, "%a,%b" }, // 25: 0010 0101 oooo oooo xxxx xxxx - {ADINC, "A,%b" }, // 26: 0010 0110 xxxx xxxx - {GTI, "A,%b" }, // 27: 0010 0111 xxxx xxxx - { }, // 28: 0010 1000 - {LDAX, "(BC)" }, // 29: 0010 1001 - {LDAX, "(DE)" }, // 2a: 0010 1010 - {LDAX, "(HL)" }, // 2b: 0010 1011 - {LDAX, "(DE+)" }, // 2c: 0010 1100 - {LDAX, "(HL+)" }, // 2d: 0010 1101 - {LDAX, "(DE-)" }, // 2e: 0010 1110 - {LDAX, "(HL-)" }, // 2f: 0010 1111 + {XRI, "PA,%b" }, // 10: 0110 0100 0001 0000 xxxx xxxx + {XRI, "PB,%b" }, // 11: 0110 0100 0001 0001 xxxx xxxx + {XRI, "PC,%b" }, // 12: 0110 0100 0001 0010 xxxx xxxx + {XRI, "PD,%b" }, // 13: 0110 0100 0001 0011 xxxx xxxx + { }, // 14: 0110 0100 0001 0100 xxxx xxxx + {XRI, "PF,%b" }, // 15: 0110 0100 0001 0101 xxxx xxxx + {XRI, "MKH,%b" }, // 16: 0110 0100 0001 0110 xxxx xxxx + {XRI, "MKL,%b" }, // 17: 0110 0100 0001 0111 xxxx xxxx + {ORI, "PA,%b" }, // 18: 0110 0100 0001 1000 xxxx xxxx + {ORI, "PB,%b" }, // 19: 0110 0100 0001 1001 xxxx xxxx + {ORI, "PC,%b" }, // 1a: 0110 0100 0001 1010 xxxx xxxx + {ORI, "PD,%b" }, // 1b: 0110 0100 0001 1011 xxxx xxxx + { }, // 1c: 0110 0100 0001 1100 xxxx xxxx + {ORI, "PF,%b" }, // 1d: 0110 0100 0001 1101 xxxx xxxx + {ORI, "MKH,%b" }, // 1e: 0110 0100 0001 1110 xxxx xxxx + {ORI, "MKL,%b" }, // 1f: 0110 0100 0001 1111 xxxx xxxx - {DCRW, "%a" }, // 30: 0011 0000 oooo oooo - {BLOCK, nullptr }, // 31: 0011 0001 7810 - {INX, "HL", }, // 32: 0011 0010 - {DCX, "HL", }, // 33: 0011 0011 - {LXI, "HL,%w" }, // 34: 0011 0100 llll llll hhhh hhhh - {LTIW, "%a,%b" }, // 35: 0011 0101 oooo oooo xxxx xxxx - {SUINB, "A,%b" }, // 36: 0011 0110 xxxx xxxx - {LTI, "A,%b" }, // 37: 0011 0111 xxxx xxxx - { }, // 38: - {STAX, "(BC)" }, // 39: 0011 1001 - {STAX, "(DE)" }, // 3a: 0011 1010 - {STAX, "(HL)" }, // 3b: 0011 1011 - {STAX, "(DE+)" }, // 3c: 0011 1100 - {STAX, "(HL+)" }, // 3d: 0011 1101 - {STAX, "(DE-)" }, // 3e: 0011 1110 - {STAX, "(HL-)" }, // 3f: 0011 1111 + {ADINC, "PA,%b" }, // 20: 0110 0100 0010 0000 xxxx xxxx + {ADINC, "PB,%b" }, // 21: 0110 0100 0010 0001 xxxx xxxx + {ADINC, "PC,%b" }, // 22: 0110 0100 0010 0010 xxxx xxxx + {ADINC, "PD,%b" }, // 23: 0110 0100 0010 0011 xxxx xxxx + { }, // 24: 0110 0100 0010 0100 xxxx xxxx + {ADINC, "PF,%b" }, // 25: 0110 0100 0010 0101 xxxx xxxx + {ADINC, "MKH,%b" }, // 26: 0110 0100 0010 0110 xxxx xxxx + {ADINC, "MKL,%b" }, // 27: 0110 0100 0010 0111 xxxx xxxx + {GTI, "PA,%b" }, // 28: 0110 0100 0010 1000 xxxx xxxx + {GTI, "PB,%b" }, // 29: 0110 0100 0010 1001 xxxx xxxx + {GTI, "PC,%b" }, // 2a: 0110 0100 0010 1010 xxxx xxxx + {GTI, "PD,%b" }, // 2b: 0110 0100 0010 1011 xxxx xxxx + { }, // 2c: 0110 0100 0010 1100 xxxx xxxx + {GTI, "PF,%b" }, // 2d: 0110 0100 0010 1101 xxxx xxxx + {GTI, "MKH,%b" }, // 2e: 0110 0100 0010 1110 xxxx xxxx + {GTI, "MKL,%b" }, // 2f: 0110 0100 0010 1111 xxxx xxxx - {CALL, "%w" }, // 40: 0100 0000 llll llll hhhh hhhh - {INR, "A" }, // 41: 0100 0001 - {INR, "B" }, // 42: 0100 0010 - {INR, "C" }, // 43: 0100 0011 - {LXI, "EA,%w" }, // 44: 0100 0100 llll llll hhhh hhhh - {ONIW, "%a,%b" }, // 45: 0100 0101 oooo oooo xxxx xxxx - {ADI, "A,%b" }, // 46: 0100 0110 xxxx xxxx - {ONI, "A,%b" }, // 47: 0100 0111 xxxx xxxx - {d48_7810 }, // 48: prefix - {MVIX, "BC,%b" }, // 49: 0100 1001 xxxx xxxx - {MVIX, "DE,%b" }, // 4a: 0100 1010 xxxx xxxx - {MVIX, "HL,%b" }, // 4b: 0100 1011 xxxx xxxx - {d4C_7810 }, // 4c: prefix - {d4D_7810 }, // 4d: prefix - {JRE, "%d" }, // 4e: 0100 111d dddd dddd - {JRE, "%d" }, // 4f: 0100 111d dddd dddd + {SUINB, "PA,%b" }, // 30: 0110 0100 0011 0000 xxxx xxxx + {SUINB, "PB,%b" }, // 31: 0110 0100 0011 0001 xxxx xxxx + {SUINB, "PC,%b" }, // 32: 0110 0100 0011 0010 xxxx xxxx + {SUINB, "PD,%b" }, // 33: 0110 0100 0011 0011 xxxx xxxx + { }, // 34: 0110 0100 0011 0100 xxxx xxxx + {SUINB, "PF,%b" }, // 35: 0110 0100 0011 0101 xxxx xxxx + {SUINB, "MKH,%b" }, // 36: 0110 0100 0011 0110 xxxx xxxx + {SUINB, "MKL,%b" }, // 37: 0110 0100 0011 0111 xxxx xxxx + {LTI, "PA,%b" }, // 38: 0110 0100 0011 1000 xxxx xxxx + {LTI, "PB,%b" }, // 39: 0110 0100 0011 1001 xxxx xxxx + {LTI, "PC,%b" }, // 3a: 0110 0100 0011 1010 xxxx xxxx + {LTI, "PD,%b" }, // 3b: 0110 0100 0011 1011 xxxx xxxx + { }, // 3c: 0110 0100 0011 1100 xxxx xxxx + {LTI, "PF,%b" }, // 3d: 0110 0100 0011 1101 xxxx xxxx + {LTI, "MKH,%b" }, // 3e: 0110 0100 0011 1110 xxxx xxxx + {LTI, "MKL,%b" }, // 3f: 0110 0100 0011 1111 xxxx xxxx - {EXH, nullptr }, // 50: 0101 0000 7810 - {DCR, "A" }, // 51: 0101 0001 - {DCR, "B" }, // 52: 0101 0010 - {DCR, "C" }, // 53: 0101 0011 - {JMP, "%w" }, // 54: 0101 0100 llll llll hhhh hhhh - {OFFIW, "%a,%b" }, // 55: 0101 0101 oooo oooo xxxx xxx - {ACI, "A,%b" }, // 56: 0101 0110 xxxx xxxx - {OFFI, "A,%b" }, // 57: 0101 0111 xxxx xxxx - {BIT, "0,%a", }, // 58: 0101 1000 oooo oooo 7810 - {BIT, "1,%a", }, // 59: 0101 1001 oooo oooo 7810 - {BIT, "2,%a", }, // 5a: 0101 1010 oooo oooo 7810 - {BIT, "3,%a", }, // 5b: 0101 1011 oooo oooo 7810 - {BIT, "4,%a", }, // 5c: 0101 1100 oooo oooo 7810 - {BIT, "5,%a", }, // 5d: 0101 1101 oooo oooo 7810 - {BIT, "6,%a", }, // 5e: 0101 1110 oooo oooo 7810 - {BIT, "7,%a", }, // 5f: 0101 1111 oooo oooo 7810 + {ADI, "PA,%b" }, // 40: 0110 0100 0100 0000 xxxx xxxx + {ADI, "PB,%b" }, // 41: 0110 0100 0100 0001 xxxx xxxx + {ADI, "PC,%b" }, // 42: 0110 0100 0100 0010 xxxx xxxx + {ADI, "PD,%b" }, // 43: 0110 0100 0100 0011 xxxx xxxx + { }, // 44: 0110 0100 0100 0100 xxxx xxxx + {ADI, "PF,%b" }, // 45: 0110 0100 0100 0101 xxxx xxxx + {ADI, "MKH,%b" }, // 46: 0110 0100 0100 0110 xxxx xxxx + {ADI, "MKL,%b" }, // 47: 0110 0100 0100 0111 xxxx xxxx + {ONI, "PA,%b" }, // 48: 0110 0100 0100 1000 xxxx xxxx + {ONI, "PB,%b" }, // 49: 0110 0100 0100 1001 xxxx xxxx + {ONI, "PC,%b" }, // 4a: 0110 0100 0100 1010 xxxx xxxx + {ONI, "PD,%b" }, // 4b: 0110 0100 0100 1011 xxxx xxxx + { }, // 4c: 0110 0100 0100 1100 xxxx xxxx + {ONI, "PF,%b" }, // 4d: 0110 0100 0100 1101 xxxx xxxx + {ONI, "MKH,%b" }, // 4e: 0110 0100 0100 1110 xxxx xxxx + {ONI, "MKL,%b" }, // 4f: 0110 0100 0100 1111 xxxx xxxx - {d60 }, // 60: prefix - {DAA, nullptr }, // 61: 0110 0001 - {RETI, nullptr }, // 62: 0110 0010 - {STAW, "%a" }, // 63: 0110 0011 oooo oooo - {d64_7810 }, // 64: prefix - {NEIW, "%a,%b" }, // 65: 0110 0101 oooo oooo xxxx xxxx - {SUI, "A,%b" }, // 66: 0110 0110 xxxx xxxx - {NEI, "A,%b" }, // 67: 0110 0111 xxxx xxxx - {MVI, "V,%b" }, // 68: 0110 1000 xxxx xxxx - {MVI, "A,%b" }, // 69: 0110 1001 xxxx xxxx - {MVI, "B,%b" }, // 6a: 0110 1010 xxxx xxxx - {MVI, "C,%b" }, // 6b: 0110 1011 xxxx xxxx - {MVI, "D,%b" }, // 6c: 0110 1100 xxxx xxxx - {MVI, "E,%b" }, // 6d: 0110 1101 xxxx xxxx - {MVI, "H,%b" }, // 6e: 0110 1110 xxxx xxxx - {MVI, "L,%b" }, // 6f: 0110 1111 xxxx xxxx + {ACI, "PA,%b" }, // 50: 0110 0100 0101 0000 xxxx xxxx + {ACI, "PB,%b" }, // 51: 0110 0100 0101 0001 xxxx xxxx + {ACI, "PC,%b" }, // 52: 0110 0100 0101 0010 xxxx xxxx + {ACI, "PD,%b" }, // 53: 0110 0100 0101 0011 xxxx xxxx + { }, // 54: 0110 0100 0101 0100 xxxx xxxx + {ACI, "PF,%b" }, // 55: 0110 0100 0101 0101 xxxx xxxx + {ACI, "MKH,%b" }, // 56: 0110 0100 0101 0110 xxxx xxxx + {ACI, "MKL,%b" }, // 57: 0110 0100 0101 0111 xxxx xxxx + {OFFI, "PA,%b" }, // 58: 0110 0100 0101 1000 xxxx xxxx + {OFFI, "PB,%b" }, // 59: 0110 0100 0101 1001 xxxx xxxx + {OFFI, "PC,%b" }, // 5a: 0110 0100 0101 1010 xxxx xxxx + {OFFI, "PD,%b" }, // 5b: 0110 0100 0101 1011 xxxx xxxx + { }, // 5c: 0110 0100 0101 1100 xxxx xxxx + {OFFI, "PF,%b" }, // 5d: 0110 0100 0101 1101 xxxx xxxx + {OFFI, "MKH,%b" }, // 5e: 0110 0100 0101 1110 xxxx xxxx + {OFFI, "MKL,%b" }, // 5f: 0110 0100 0101 1111 xxxx xxxx - {d70 }, // 70: prefix - {MVIW, "%a,%b" }, // 71: 0111 0001 oooo oooo xxxx xxxx - {SOFTI, nullptr }, // 72: 0111 0010 - { }, // 73: - {d74 }, // 74: prefix - {EQIW, "%a,%b" }, // 75: 0111 0101 oooo oooo xxxx xxxx - {SBI, "A,%b" }, // 76: 0111 0110 xxxx xxxx - {EQI, "A,%b" }, // 77: 0111 0111 xxxx xxxx - {CALF, "%f" }, // 78: 0111 1ddd dddd dddd - {CALF, "%f" }, // 79: 0111 1ddd dddd dddd - {CALF, "%f" }, // 7a: 0111 1ddd dddd dddd - {CALF, "%f" }, // 7b: 0111 1ddd dddd dddd - {CALF, "%f" }, // 7c: 0111 1ddd dddd dddd - {CALF, "%f" }, // 7d: 0111 1ddd dddd dddd - {CALF, "%f" }, // 7e: 0111 1ddd dddd dddd - {CALF, "%f" }, // 7f: 0111 1ddd dddd dddd + {SUI, "PA,%b" }, // 60: 0110 0100 0110 0000 xxxx xxxx + {SUI, "PB,%b" }, // 61: 0110 0100 0110 0001 xxxx xxxx + {SUI, "PC,%b" }, // 62: 0110 0100 0110 0010 xxxx xxxx + {SUI, "PD,%b" }, // 63: 0110 0100 0110 0011 xxxx xxxx + { }, // 64: 0110 0100 0110 0100 xxxx xxxx + {SUI, "PF,%b" }, // 65: 0110 0100 0110 0101 xxxx xxxx + {SUI, "MKH,%b" }, // 66: 0110 0100 0110 0110 xxxx xxxx + {SUI, "MKL,%b" }, // 67: 0110 0100 0110 0111 xxxx xxxx + {NEI, "PA,%b" }, // 68: 0110 0100 0110 1000 xxxx xxxx + {NEI, "PB,%b" }, // 69: 0110 0100 0110 1001 xxxx xxxx + {NEI, "PC,%b" }, // 6a: 0110 0100 0110 1010 xxxx xxxx + {NEI, "PD,%b" }, // 6b: 0110 0100 0110 1011 xxxx xxxx + { }, // 6c: 0110 0100 0110 1100 xxxx xxxx + {NEI, "PF,%b" }, // 6d: 0110 0100 0110 1101 xxxx xxxx + {NEI, "MKH,%b" }, // 6e: 0110 0100 0110 1110 xxxx xxxx + {NEI, "MKL,%b" }, // 6f: 0110 0100 0110 1111 xxxx xxxx - {CALT, "%t" }, // 80: 100t tttt - {CALT, "%t" }, // 81: 100t tttt - {CALT, "%t" }, // 82: 100t tttt - {CALT, "%t" }, // 83: 100t tttt - {CALT, "%t" }, // 84: 100t tttt - {CALT, "%t" }, // 85: 100t tttt - {CALT, "%t" }, // 86: 100t tttt - {CALT, "%t" }, // 87: 100t tttt - {CALT, "%t" }, // 88: 100t tttt - {CALT, "%t" }, // 89: 100t tttt - {CALT, "%t" }, // 8a: 100t tttt - {CALT, "%t" }, // 8b: 100t tttt - {CALT, "%t" }, // 8c: 100t tttt - {CALT, "%t" }, // 8d: 100t tttt - {CALT, "%t" }, // 8e: 100t tttt - {CALT, "%t" }, // 8f: 100t tttt + {SBI, "PA,%b" }, // 70: 0110 0100 0111 0000 xxxx xxxx + {SBI, "PB,%b" }, // 71: 0110 0100 0111 0001 xxxx xxxx + {SBI, "PC,%b" }, // 72: 0110 0100 0111 0010 xxxx xxxx + {SBI, "PD,%b" }, // 73: 0110 0100 0111 0011 xxxx xxxx + { }, // 74: 0110 0100 0111 0100 xxxx xxxx + {SBI, "PF,%b" }, // 75: 0110 0100 0111 0101 xxxx xxxx + {SBI, "MKH,%b" }, // 76: 0110 0100 0111 0110 xxxx xxxx + {SBI, "MKL,%b" }, // 77: 0110 0100 0111 0111 xxxx xxxx + {EQI, "PA,%b" }, // 78: 0110 0100 0111 1000 xxxx xxxx + {EQI, "PB,%b" }, // 79: 0110 0100 0111 1001 xxxx xxxx + {EQI, "PC,%b" }, // 7a: 0110 0100 0111 1010 xxxx xxxx + {EQI, "PD,%b" }, // 7b: 0110 0100 0111 1011 xxxx xxxx + { }, // 7c: 0110 0100 0111 1100 xxxx xxxx + {EQI, "PF,%b" }, // 7d: 0110 0100 0111 1101 xxxx xxxx + {EQI, "MKH,%b" }, // 7e: 0110 0100 0111 1110 xxxx xxxx + {EQI, "MKL,%b" }, // 7f: 0110 0100 0111 1111 xxxx xxxx - {CALT, "%t" }, // 90: 100t tttt - {CALT, "%t" }, // 91: 100t tttt - {CALT, "%t" }, // 92: 100t tttt - {CALT, "%t" }, // 93: 100t tttt - {CALT, "%t" }, // 94: 100t tttt - {CALT, "%t" }, // 95: 100t tttt - {CALT, "%t" }, // 96: 100t tttt - {CALT, "%t" }, // 97: 100t tttt - {CALT, "%t" }, // 98: 100t tttt - {CALT, "%t" }, // 99: 100t tttt - {CALT, "%t" }, // 9a: 100t tttt - {CALT, "%t" }, // 9b: 100t tttt - {CALT, "%t" }, // 9c: 100t tttt - {CALT, "%t" }, // 9d: 100t tttt - {CALT, "%t" }, // 9e: 100t tttt - {CALT, "%t" }, // 9f: 100t tttt + { }, // 80: 0110 0100 1000 0000 xxxx xxxx + {MVI, "SMH,%b" }, // 81: 0110 0100 1000 0001 xxxx xxxx + { }, // 82: 0110 0100 1000 0010 xxxx xxxx + {MVI, "EOM,%b" }, // 83: 0110 0100 1000 0011 xxxx xxxx + { }, // 84: 0110 0100 1000 0100 xxxx xxxx + {MVI, "TMM,%b" }, // 85: 0110 0100 1000 0101 xxxx xxxx + { }, // 86: 0110 0100 1000 0110 xxxx xxxx + { }, // 87: 0110 0100 1000 0111 xxxx xxxx + { }, // 88: 0110 0100 1000 1000 xxxx xxxx + {ANI, "SMH,%b" }, // 89: 0110 0100 1000 1001 xxxx xxxx + { }, // 8a: 0110 0100 1000 1010 xxxx xxxx + {ANI, "EOM,%b" }, // 8b: 0110 0100 1000 1011 xxxx xxxx + { }, // 8c: 0110 0100 1000 1100 xxxx xxxx + {ANI, "TMM,%b" }, // 8d: 0110 0100 1000 1101 xxxx xxxx + { }, // 8e: 0110 0100 1000 1110 xxxx xxxx + { }, // 8f: 0110 0100 1000 1111 xxxx xxxx - {POP, "VA" }, // a0: 1010 0000 - {POP, "BC" }, // a1: 1010 0001 - {POP, "DE" }, // a2: 1010 0010 - {POP, "HL", }, // a3: 1010 0011 - {POP, "EA" }, // a4: 1010 0100 - {DMOV, "EA,BC" }, // a5: 1010 0101 - {DMOV, "EA,DE" }, // a6: 1010 0110 - {DMOV, "EA,HL" }, // a7: 1010 0111 - {INX, "EA" }, // a8: 1010 1000 - {DCX, "EA" }, // a9: 1010 1001 - {EI, nullptr }, // aa: 1010 1010 - {LDAX, "(DE+%b)" }, // ab: 1010 1011 dddd dddd - {LDAX, "(HL+A)" }, // ac: 1010 1100 - {LDAX, "(HL+B)" }, // ad: 1010 1101 - {LDAX, "(HL+EA)" }, // ae: 1010 1110 - {LDAX, "(HL+%b)" }, // af: 1010 1111 dddd dddd + { }, // 90: 0110 0100 1001 0000 xxxx xxxx + {XRI, "SMH,%b" }, // 91: 0110 0100 1001 0001 xxxx xxxx + { }, // 92: 0110 0100 1001 0010 xxxx xxxx + {XRI, "EOM,%b" }, // 93: 0110 0100 1001 0011 xxxx xxxx + { }, // 94: 0110 0100 1001 0100 xxxx xxxx + {XRI, "TMM,%b" }, // 95: 0110 0100 1001 0101 xxxx xxxx + { }, // 96: 0110 0100 1001 0110 xxxx xxxx + { }, // 97: 0110 0100 1001 0111 xxxx xxxx + { }, // 98: 0110 0100 1001 1000 xxxx xxxx + {ORI, "SMH,%b" }, // 99: 0110 0100 1001 1001 xxxx xxxx + { }, // 9a: 0110 0100 1001 1010 xxxx xxxx + {ORI, "EOM,%b" }, // 9b: 0110 0100 1001 1011 xxxx xxxx + { }, // 9c: 0110 0100 1001 1100 xxxx xxxx + {ORI, "TMM,%b" }, // 9d: 0110 0100 1001 1101 xxxx xxxx + { }, // 9e: 0110 0100 1001 1110 xxxx xxxx + { }, // 9f: 0110 0100 1001 1111 xxxx xxxx - {PUSH, "VA" }, // b0: 1011 0000 - {PUSH, "BC" }, // b1: 1011 0001 - {PUSH, "DE" }, // b2: 1011 0010 - {PUSH, "HL", }, // b3: 1011 0011 - {PUSH, "EA" }, // b4: 1011 0100 - {DMOV, "BC,EA" }, // b5: 1011 0101 - {DMOV, "DE,EA" }, // b6: 1011 0110 - {DMOV, "HL,EA" }, // b7: 1011 0111 - {RET, nullptr }, // b8: 1011 1000 - {RETS, nullptr }, // b9: 1011 1001 - {DI, nullptr }, // ba: 1011 1010 - {STAX, "(DE+%b)" }, // bb: 1011 1011 dddd dddd - {STAX, "(HL+A)" }, // bc: 1011 1100 - {STAX, "(HL+B)" }, // bd: 1011 1101 - {STAX, "(HL+EA)" }, // be: 1011 1110 - {STAX, "(HL+%b)" }, // bf: 1011 1111 dddd dddd + { }, // a0: 0110 0100 1010 0000 xxxx xxxx + {ADINC, "SMH,%b" }, // a1: 0110 0100 1010 0001 xxxx xxxx + { }, // a2: 0110 0100 1010 0010 xxxx xxxx + {ADINC, "EOM,%b" }, // a3: 0110 0100 1010 0011 xxxx xxxx + { }, // a4: 0110 0100 1010 0100 xxxx xxxx + {ADINC, "TMM,%b" }, // a5: 0110 0100 1010 0101 xxxx xxxx + { }, // a6: 0110 0100 1010 0110 xxxx xxxx + { }, // a7: 0110 0100 1010 0111 xxxx xxxx + { }, // a8: 0110 0100 1010 1000 xxxx xxxx + {GTI, "SMH,%b" }, // a9: 0110 0100 1010 1001 xxxx xxxx + { }, // aa: 0110 0100 1010 1010 xxxx xxxx + {GTI, "EOM,%b" }, // ab: 0110 0100 1010 1011 xxxx xxxx + { }, // ac: 0110 0100 1010 1100 xxxx xxxx + {GTI, "TMM,%b" }, // ad: 0110 0100 1010 1101 xxxx xxxx + {GTI, "PT,%b" }, // ae: 0110 0100 1010 1110 xxxx xxxx + { }, // af: 0110 0100 1010 1111 xxxx xxxx - {JR, "%o" }, // c0: 11oo oooo - {JR, "%o" }, // c1: 11oo oooo - {JR, "%o" }, // c2: 11oo oooo - {JR, "%o" }, // c3: 11oo oooo - {JR, "%o" }, // c4: 11oo oooo - {JR, "%o" }, // c5: 11oo oooo - {JR, "%o" }, // c6: 11oo oooo - {JR, "%o" }, // c7: 11oo oooo - {JR, "%o" }, // c8: 11oo oooo - {JR, "%o" }, // c9: 11oo oooo - {JR, "%o" }, // ca: 11oo oooo - {JR, "%o" }, // cb: 11oo oooo - {JR, "%o" }, // cc: 11oo oooo - {JR, "%o" }, // cd: 11oo oooo - {JR, "%o" }, // ce: 11oo oooo - {JR, "%o" }, // cf: 11oo oooo + { }, // b0: 0110 0100 1011 0000 xxxx xxxx + {SUINB, "SMH,%b" }, // b1: 0110 0100 1011 0001 xxxx xxxx + { }, // b2: 0110 0100 1011 0010 xxxx xxxx + {SUINB, "EOM,%b" }, // b3: 0110 0100 1011 0011 xxxx xxxx + { }, // b4: 0110 0100 1011 0100 xxxx xxxx + {SUINB, "TMM,%b" }, // b5: 0110 0100 1011 0101 xxxx xxxx + { }, // b6: 0110 0100 1011 0110 xxxx xxxx + { }, // b7: 0110 0100 1011 0111 xxxx xxxx + { }, // b8: 0110 0100 1011 1000 xxxx xxxx + {LTI, "SMH,%b" }, // b9: 0110 0100 1011 1001 xxxx xxxx + { }, // ba: 0110 0100 1011 1010 xxxx xxxx + {LTI, "EOM,%b" }, // bb: 0110 0100 1011 1011 xxxx xxxx + { }, // bc: 0110 0100 1011 1100 xxxx xxxx + {LTI, "TMM,%b" }, // bd: 0110 0100 1011 1101 xxxx xxxx + {LTI, "PT,%b" }, // be: 0110 0100 1011 1110 xxxx xxxx + { }, // bf: 0110 0100 1011 1111 xxxx xxxx - {JR, "%o" }, // d0: 11oo oooo - {JR, "%o" }, // d1: 11oo oooo - {JR, "%o" }, // d2: 11oo oooo - {JR, "%o" }, // d3: 11oo oooo - {JR, "%o" }, // d4: 11oo oooo - {JR, "%o" }, // d5: 11oo oooo - {JR, "%o" }, // d6: 11oo oooo - {JR, "%o" }, // d7: 11oo oooo - {JR, "%o" }, // d8: 11oo oooo - {JR, "%o" }, // d9: 11oo oooo - {JR, "%o" }, // da: 11oo oooo - {JR, "%o" }, // db: 11oo oooo - {JR, "%o" }, // dc: 11oo oooo - {JR, "%o" }, // dd: 11oo oooo - {JR, "%o" }, // de: 11oo oooo - {JR, "%o" }, // df: 11oo oooo + { }, // c0: 0110 0100 1100 0000 xxxx xxxx + {ADI, "SMH,%b" }, // c1: 0110 0100 1100 0001 xxxx xxxx + { }, // c2: 0110 0100 1100 0010 xxxx xxxx + {ADI, "EOM,%b" }, // c3: 0110 0100 1100 0011 xxxx xxxx + { }, // c4: 0110 0100 1100 0100 xxxx xxxx + {ADI, "TMM,%b" }, // c5: 0110 0100 1100 0101 xxxx xxxx + { }, // c6: 0110 0100 1100 0110 xxxx xxxx + { }, // c7: 0110 0100 1100 0111 xxxx xxxx + { }, // c8: 0110 0100 1100 1000 xxxx xxxx + {ONI, "SMH,%b" }, // c9: 0110 0100 1100 1001 xxxx xxxx + { }, // ca: 0110 0100 1100 1010 xxxx xxxx + {ONI, "EOM,%b" }, // cb: 0110 0100 1100 1011 xxxx xxxx + { }, // cc: 0110 0100 1100 1100 xxxx xxxx + {ONI, "TMM,%b" }, // cd: 0110 0100 1100 1101 xxxx xxxx + {ONI, "PT,%b" }, // ce: 0110 0100 1100 1110 xxxx xxxx + { }, // cf: 0110 0100 1100 1111 xxxx xxxx - {JR, "%o" }, // e0: 11oo oooo - {JR, "%o" }, // e1: 11oo oooo - {JR, "%o" }, // e2: 11oo oooo - {JR, "%o" }, // e3: 11oo oooo - {JR, "%o" }, // e4: 11oo oooo - {JR, "%o" }, // e5: 11oo oooo - {JR, "%o" }, // e6: 11oo oooo - {JR, "%o" }, // e7: 11oo oooo - {JR, "%o" }, // e8: 11oo oooo - {JR, "%o" }, // e9: 11oo oooo - {JR, "%o" }, // ea: 11oo oooo - {JR, "%o" }, // eb: 11oo oooo - {JR, "%o" }, // ec: 11oo oooo - {JR, "%o" }, // ed: 11oo oooo - {JR, "%o" }, // ee: 11oo oooo - {JR, "%o" }, // ef: 11oo oooo + { }, // d0: 0110 0100 1101 0000 xxxx xxxx + {ACI, "SMH,%b" }, // d1: 0110 0100 1101 0001 xxxx xxxx + { }, // d2: 0110 0100 1101 0010 xxxx xxxx + {ACI, "EOM,%b" }, // d3: 0110 0100 1101 0011 xxxx xxxx + { }, // d4: 0110 0100 1101 0100 xxxx xxxx + {ACI, "TMM,%b" }, // d5: 0110 0100 1101 0101 xxxx xxxx + { }, // d6: 0110 0100 1101 0110 xxxx xxxx + { }, // d7: 0110 0100 1101 0111 xxxx xxxx + { }, // d8: 0110 0100 1101 1000 xxxx xxxx + {OFFI, "SMH,%b" }, // d9: 0110 0100 1101 1001 xxxx xxxx + { }, // da: 0110 0100 1101 1010 xxxx xxxx + {OFFI, "EOM,%b" }, // db: 0110 0100 1101 1011 xxxx xxxx + { }, // dc: 0110 0100 1101 1100 xxxx xxxx + {OFFI, "TMM,%b" }, // dd: 0110 0100 1101 1101 xxxx xxxx + {OFFI, "PT,%b" }, // de: 0110 0100 1101 1110 xxxx xxxx + { }, // df: 0110 0100 1101 1111 xxxx xxxx - {JR, "%o" }, // f0: 11oo oooo - {JR, "%o" }, // f1: 11oo oooo - {JR, "%o" }, // f2: 11oo oooo - {JR, "%o" }, // f3: 11oo oooo - {JR, "%o" }, // f4: 11oo oooo - {JR, "%o" }, // f5: 11oo oooo - {JR, "%o" }, // f6: 11oo oooo - {JR, "%o" }, // f7: 11oo oooo - {JR, "%o" }, // f8: 11oo oooo - {JR, "%o" }, // f9: 11oo oooo - {JR, "%o" }, // fa: 11oo oooo - {JR, "%o" }, // fb: 11oo oooo - {JR, "%o" }, // fc: 11oo oooo - {JR, "%o" }, // fd: 11oo oooo - {JR, "%o" }, // fe: 11oo oooo - {JR, "%o" } // ff: 11oo oooo + { }, // e0: 0110 0100 1110 0000 xxxx xxxx + {SUI, "SMH,%b" }, // e1: 0110 0100 1110 0001 xxxx xxxx + { }, // e2: 0110 0100 1110 0010 xxxx xxxx + {SUI, "EOM,%b" }, // e3: 0110 0100 1110 0011 xxxx xxxx + { }, // e4: 0110 0100 1110 0100 xxxx xxxx + {SUI, "TMM,%b" }, // e5: 0110 0100 1110 0101 xxxx xxxx + { }, // e6: 0110 0100 1110 0110 xxxx xxxx + { }, // e7: 0110 0100 1110 0111 xxxx xxxx + { }, // e8: 0110 0100 1110 1000 xxxx xxxx + {NEI, "SMH,%b" }, // e9: 0110 0100 1110 1001 xxxx xxxx + { }, // ea: 0110 0100 1110 1010 xxxx xxxx + {NEI, "EOM,%b" }, // eb: 0110 0100 1110 1011 xxxx xxxx + { }, // ec: 0110 0100 1110 1100 xxxx xxxx + {NEI, "TMM,%b" }, // ed: 0110 0100 1110 1101 xxxx xxxx + {NEI, "PT,%b" }, // ee: 0110 0100 1110 1110 xxxx xxxx + { }, // ef: 0110 0100 1110 1111 xxxx xxxx + + { }, // f0: 0110 0100 1111 0000 xxxx xxxx + {SBI, "SMH,%b" }, // f1: 0110 0100 1111 0001 xxxx xxxx + { }, // f2: 0110 0100 1111 0010 xxxx xxxx + {SBI, "EOM,%b" }, // f3: 0110 0100 1111 0011 xxxx xxxx + { }, // f4: 0110 0100 1111 0100 xxxx xxxx + {SBI, "TMM,%b" }, // f5: 0110 0100 1111 0101 xxxx xxxx + { }, // f6: 0110 0100 1111 0110 xxxx xxxx + { }, // f7: 0110 0100 1111 0111 xxxx xxxx + { }, // f8: 0110 0100 1111 1000 xxxx xxxx + {EQI, "SMH,%b" }, // f9: 0110 0100 1111 1001 xxxx xxxx + { }, // fa: 0110 0100 1111 1010 xxxx xxxx + {EQI, "EOM,%b" }, // fb: 0110 0100 1111 1011 xxxx xxxx + { }, // fc: 0110 0100 1111 1100 xxxx xxxx + {EQI, "TMM,%b" }, // fd: 0110 0100 1111 1101 xxxx xxxx + {EQI, "PT,%b" }, // fe: 0110 0100 1111 1110 xxxx xxxx + { } // ff: 0110 0100 1111 1111 xxxx xxxx }; -const dasm_s dasm_s::XX_7807[256] = +const upd7810_base_disassembler::dasm_s upd7807_disassembler::XX_7807[256] = { {NOP, nullptr }, // 00: 0000 0000 {LDAW, "%a" }, // 01: 0000 0001 oooo oooo @@ -4020,7 +3827,7 @@ const dasm_s dasm_s::XX_7807[256] = * *********************************************************/ -const dasm_s dasm_s::d48_7801[256] = { +const upd7810_base_disassembler::dasm_s upd7801_disassembler::d48_7801[256] = { // 0x00 - 0x3F { SKIT, "F0" }, { SKIT, "FT" }, { SKIT, "F1" }, { SKIT, "F2" }, { SKIT, "FS" }, { }, { }, { }, @@ -4106,7 +3913,7 @@ const dasm_s dasm_s::d48_7801[256] = { { }, { }, { }, { } }; -const dasm_s dasm_s::d4C_7801[256] = { +const upd7810_base_disassembler::dasm_s upd7801_disassembler::d4C_7801[256] = { // 0x00 - 0x3F { IN, nullptr }, { IN, nullptr }, { IN, nullptr }, { IN, nullptr }, { IN, nullptr }, { IN, nullptr }, { IN, nullptr }, { IN, nullptr }, @@ -4192,7 +3999,7 @@ const dasm_s dasm_s::d4C_7801[256] = { { }, { }, { }, { } }; -const dasm_s dasm_s::d4D_7801[256] = { +const upd7810_base_disassembler::dasm_s upd7801_disassembler::d4D_7801[256] = { // 0x00 - 0x3F { OUT, nullptr }, { OUT, nullptr }, { OUT, nullptr }, { OUT, nullptr }, { OUT, nullptr }, { OUT, nullptr }, { OUT, nullptr }, { OUT, nullptr }, @@ -4278,7 +4085,7 @@ const dasm_s dasm_s::d4D_7801[256] = { { }, { }, { }, { } }; -const dasm_s dasm_s::d60_7801[256] = { +const upd7810_base_disassembler::dasm_s upd7801_disassembler::d60_7801[256] = { // 0x00 - 0x3F { }, { }, { }, { }, { }, { }, { }, { }, @@ -4364,7 +4171,7 @@ const dasm_s dasm_s::d60_7801[256] = { { EQA, "A,D" }, { EQA, "A,E" }, { EQA, "A,H" }, { EQA, "A,L" } }; -const dasm_s dasm_s::d64_7801[256] = { +const upd7810_base_disassembler::dasm_s upd7801_disassembler::d64_7801[256] = { // 0x00 - 0x3F { }, { }, { }, { }, { }, { }, { }, { }, @@ -4450,7 +4257,7 @@ const dasm_s dasm_s::d64_7801[256] = { { }, { }, { }, { } }; -const dasm_s dasm_s::d70_7801[256] = { +const upd7810_base_disassembler::dasm_s upd7801_disassembler::d70_7801[256] = { // 0x00 - 0x3F { }, { }, { }, { }, { }, { }, { }, { }, @@ -4536,7 +4343,7 @@ const dasm_s dasm_s::d70_7801[256] = { { EQAX, "DE+" }, { EQAX, "HL+" }, { EQAX, "DE-" }, { EQAX, "HL-" }, }; -const dasm_s dasm_s::d74_7801[256] = { +const upd7810_base_disassembler::dasm_s upd7801_disassembler::d74_7801[256] = { // 0x00 - 0x3F { }, { }, { }, { }, { }, { }, { }, { }, @@ -4622,7 +4429,7 @@ const dasm_s dasm_s::d74_7801[256] = { { }, { }, { }, { } }; -const dasm_s dasm_s::XX_7801[256] = { +const upd7810_base_disassembler::dasm_s upd7801_disassembler::XX_7801[256] = { // 0x00 - 0x3F { NOP, nullptr }, { HALT, nullptr }, { INX, "SP" }, { DCX, "SP" }, { LXI, "SP,%w" }, { ANIW, "%a,%b" }, { }, { ANI, "A,%b" }, @@ -4714,7 +4521,7 @@ const dasm_s dasm_s::XX_7801[256] = { * *********************************************************/ -const dasm_s dasm_s::d48_78c05[256] = { +const upd7810_base_disassembler::dasm_s upd78c05_disassembler::d48_78c05[256] = { // 0x00 - 0x3F { SKIT, "F0" }, { SKIT, "FT" }, { SKIT, "F1" }, { }, // TODO: PDF doesn't mention SKIT and SK { SKIT, "FS" }, { }, { }, { }, @@ -4800,7 +4607,7 @@ const dasm_s dasm_s::d48_78c05[256] = { { }, { }, { }, { } }; -const dasm_s dasm_s::d4C_78c05[256] = { +const upd7810_base_disassembler::dasm_s upd78c05_disassembler::d4C_78c05[256] = { // 0x00 - 0x3F { }, { }, { }, { }, { }, { }, { }, { }, @@ -4867,7 +4674,7 @@ const dasm_s dasm_s::d4C_78c05[256] = { // 0xC0 - 0xFF { MOV, "A,PA" }, { MOV, "A,PB" }, { MOV, "A,PC" }, { MOV, "A,MK" }, { MOV, "A,MB" }, { MOV, "A,MC" }, { MOV, "A,TM0" }, { MOV, "A,TM1" }, - { MOV, "A,S" }, { }, { }, { }, // TODO: Figure out what regsiter C9 indicates + { MOV, "A,S" }, { }, { }, { }, // TODO: Figure out what register C9 indicates { }, { }, { }, { }, { }, { }, { }, { }, @@ -4886,7 +4693,7 @@ const dasm_s dasm_s::d4C_78c05[256] = { { }, { }, { }, { } }; -const dasm_s dasm_s::d4D_78c05[256] = { +const upd7810_base_disassembler::dasm_s upd78c05_disassembler::d4D_78c05[256] = { // 0x00 - 0x3F { }, { }, { }, { }, { }, { }, { }, { }, @@ -4972,7 +4779,7 @@ const dasm_s dasm_s::d4D_78c05[256] = { { }, { }, { }, { } }; -const dasm_s dasm_s::d60_78c05[256] = { +const upd7810_base_disassembler::dasm_s upd78c05_disassembler::d60_78c05[256] = { // 0x00 - 0x3F { }, { }, { }, { }, { }, { }, { }, { }, @@ -5058,7 +4865,7 @@ const dasm_s dasm_s::d60_78c05[256] = { { EQA, "A,D" }, { EQA, "A,E" }, { EQA, "A,H" }, { EQA, "A,L" } }; -const dasm_s dasm_s::d64_78c05[256] = { +const upd7810_base_disassembler::dasm_s upd78c05_disassembler::d64_78c05[256] = { // 0x00 - 0x3F { }, { }, { }, { }, { }, { }, { }, { }, @@ -5144,7 +4951,7 @@ const dasm_s dasm_s::d64_78c05[256] = { { }, { }, { }, { } }; -const dasm_s dasm_s::d70_78c05[256] = { +const upd7810_base_disassembler::dasm_s upd78c05_disassembler::d70_78c05[256] = { // 0x00 - 0x3F { }, { }, { }, { }, { }, { }, { }, { }, @@ -5230,7 +5037,7 @@ const dasm_s dasm_s::d70_78c05[256] = { { EQAX, "DE+" }, { EQAX, "HL+" }, { EQAX, "DE-" }, { EQAX, "HL-" }, }; -const dasm_s dasm_s::d74_78c05[256] = { +const upd7810_base_disassembler::dasm_s upd78c05_disassembler::d74_78c05[256] = { // 0x00 - 0x3F { }, { }, { }, { }, { }, { }, { }, { }, @@ -5316,7 +5123,7 @@ const dasm_s dasm_s::d74_78c05[256] = { { }, { }, { }, { }, }; -const dasm_s dasm_s::XX_78c05[256] = { +const upd7810_base_disassembler::dasm_s upd78c05_disassembler::XX_78c05[256] = { // 0x00 - 0x3F { NOP, nullptr }, { HALT, nullptr }, { INX, "SP" }, { DCX, "SP" }, { LXI, "SP,%w" }, { ANIW, "%a,%b" }, { }, { ANI, "A,%b" }, @@ -5404,7 +5211,7 @@ const dasm_s dasm_s::XX_78c05[256] = { // register names for bit manipulation instructions -const char *const regname[32] = +const char *const upd7810_base_disassembler::regname[32] = { "illegal", "illegal", "illegal", "illegal", "illegal", "illegal", "illegal", "illegal", @@ -5416,17 +5223,17 @@ const char *const regname[32] = "illegal", "TMM", "PT", "illegal" }; -offs_t Dasm( std::ostream &stream, offs_t pc, const dasm_s (&dasmXX)[256], const uint8_t *oprom, const uint8_t *opram, bool is_7810 ) +offs_t upd7810_base_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - unsigned idx = 0; - const uint8_t op = oprom[idx++]; - const dasm_s *desc = &dasmXX[op]; + offs_t idx = pc; + const uint8_t op = opcodes.r8(idx++); + const dasm_s *desc = &m_dasmXX[op]; if (desc->is_prefix()) - desc = &desc->prefix_get(oprom[idx++]); + desc = &desc->prefix_get(opcodes.r8(idx++)); util::stream_format(stream, "%-8.8s", desc->name()); - uint32_t flags = desc->is_call() ? DASMFLAG_STEP_OVER : desc->is_return() ? DASMFLAG_STEP_OUT : 0; + uint32_t flags = desc->is_call() ? STEP_OVER : desc->is_return() ? STEP_OUT : 0; uint8_t op2; int offset; uint16_t ea; @@ -5439,28 +5246,28 @@ offs_t Dasm( std::ostream &stream, offs_t pc, const dasm_s (&dasmXX)[256], const switch (*a) { case 'a': /* address V * 256 + offset */ - op2 = opram[idx++]; + op2 = params.r8(idx++); util::stream_format(stream, "VV:%02X", op2); break; case 'b': /* immediate byte */ - util::stream_format(stream, "$%02X", opram[idx++]); + util::stream_format(stream, "$%02X", params.r8(idx++)); break; case 'w': /* immediate word */ - ea = opram[idx++]; - ea += opram[idx++] << 8; + ea = params.r8(idx++); + ea += params.r8(idx++) << 8; util::stream_format(stream, "$%04X", ea); break; case 'd': /* JRE address */ - op2 = oprom[idx++]; + op2 = opcodes.r8(idx++); offset = (op & 1) ? -(256 - op2): + op2; util::stream_format(stream, "$%04X", ( pc + idx + offset ) & 0xFFFF ); break; case 't': /* CALT address */ - ea = 0x80 + 2 * (op & (is_7810 ? 0x1f : 0x3f)); + ea = 0x80 + 2 * (op & (m_is_7810 ? 0x1f : 0x3f)); util::stream_format(stream, "($%04X)", ea); break; case 'f': /* CALF address */ - op2 = oprom[idx++]; + op2 = opcodes.r8(idx++); ea = 0x800 + 0x100 * (op & 0x07) + op2; util::stream_format(stream, "$%04X", ea); break; @@ -5469,7 +5276,7 @@ offs_t Dasm( std::ostream &stream, offs_t pc, const dasm_s (&dasmXX)[256], const util::stream_format(stream, "$%04X", ( pc + idx + offset ) & 0xFFFF ); break; case 'i': /* bit manipulation */ - op2 = oprom[idx++]; + op2 = opcodes.r8(idx++); util::stream_format(stream, "%s,%d", regname[op2 & 0x1f], op2 >> 5); break; default: @@ -5480,27 +5287,30 @@ offs_t Dasm( std::ostream &stream, offs_t pc, const dasm_s (&dasmXX)[256], const stream << *a; } - return idx | flags | DASMFLAG_SUPPORTED; + return (idx - pc) | flags | SUPPORTED; +} + +upd7810_base_disassembler::upd7810_base_disassembler(const dasm_s *table, bool is_7810) : m_is_7810(is_7810), m_dasmXX(table) +{ } -} // anonymous namespace +uint32_t upd7810_base_disassembler::opcode_alignment() const +{ + return 1; +} -CPU_DISASSEMBLE( upd7810 ) +upd7810_disassembler::upd7810_disassembler() : upd7810_base_disassembler(XX_7810, true) { - return Dasm( stream, pc, dasm_s::XX_7810, oprom, opram, true ); } -CPU_DISASSEMBLE( upd7807 ) +upd7807_disassembler::upd7807_disassembler() : upd7810_base_disassembler(XX_7807, true) { - return Dasm( stream, pc, dasm_s::XX_7807, oprom, opram, true ); } -CPU_DISASSEMBLE( upd7801 ) +upd7801_disassembler::upd7801_disassembler() : upd7810_base_disassembler(XX_7801, false) { - return Dasm( stream, pc, dasm_s::XX_7801, oprom, opram, false ); } -CPU_DISASSEMBLE( upd78c05 ) +upd78c05_disassembler::upd78c05_disassembler() : upd7810_base_disassembler(XX_78c05, false) { - return Dasm( stream, pc, dasm_s::XX_78c05, oprom, opram, false ); } diff --git a/src/devices/cpu/upd7810/upd7810_dasm.h b/src/devices/cpu/upd7810/upd7810_dasm.h new file mode 100644 index 00000000000..a367ab24a48 --- /dev/null +++ b/src/devices/cpu/upd7810/upd7810_dasm.h @@ -0,0 +1,291 @@ +// license:BSD-3-Clause +// copyright-holders:Juergen Buchmueller +/***************************************************************************** + * + * Portable uPD7810/11, 7810H/11H, 78C10/C11/C14 disassembler + * + * NS20030112: added 7807. + * + *****************************************************************************/ + +#ifndef MAME_CPU_UPD7810_UPD7810DASM_H +#define MAME_CPU_UPD7810_UPD7810DASM_H + +#pragma once + +class upd7810_base_disassembler : public util::disasm_interface +{ +public: + struct dasm_s { + public: + dasm_s(); + dasm_s(uint8_t t, const char *a); + dasm_s(const dasm_s (&a)[256]); + + const char *name() const; + const char *args() const; + + bool is_prefix() const; + bool is_call() const; + bool is_return() const; + + const dasm_s &prefix_get(uint8_t op) const; + + uint8_t m_token; + const void *m_args; + + static const char *const token_names[]; + }; + + enum + { + prefix = 0, + illegal, + ACI, + ADC, + ADCW, + ADCX, + ADD, + ADDNC, + ADDNCW, + ADDNCX, + ADDW, + ADDX, + ADI, + ADINC, + ANA, + ANAW, + ANAX, + AND, + ANI, + ANIW, + BIT, + BLOCK, + CALB, + CALF, + CALL, + CALT, + CLC, + CLR, /* 7807 */ + CMC, /* 7807 */ + DAA, + DADC, + DADD, + DADDNC, + DAN, + DCR, + DCRW, + DCX, + DEQ, + DGT, + DI, + DIV, + DLT, + DMOV, + DNE, + DOFF, + DON, + DOR, + DRLL, + DRLR, + DSBB, + DSLL, + DSLR, + DSUB, + DSUBNB, + DXR, + EADD, + EI, + EQA, + EQAW, + EQAX, + EQI, + EQIW, + ESUB, + EX, /* 7801 */ + EXA, + EXH, + EXX, + EXR, /* 7807 */ + GTA, + GTAW, + GTAX, + GTI, + GTIW, + HALT, + IN, /* 7801 */ + INR, + INRW, + INX, + JB, + JEA, + JMP, + JR, + JRE, + LBCD, + LDAW, + LDAX, + LDEAX, + LDED, + LHLD, + LSPD, + LTA, + LTAW, + LTAX, + LTI, + LTIW, + LXI, + MOV, + MUL, + MVI, + MVIW, + MVIX, + NEA, + NEAW, + NEAX, + NEGA, + NEI, + NEIW, + NOP, + NOT, /* 7807 */ + OFFA, + OFFAW, + OFFAX, + OFFI, + OFFIW, + ONA, + ONAW, + ONAX, + ONI, + ONIW, + OR, /* 7807 */ + ORA, + ORAW, + ORAX, + ORI, + ORIW, + OUT, /* 7801 */ + PER, /* 7801 */ + PEX, /* 7801 */ + POP, + PUSH, + RET, + RETI, + RETS, + RLD, + RLL, + RLR, + RRD, + SBB, + SBBW, + SBBX, + SBCD, + SBI, + SDED, + SETB, /* 7807 */ + SHLD, + SIO, /* 7801 */ + SK, + SKIT, + SKN, + SKNIT, + SLL, + SLLC, + SLR, + SLRC, + SOFTI, + SSPD, + STAW, + STAX, + STC, + STEAX, + STM, /* 7801 */ + STOP, + SUB, + SUBNB, + SUBNBW, + SUBNBX, + SUBW, + SUBX, + SUI, + SUINB, + TABLE, + XOR, /* 7807 */ + XRA, + XRAW, + XRAX, + XRI + }; + + upd7810_base_disassembler(const dasm_s *table, bool is_7810); + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + + static const char *const regname[32]; + static const dasm_s d60[256]; + static const dasm_s d70[256]; + static const dasm_s d74[256]; + + bool m_is_7810; + const dasm_s *m_dasmXX; +}; + +class upd7810_disassembler : public upd7810_base_disassembler +{ +public: + static const dasm_s XX_7810[256]; + static const dasm_s d48_7810[256]; + static const dasm_s d4C_7810[256]; + static const dasm_s d4D_7810[256]; + static const dasm_s d64_7810[256]; + + upd7810_disassembler(); + virtual ~upd7810_disassembler() = default; +}; + +class upd7807_disassembler : public upd7810_base_disassembler +{ +public: + static const dasm_s XX_7807[256]; + static const dasm_s d48_7807[256]; + static const dasm_s d4C_7807[256]; + static const dasm_s d4D_7807[256]; + static const dasm_s d64_7807[256]; + + upd7807_disassembler(); + virtual ~upd7807_disassembler() = default; +}; + +class upd7801_disassembler : public upd7810_base_disassembler +{ +public: + static const dasm_s XX_7801[256]; + static const dasm_s d48_7801[256]; + static const dasm_s d4C_7801[256]; + static const dasm_s d4D_7801[256]; + static const dasm_s d60_7801[256]; + static const dasm_s d64_7801[256]; + static const dasm_s d70_7801[256]; + static const dasm_s d74_7801[256]; + + upd7801_disassembler(); + virtual ~upd7801_disassembler() = default; +}; + +class upd78c05_disassembler : public upd7810_base_disassembler +{ +public: + static const dasm_s XX_78c05[256]; + static const dasm_s d48_78c05[256]; + static const dasm_s d4C_78c05[256]; + static const dasm_s d4D_78c05[256]; + static const dasm_s d60_78c05[256]; + static const dasm_s d64_78c05[256]; + static const dasm_s d70_78c05[256]; + static const dasm_s d74_78c05[256]; + + upd78c05_disassembler(); + virtual ~upd78c05_disassembler() = default; +}; + +#endif diff --git a/src/devices/cpu/v30mz/v30mz.cpp b/src/devices/cpu/v30mz/v30mz.cpp index 718c07a2ec8..3b62098bf5c 100644 --- a/src/devices/cpu/v30mz/v30mz.cpp +++ b/src/devices/cpu/v30mz/v30mz.cpp @@ -44,6 +44,7 @@ #include "emu.h" #include "v30mz.h" +#include "cpu/nec/necdasm.h" #include "debugger.h" @@ -1304,10 +1305,9 @@ void v30mz_cpu_device::execute_set_input( int inptnum, int state ) } -offs_t v30mz_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *v30mz_cpu_device::create_disassembler() { - extern CPU_DISASSEMBLE( nec ); - return CPU_DISASSEMBLE_NAME(nec)(this, stream, pc, oprom, opram, options); + return new nec_disassembler; } diff --git a/src/devices/cpu/v30mz/v30mz.h b/src/devices/cpu/v30mz/v30mz.h index 1b8665fd0ea..d19d29fa6fd 100644 --- a/src/devices/cpu/v30mz/v30mz.h +++ b/src/devices/cpu/v30mz/v30mz.h @@ -47,9 +47,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 7; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; void interrupt(int int_num); diff --git a/src/devices/cpu/v60/v60.cpp b/src/devices/cpu/v60/v60.cpp index dbe8ed08599..33184a0c776 100644 --- a/src/devices/cpu/v60/v60.cpp +++ b/src/devices/cpu/v60/v60.cpp @@ -75,6 +75,7 @@ Package: 132-pin PGA, 200-pin QFP #include "emu.h" #include "v60.h" +#include "v60d.h" #include "debugger.h" DEFINE_DEVICE_TYPE(V60, v60_device, "v60", "V60") @@ -115,17 +116,9 @@ device_memory_interface::space_config_vector v60_device::memory_space_config() c } -offs_t v60_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *v60_device::create_disassembler() { - extern CPU_DISASSEMBLE( v60 ); - return CPU_DISASSEMBLE_NAME(v60)(this, stream, pc, oprom, opram, options); -} - - -offs_t v70_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) -{ - extern CPU_DISASSEMBLE( v70 ); - return CPU_DISASSEMBLE_NAME(v70)(this, stream, pc, oprom, opram, options); + return new v60_disassembler; } diff --git a/src/devices/cpu/v60/v60.h b/src/devices/cpu/v60/v60.h index b891630f048..b0d51f9e867 100644 --- a/src/devices/cpu/v60/v60.h +++ b/src/devices/cpu/v60/v60.h @@ -110,9 +110,7 @@ protected: virtual void state_export(const device_state_entry &entry) override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 22; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: typedef uint32_t (v60_device::*am_func)(); @@ -777,9 +775,6 @@ class v70_device : public v60_device public: // construction/destruction v70_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); - -protected: - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; }; diff --git a/src/devices/cpu/v60/v60d.cpp b/src/devices/cpu/v60/v60d.cpp index 70fcdab8296..2a14f65436f 100644 --- a/src/devices/cpu/v60/v60d.cpp +++ b/src/devices/cpu/v60/v60d.cpp @@ -2,11 +2,10 @@ // copyright-holders:Farfetch'd, R. Belmont #include "emu.h" -#include "debugger.h" -#include "v60.h" +#include "v60d.h" // Register names -static const char *const v60_reg_names[69] = { +const char *const v60_disassembler::v60_reg_names[69] = { "R0", "R1", "R2", "R3", "R4", "R5", "R6", "R7", "R8", "R9", "R10", "R11", @@ -26,39 +25,19 @@ static const char *const v60_reg_names[69] = { "ADTMR1","Reserved","Reserved","Reserved" }; -static const uint8_t *rombase; -static offs_t pcbase; - -#define readop(a) rombase[(a) - pcbase] - -static signed char read8(unsigned pc) -{ - return readop(pc); -} - -static signed short read16(unsigned pc) -{ - return readop(pc) | (readop(pc+1) << 8); -} - -static signed int read32(unsigned pc) -{ - return readop(pc) | (readop(pc+1) << 8)| (readop(pc+2) << 16)| (readop(pc+3) << 24); -} - -static void out_AM_Register(int reg, std::ostream &stream) +void v60_disassembler::out_AM_Register(int reg, std::ostream &stream) { stream << v60_reg_names[reg]; } -static void out_AM_RegisterIndirect(int reg, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_RegisterIndirect(int reg, int opsize, std::ostream &stream) { if(opsize & 0x80) stream << '@'; util::stream_format(stream, "[%s]", v60_reg_names[reg]); } -static void out_AM_RegisterIndirectIndexed(int rn, int rx, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_RegisterIndirectIndexed(int rn, int rx, int opsize, std::ostream &stream) { if(opsize & 0x80) util::stream_format(stream, "%s@[%s]", v60_reg_names[rx], v60_reg_names[rn]); @@ -67,21 +46,21 @@ static void out_AM_RegisterIndirectIndexed(int rn, int rx, int opsize, std::ostr } -static void out_AM_Autoincrement(int reg, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_Autoincrement(int reg, int opsize, std::ostream &stream) { if(opsize & 0x80) stream << '@'; util::stream_format(stream, "[%s+]", v60_reg_names[reg]); } -static void out_AM_Autodecrement(int reg, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_Autodecrement(int reg, int opsize, std::ostream &stream) { if(opsize & 0x80) stream << '@'; util::stream_format(stream, "[-%s]", v60_reg_names[reg]); } -static void out_AM_Displacement(int reg, int disp, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_Displacement(int reg, int disp, int opsize, std::ostream &stream) { util::stream_format(stream, "%s%X%s[%s]", disp >= 0 ? "" : "-", disp >= 0 ? disp : -disp, @@ -89,7 +68,7 @@ static void out_AM_Displacement(int reg, int disp, int opsize, std::ostream &str v60_reg_names[reg]); } -static void out_AM_DisplacementIndexed(int rn, int rx, int disp, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_DisplacementIndexed(int rn, int rx, int disp, int opsize, std::ostream &stream) { if(opsize & 0x80) util::stream_format(stream, "%s@%s%X[%s]", v60_reg_names[rx], disp >= 0 ? "" : "-", disp >= 0 ? disp : -disp,v60_reg_names[rn]); @@ -97,12 +76,12 @@ static void out_AM_DisplacementIndexed(int rn, int rx, int disp, int opsize, std util::stream_format(stream, "%s%X[%s](%s)", disp >= 0 ? "" : "-", disp >= 0 ? disp : -disp,v60_reg_names[rn], v60_reg_names[rx]); } -static void out_AM_PCDisplacement(unsigned pc, int disp, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_PCDisplacement(offs_t pc, int disp, int opsize, std::ostream &stream) { util::stream_format(stream, "%X%s[PC]", pc+disp, opsize & 0x80 ? "@" : ""); } -static void out_AM_PCDisplacementIndexed(unsigned pc, int disp, int rx, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_PCDisplacementIndexed(offs_t pc, int disp, int rx, int opsize, std::ostream &stream) { if(opsize & 0x80) util::stream_format(stream, "%s@%X[PC]", v60_reg_names[rx], pc+disp); @@ -110,7 +89,7 @@ static void out_AM_PCDisplacementIndexed(unsigned pc, int disp, int rx, int opsi util::stream_format(stream, "%X[PC](%s)", pc+disp, v60_reg_names[rx]); } -static void out_AM_DisplacementIndirect(int reg, int disp, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_DisplacementIndirect(int reg, int disp, int opsize, std::ostream &stream) { util::stream_format(stream, "%s[%s%X[%s]]", opsize & 0x80 ? "@" : "", @@ -118,7 +97,7 @@ static void out_AM_DisplacementIndirect(int reg, int disp, int opsize, std::ostr v60_reg_names[reg]); } -static void out_AM_DisplacementIndirectIndexed(int rn, int rx, int disp, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_DisplacementIndirectIndexed(int rn, int rx, int disp, int opsize, std::ostream &stream) { if(opsize & 0x80) util::stream_format(stream, "%s@[%s%X[%s]]", v60_reg_names[rx], disp >= 0 ? "" : "-", disp >= 0 ? disp : -disp,v60_reg_names[rn]); @@ -126,12 +105,12 @@ static void out_AM_DisplacementIndirectIndexed(int rn, int rx, int disp, int ops util::stream_format(stream, "[%s%X[%s]](%s)", disp >= 0 ? "" : "-", disp >= 0 ? disp : -disp,v60_reg_names[rn], v60_reg_names[rx]); } -static void out_AM_PCDisplacementIndirect(unsigned pc, int disp, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_PCDisplacementIndirect(offs_t pc, int disp, int opsize, std::ostream &stream) { util::stream_format(stream, "%s[%X[PC]]", opsize & 0x80 ? "@" : "", pc+disp); } -static void out_AM_PCDisplacementIndirectIndexed(unsigned pc, int disp, int rx, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_PCDisplacementIndirectIndexed(offs_t pc, int disp, int rx, int opsize, std::ostream &stream) { if(opsize & 0x80) util::stream_format(stream, "%s@[%X[PC]]", v60_reg_names[rx], pc+disp); @@ -139,7 +118,7 @@ static void out_AM_PCDisplacementIndirectIndexed(unsigned pc, int disp, int rx, util::stream_format(stream, "[%X[PC]](%s)", pc+disp, v60_reg_names[rx]); } -static void out_AM_DoubleDisplacement(int reg, int disp2, int disp1, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_DoubleDisplacement(int reg, int disp2, int disp1, int opsize, std::ostream &stream) { util::stream_format(stream, "%s%X%s[%s%X[%s]]", disp1 >= 0 ? "" : "-", disp1 >= 0 ? disp1 : -disp1, @@ -148,7 +127,7 @@ static void out_AM_DoubleDisplacement(int reg, int disp2, int disp1, int opsize, v60_reg_names[reg]); } -static void out_AM_PCDoubleDisplacement(unsigned pc, int disp2, int disp1, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_PCDoubleDisplacement(offs_t pc, int disp2, int disp1, int opsize, std::ostream &stream) { util::stream_format(stream, "%s%X%s[%X[PC]]", disp1 >= 0 ? "" : "-", disp1 >= 0 ? disp1 : -disp1, @@ -156,14 +135,14 @@ static void out_AM_PCDoubleDisplacement(unsigned pc, int disp2, int disp1, int o disp2 + pc); } -static void out_AM_DirectAddress(unsigned addr, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_DirectAddress(unsigned addr, int opsize, std::ostream &stream) { if(opsize & 0x80) stream << '@'; util::stream_format(stream, "%X", addr); } -static void out_AM_DirectAddressIndexed(unsigned addr, int rx, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_DirectAddressIndexed(unsigned addr, int rx, int opsize, std::ostream &stream) { if(opsize & 0x80) util::stream_format(stream, "%s@%X", v60_reg_names[rx], addr); @@ -171,14 +150,14 @@ static void out_AM_DirectAddressIndexed(unsigned addr, int rx, int opsize, std:: util::stream_format(stream, "%X(%s)", addr, v60_reg_names[rx]); } -static void out_AM_DirectAddressDeferred(unsigned addr, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_DirectAddressDeferred(unsigned addr, int opsize, std::ostream &stream) { if(opsize & 0x80) stream << '@'; util::stream_format(stream, "[%X]", addr); } -static void out_AM_DirectAddressDeferredIndexed(unsigned addr, int rx, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_DirectAddressDeferredIndexed(unsigned addr, int rx, int opsize, std::ostream &stream) { if(opsize & 0x80) util::stream_format(stream, "%s@[%X]", v60_reg_names[rx], addr); @@ -186,7 +165,7 @@ static void out_AM_DirectAddressDeferredIndexed(unsigned addr, int rx, int opsiz util::stream_format(stream, "[%X](%s)", addr, v60_reg_names[rx]); } -static void out_AM_Immediate(unsigned value, int opsize, std::ostream &stream) +void v60_disassembler::out_AM_Immediate(unsigned value, int opsize, std::ostream &stream) { if(opsize == 0) value &= 0xff; @@ -196,21 +175,21 @@ static void out_AM_Immediate(unsigned value, int opsize, std::ostream &stream) util::stream_format(stream, "#%X", value); } -static int decode_AM(unsigned ipc, unsigned pc, int m, int opsize, std::ostream &stream) +u32 v60_disassembler::decode_AM(unsigned ipc, offs_t pc, int m, int opsize, const data_buffer &opcodes, std::ostream &stream) { - unsigned char mod = readop(pc); + unsigned char mod = opcodes.r8(pc); if(m) { switch(mod>>5) { case 0: // Double displacement (8 bit) - out_AM_DoubleDisplacement(mod&0x1F, read8(pc+1), read8(pc+2), opsize, stream); + out_AM_DoubleDisplacement(mod&0x1F, opcodes.r8(pc+1), opcodes.r8(pc+2), opsize, stream); return 3; case 1: // Double displacement (16 bit) - out_AM_DoubleDisplacement(mod&0x1F, read16(pc+1), read16(pc+3), opsize, stream); + out_AM_DoubleDisplacement(mod&0x1F, opcodes.r16(pc+1), opcodes.r16(pc+3), opsize, stream); return 5; case 2: // Double displacement (32 bit) - out_AM_DoubleDisplacement(mod&0x1F, read32(pc+1), read32(pc+5), opsize, stream); + out_AM_DoubleDisplacement(mod&0x1F, opcodes.r32(pc+1), opcodes.r32(pc+5), opsize, stream); return 9; case 3: // Register @@ -226,69 +205,69 @@ static int decode_AM(unsigned ipc, unsigned pc, int m, int opsize, std::ostream return 1; case 6: - switch (readop(pc+1)>>5) + switch (opcodes.r8(pc+1)>>5) { case 0: // Displacement indexed (8 bit) - out_AM_DisplacementIndexed(readop(pc+1)&0x1F, mod&0x1F, read8(pc+2), opsize, stream); + out_AM_DisplacementIndexed(opcodes.r8(pc+1)&0x1F, mod&0x1F, opcodes.r8(pc+2), opsize, stream); return 3; case 1: // Displacement indexed (16 bit) - out_AM_DisplacementIndexed(readop(pc+1)&0x1F, mod&0x1F, read16(pc+2), opsize, stream); + out_AM_DisplacementIndexed(opcodes.r8(pc+1)&0x1F, mod&0x1F, opcodes.r16(pc+2), opsize, stream); return 4; case 2: // Displacement indexed (32 bit) - out_AM_DisplacementIndexed(readop(pc+1)&0x1F, mod&0x1F, read32(pc+2), opsize, stream); + out_AM_DisplacementIndexed(opcodes.r8(pc+1)&0x1F, mod&0x1F, opcodes.r32(pc+2), opsize, stream); return 6; case 3: // Register indirect indexed - out_AM_RegisterIndirectIndexed(readop(pc+1)&0x1F, mod&0x1F, opsize, stream); + out_AM_RegisterIndirectIndexed(opcodes.r8(pc+1)&0x1F, mod&0x1F, opsize, stream); return 2; case 4: // Displacement indirect indexed (8 bit) - out_AM_DisplacementIndirectIndexed(readop(pc+1)&0x1F, mod&0x1F, read8(pc+2), opsize, stream); + out_AM_DisplacementIndirectIndexed(opcodes.r8(pc+1)&0x1F, mod&0x1F, opcodes.r8(pc+2), opsize, stream); return 3; case 5: // Displacement indirect indexed (16 bit) - out_AM_DisplacementIndirectIndexed(readop(pc+1)&0x1F, mod&0x1F, read16(pc+2), opsize, stream); + out_AM_DisplacementIndirectIndexed(opcodes.r8(pc+1)&0x1F, mod&0x1F, opcodes.r16(pc+2), opsize, stream); return 4; case 6: // Displacement indirect indexed (32 bit) - out_AM_DisplacementIndirectIndexed(readop(pc+1)&0x1F, mod&0x1F, read32(pc+2), opsize, stream); + out_AM_DisplacementIndirectIndexed(opcodes.r8(pc+1)&0x1F, mod&0x1F, opcodes.r32(pc+2), opsize, stream); return 6; case 7: - switch (readop(pc+1)&0x1F) + switch (opcodes.r8(pc+1)&0x1F) { case 16: // PC Displacement Indexed (8 bit) - out_AM_PCDisplacementIndexed(ipc, read8(pc+2), mod&0x1F, opsize, stream); + out_AM_PCDisplacementIndexed(ipc, opcodes.r8(pc+2), mod&0x1F, opsize, stream); return 3; case 17: // PC Displacement Indexed (16 bit) - out_AM_PCDisplacementIndexed(ipc, read16(pc+2), mod&0x1F, opsize, stream); + out_AM_PCDisplacementIndexed(ipc, opcodes.r16(pc+2), mod&0x1F, opsize, stream); return 4; case 18: // PC Displacement Indexed (32 bit) - out_AM_PCDisplacementIndexed(ipc, read32(pc+2), mod&0x1F, opsize, stream); + out_AM_PCDisplacementIndexed(ipc, opcodes.r32(pc+2), mod&0x1F, opsize, stream); return 6; case 19: // Direct Address Indexed - out_AM_DirectAddressIndexed(read32(pc+2), mod&0x1F, opsize, stream); + out_AM_DirectAddressIndexed(opcodes.r32(pc+2), mod&0x1F, opsize, stream); return 6; case 24: // PC Displacement Indirect Indexed(8 bit) - out_AM_PCDisplacementIndirectIndexed(ipc, read8(pc+2), mod&0x1F, opsize, stream); + out_AM_PCDisplacementIndirectIndexed(ipc, opcodes.r8(pc+2), mod&0x1F, opsize, stream); return 3; case 25: // PC Displacement Indirect Indexed (16 bit) - out_AM_PCDisplacementIndirectIndexed(ipc, read16(pc+2), mod&0x1F, opsize, stream); + out_AM_PCDisplacementIndirectIndexed(ipc, opcodes.r16(pc+2), mod&0x1F, opsize, stream); return 4; case 26: // PC Displacement Indirect Indexed (32 bit) - out_AM_PCDisplacementIndirectIndexed(ipc, read32(pc+2), mod&0x1F, opsize, stream); + out_AM_PCDisplacementIndirectIndexed(ipc, opcodes.r32(pc+2), mod&0x1F, opsize, stream); return 6; case 27: // Direct Address Deferred Indexed - out_AM_DirectAddressDeferredIndexed(read32(pc+2), mod&0x1F, opsize, stream); + out_AM_DirectAddressDeferredIndexed(opcodes.r32(pc+2), mod&0x1F, opsize, stream); return 6; default: @@ -308,15 +287,15 @@ static int decode_AM(unsigned ipc, unsigned pc, int m, int opsize, std::ostream } else { switch(mod>>5) { case 0: // Displacement (8 bit) - out_AM_Displacement(mod&0x1F, read8(pc+1), opsize, stream); + out_AM_Displacement(mod&0x1F, opcodes.r8(pc+1), opsize, stream); return 2; case 1: // Displacement (16 bit) - out_AM_Displacement(mod&0x1F, read16(pc+1), opsize, stream); + out_AM_Displacement(mod&0x1F, opcodes.r16(pc+1), opsize, stream); return 3; case 2: // Displacement (32 bit) - out_AM_Displacement(mod&0x1F, read32(pc+1), opsize, stream); + out_AM_Displacement(mod&0x1F, opcodes.r32(pc+1), opsize, stream); return 5; case 3: // Register indirect @@ -324,15 +303,15 @@ static int decode_AM(unsigned ipc, unsigned pc, int m, int opsize, std::ostream return 1; case 4: // Displacement indirect (8 bit) - out_AM_DisplacementIndirect(mod&0x1F, read8(pc+1), opsize, stream); + out_AM_DisplacementIndirect(mod&0x1F, opcodes.r8(pc+1), opsize, stream); return 2; case 5: // Displacement indirect (16 bit) - out_AM_DisplacementIndirect(mod&0x1F, read16(pc+1), opsize, stream); + out_AM_DisplacementIndirect(mod&0x1F, opcodes.r16(pc+1), opsize, stream); return 3; case 6: // Displacement indirect (32 bit) - out_AM_DisplacementIndirect(mod&0x1F, read32(pc+1), opsize, stream); + out_AM_DisplacementIndirect(mod&0x1F, opcodes.r32(pc+1), opsize, stream); return 5; case 7: @@ -357,34 +336,34 @@ static int decode_AM(unsigned ipc, unsigned pc, int m, int opsize, std::ostream return 1; case 16: // PC Displacement (8 bit) - out_AM_PCDisplacement(ipc, read8(pc+1), opsize, stream); + out_AM_PCDisplacement(ipc, opcodes.r8(pc+1), opsize, stream); return 2; case 17: // PC Displacement (16 bit) - out_AM_PCDisplacement(ipc, read16(pc+1), opsize, stream); + out_AM_PCDisplacement(ipc, opcodes.r16(pc+1), opsize, stream); return 3; case 18: // PC Displacement (32 bit) - out_AM_PCDisplacement(ipc, read32(pc+1), opsize, stream); + out_AM_PCDisplacement(ipc, opcodes.r32(pc+1), opsize, stream); return 5; case 19: // Direct Address - out_AM_DirectAddress(read32(pc+1), opsize, stream); + out_AM_DirectAddress(opcodes.r32(pc+1), opsize, stream); return 5; case 20: switch(opsize&0x7F) { case 0: // Immediate (8 bit) - out_AM_Immediate(read8(pc+1), opsize, stream); + out_AM_Immediate(opcodes.r8(pc+1), opsize, stream); return 2; case 1: // Immediate (16 bit) - out_AM_Immediate(read16(pc+1), opsize, stream); + out_AM_Immediate(opcodes.r16(pc+1), opsize, stream); return 3; case 2: // Immediate (32 bit) - out_AM_Immediate(read32(pc+1), opsize, stream); + out_AM_Immediate(opcodes.r32(pc+1), opsize, stream); return 5; default: @@ -393,31 +372,31 @@ static int decode_AM(unsigned ipc, unsigned pc, int m, int opsize, std::ostream } case 24: // PC Displacement Indirect (8 bit) - out_AM_PCDisplacementIndirect(ipc, read8(pc+1), opsize, stream); + out_AM_PCDisplacementIndirect(ipc, opcodes.r8(pc+1), opsize, stream); return 2; case 25: // PC Displacement Indirect (16 bit) - out_AM_PCDisplacementIndirect(ipc, read16(pc+1), opsize, stream); + out_AM_PCDisplacementIndirect(ipc, opcodes.r16(pc+1), opsize, stream); return 3; case 26: // PC Displacement Indirect (32 bit) - out_AM_PCDisplacementIndirect(ipc, read32(pc+1), opsize, stream); + out_AM_PCDisplacementIndirect(ipc, opcodes.r32(pc+1), opsize, stream); return 5; case 27: // Direct Address Deferred - out_AM_DirectAddressDeferred(read32(pc+1), opsize, stream); + out_AM_DirectAddressDeferred(opcodes.r32(pc+1), opsize, stream); return 5; case 28: // PC Double Displacement (8 bit) - out_AM_PCDoubleDisplacement(ipc, read8(pc+1), read8(pc+2), opsize, stream); + out_AM_PCDoubleDisplacement(ipc, opcodes.r8(pc+1), opcodes.r8(pc+2), opsize, stream); return 3; case 29: // PC Double Displacement (16 bit) - out_AM_PCDoubleDisplacement(ipc, read16(pc+1), read16(pc+3), opsize, stream); + out_AM_PCDoubleDisplacement(ipc, opcodes.r16(pc+1), opcodes.r16(pc+3), opsize, stream); return 5; case 30: // PC Double Displacement (32 bit) - out_AM_PCDoubleDisplacement(ipc, read32(pc+1), read32(pc+5), opsize, stream); + out_AM_PCDoubleDisplacement(ipc, opcodes.r32(pc+1), opcodes.r32(pc+5), opsize, stream); return 9; default: @@ -433,92 +412,92 @@ static int decode_AM(unsigned ipc, unsigned pc, int m, int opsize, std::ostream } -static int decode_F1(const char *opnm, int opsize1, int opsize2, unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::decode_F1(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { - unsigned char code = readop(pc); + unsigned char code = opcodes.r8(pc); util::stream_format(stream, "%-8s", opnm); if(code & 0x20) { - int ret = decode_AM(ipc, pc+1, code & 0x40, opsize1, stream) + 2; + int ret = decode_AM(ipc, pc+1, code & 0x40, opsize1, opcodes, stream) + 2; stream << ", "; out_AM_Register(code & 0x1f, stream); return ret; } else { out_AM_Register(code & 0x1f, stream); stream << ", "; - return decode_AM(ipc, pc+1, code & 0x40, opsize1, stream) + 2; + return decode_AM(ipc, pc+1, code & 0x40, opsize1, opcodes, stream) + 2; } } -static int decode_F2(const char *opnm, int opsize1, int opsize2, unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::decode_F2(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { int ret; - unsigned char code = readop(pc); + unsigned char code = opcodes.r8(pc); util::stream_format(stream, "%-8s", opnm); - ret = decode_AM(ipc, pc+1, code & 0x40, opsize1, stream); + ret = decode_AM(ipc, pc+1, code & 0x40, opsize1, opcodes, stream); stream << ", "; - ret += decode_AM(ipc, pc+1+ret, code & 0x20, opsize2, stream); + ret += decode_AM(ipc, pc+1+ret, code & 0x20, opsize2, opcodes, stream); return ret+2; } -static int decode_F1F2(const char *opnm, int opsize1, int opsize2, unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::decode_F1F2(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { - if(readop(pc) & 0x80) - return decode_F2(opnm, opsize1, opsize2, ipc, pc, stream); + if(opcodes.r8(pc) & 0x80) + return decode_F2(opnm, opsize1, opsize2, ipc, pc, opcodes, stream); else - return decode_F1(opnm, opsize1, opsize2, ipc, pc, stream); + return decode_F1(opnm, opsize1, opsize2, ipc, pc, opcodes, stream); } -static int decode_F3(const char *opnm, int opsize1, int opsize2, unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::decode_F3(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { util::stream_format(stream, "%-8s", opnm); - return decode_AM(ipc, pc, readop(pc-1) & 1, opsize1, stream) + 1; + return decode_AM(ipc, pc, opcodes.r8(pc-1) & 1, opsize1, opcodes, stream) + 1; } -static int decode_F4a(const char *opnm, int opsize1, int opsize2, unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::decode_F4a(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { - util::stream_format(stream, "%-8s%X", opnm, ipc+read8(pc)); + util::stream_format(stream, "%-8s%X", opnm, ipc+opcodes.r8(pc)); return 2; } -static int decode_F4b(const char *opnm, int opsize1, int opsize2, unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::decode_F4b(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { - util::stream_format(stream, "%-8s%X", opnm, ipc+read16(pc)); + util::stream_format(stream, "%-8s%X", opnm, ipc+opcodes.r16(pc)); return 3; } -static int decode_F5(const char *opnm, int opsize1, int opsize2, unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::decode_F5(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { stream << opnm; return 1; } -static int decode_F6(const char *opnm, int opsize1, int opsize2, unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::decode_F6(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { - util::stream_format(stream, "%-8s%s, %X[PC]", opnm, v60_reg_names[readop(pc) & 0x1f], ipc+read16(pc+1)); + util::stream_format(stream, "%-8s%s, %X[PC]", opnm, v60_reg_names[opcodes.r8(pc) & 0x1f], ipc+opcodes.r16(pc+1)); return 4; } -static int decode_F7a(const char *opnm, int opsize1, int opsize2, unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::decode_F7a(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { int ret; - unsigned char code = readop(pc); + unsigned char code = opcodes.r8(pc); unsigned char code2; util::stream_format(stream, "%-8s", opnm); - ret = decode_AM(ipc, pc+1, code & 0x40, opsize1, stream); + ret = decode_AM(ipc, pc+1, code & 0x40, opsize1, opcodes, stream); stream << ", "; - code2 = readop(pc+1+ret); + code2 = opcodes.r8(pc+1+ret); if(code2 & 0x80) out_AM_Register(code2 & 0x1f, stream); else out_AM_Immediate(code2, 1, stream); stream << ", "; - ret += decode_AM(ipc, pc+2+ret, code & 0x20, opsize2, stream); + ret += decode_AM(ipc, pc+2+ret, code & 0x20, opsize2, opcodes, stream); stream << ", "; - code2 = readop(pc+2+ret); + code2 = opcodes.r8(pc+2+ret); if(code2 & 0x80) out_AM_Register(code2 & 0x1f, stream); else @@ -527,42 +506,42 @@ static int decode_F7a(const char *opnm, int opsize1, int opsize2, unsigned ipc, return ret+4; } -static int decode_F7b(const char *opnm, int opsize1, int opsize2, unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::decode_F7b(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { int ret; - unsigned char code = readop(pc); + unsigned char code = opcodes.r8(pc); unsigned char code2; util::stream_format(stream, "%-8s", opnm); - ret = decode_AM(ipc, pc+1, code & 0x40, opsize1, stream); + ret = decode_AM(ipc, pc+1, code & 0x40, opsize1, opcodes, stream); stream << ", "; - code2 = readop(pc+1+ret); + code2 = opcodes.r8(pc+1+ret); if(code2 & 0x80) out_AM_Register(code2 & 0x1f, stream); else out_AM_Immediate(code2, 1, stream); stream << ", "; - ret += decode_AM(ipc, pc+2+ret, code & 0x20, opsize2, stream); + ret += decode_AM(ipc, pc+2+ret, code & 0x20, opsize2, opcodes, stream); return ret+3; } -static int decode_F7c(const char *opnm, int opsize1, int opsize2, unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::decode_F7c(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { int ret; - unsigned char code = readop(pc); + unsigned char code = opcodes.r8(pc); unsigned char code2; util::stream_format(stream, "%-8s", opnm); - ret = decode_AM(ipc, pc+1, code & 0x40, opsize1, stream); + ret = decode_AM(ipc, pc+1, code & 0x40, opsize1, opcodes, stream); stream << ", "; - ret += decode_AM(ipc, pc+1+ret, code & 0x20, opsize2, stream); + ret += decode_AM(ipc, pc+1+ret, code & 0x20, opsize2, opcodes, stream); stream << ", "; - code2 = readop(pc+1+ret); + code2 = opcodes.r8(pc+1+ret); if(code2 & 0x80) out_AM_Register(code2 & 0x1f, stream); else @@ -571,70 +550,70 @@ static int decode_F7c(const char *opnm, int opsize1, int opsize2, unsigned ipc, return ret+3; } -static int dopUNHANDLED(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dopUNHANDLED(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { - util::stream_format(stream, "$%02X", readop(pc)); + util::stream_format(stream, "$%02X", opcodes.r8(pc)); return 1; } -static int dop58UNHANDLED(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dop58UNHANDLED(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { util::stream_format(stream, "$58"); return 1; } -static int dop59UNHANDLED(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dop59UNHANDLED(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { util::stream_format(stream, "$59"); return 1; } -static int dop5AUNHANDLED(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dop5AUNHANDLED(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { util::stream_format(stream, "$5A"); return 1; } -static int dop5BUNHANDLED(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dop5BUNHANDLED(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { util::stream_format(stream, "$5B"); return 1; } -static int dop5CUNHANDLED(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dop5CUNHANDLED(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { util::stream_format(stream, "$5C"); return 1; } -static int dop5DUNHANDLED(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dop5DUNHANDLED(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { util::stream_format(stream, "$5D"); return 1; } -static int dop5EUNHANDLED(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dop5EUNHANDLED(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { util::stream_format(stream, "$5E"); return 1; } -static int dop5FUNHANDLED(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dop5FUNHANDLED(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { util::stream_format(stream, "$5F"); return 1; } #define DEFINE_EASY_OPCODE(name, opnm, ftype, opsize1, opsize2) \ - static int dop ## name(unsigned ipc, unsigned pc, std::ostream &stream) \ + u32 v60_disassembler::dop ## name(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) \ { \ - return decode_ ## ftype(opnm, opsize1, opsize2, ipc, pc, stream); \ + return decode_ ## ftype(opnm, opsize1, opsize2, ipc, pc, opcodes, stream); \ } #define DEFINE_EASY_OPCODE_EX(name, opnm, ftype, opsize1, opsize2, flags) \ - static int dop ## name(unsigned ipc, unsigned pc, std::ostream &stream) \ + u32 v60_disassembler::dop ## name(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) \ { \ - return decode_ ## ftype(opnm, opsize1, opsize2, ipc, pc, stream) | (flags); \ + return decode_ ## ftype(opnm, opsize1, opsize2, ipc, pc, opcodes, stream) | (flags); \ } #define DEFINE_TRIPLE_OPCODE(name, string, ftype) \ @@ -693,8 +672,8 @@ DEFINE_EASY_OPCODE(BR8, "br", F4a, 0, 0) DEFINE_EASY_OPCODE(BR16, "br", F4b, 0, 0) DEFINE_EASY_OPCODE(BRK, "brk", F5, 0, 0) DEFINE_EASY_OPCODE(BRKV, "brkv", F5, 0, 0) -DEFINE_EASY_OPCODE_EX(BSR, "bsr", F4b, 0, 0, DASMFLAG_STEP_OVER) -DEFINE_EASY_OPCODE_EX(CALL, "call", F1F2, 0, 2, DASMFLAG_STEP_OVER) +DEFINE_EASY_OPCODE_EX(BSR, "bsr", F4b, 0, 0, STEP_OVER) +DEFINE_EASY_OPCODE_EX(CALL, "call", F1F2, 0, 2, STEP_OVER) DEFINE_EASY_OPCODE(CAXI, "caxi", F1, 2, 2) DEFINE_EASY_OPCODE(CHKAR, "chkar", F1F2, 0, 0) // ? DEFINE_EASY_OPCODE(CHKAW, "chkaw", F1F2, 0, 0) // ? @@ -719,21 +698,21 @@ DEFINE_EASY_OPCODE(CVTSW, "cvt.sw", F2, 0, 2) DEFINE_EASY_OPCODE(CVTLW, "cvt.lw", F2, 1, 2) DEFINE_EASY_OPCODE(CVTDPZ, "cvtd.pz", F7c, 0, 1) DEFINE_EASY_OPCODE(CVTDZP, "cvtd.zp", F7c, 1, 0) -DEFINE_EASY_OPCODE_EX(DBGT, "dbgt", F6, 0, 0, DASMFLAG_STEP_OVER) -DEFINE_EASY_OPCODE_EX(DBGE, "dbge", F6, 0, 0, DASMFLAG_STEP_OVER) -DEFINE_EASY_OPCODE_EX(DBLT, "dbgt", F6, 0, 0, DASMFLAG_STEP_OVER) -DEFINE_EASY_OPCODE_EX(DBLE, "dbge", F6, 0, 0, DASMFLAG_STEP_OVER) -DEFINE_EASY_OPCODE_EX(DBH, "dbh", F6, 0, 0, DASMFLAG_STEP_OVER) -DEFINE_EASY_OPCODE_EX(DBNL, "dbnl", F6, 0, 0, DASMFLAG_STEP_OVER) -DEFINE_EASY_OPCODE_EX(DBL, "dbl", F6, 0, 0, DASMFLAG_STEP_OVER) -DEFINE_EASY_OPCODE_EX(DBNH, "dbnh", F6, 0, 0, DASMFLAG_STEP_OVER) -DEFINE_EASY_OPCODE_EX(DBE, "dbe", F6, 0, 0, DASMFLAG_STEP_OVER) -DEFINE_EASY_OPCODE_EX(DBNE, "dbne", F6, 0, 0, DASMFLAG_STEP_OVER) -DEFINE_EASY_OPCODE_EX(DBV, "dbe", F6, 0, 0, DASMFLAG_STEP_OVER) -DEFINE_EASY_OPCODE_EX(DBNV, "dbne", F6, 0, 0, DASMFLAG_STEP_OVER) -DEFINE_EASY_OPCODE_EX(DBN, "dbn", F6, 0, 0, DASMFLAG_STEP_OVER) -DEFINE_EASY_OPCODE_EX(DBP, "dbp", F6, 0, 0, DASMFLAG_STEP_OVER) -DEFINE_EASY_OPCODE_EX(DBR, "dbr", F6, 0, 0, DASMFLAG_STEP_OVER) +DEFINE_EASY_OPCODE_EX(DBGT, "dbgt", F6, 0, 0, STEP_OVER) +DEFINE_EASY_OPCODE_EX(DBGE, "dbge", F6, 0, 0, STEP_OVER) +DEFINE_EASY_OPCODE_EX(DBLT, "dbgt", F6, 0, 0, STEP_OVER) +DEFINE_EASY_OPCODE_EX(DBLE, "dbge", F6, 0, 0, STEP_OVER) +DEFINE_EASY_OPCODE_EX(DBH, "dbh", F6, 0, 0, STEP_OVER) +DEFINE_EASY_OPCODE_EX(DBNL, "dbnl", F6, 0, 0, STEP_OVER) +DEFINE_EASY_OPCODE_EX(DBL, "dbl", F6, 0, 0, STEP_OVER) +DEFINE_EASY_OPCODE_EX(DBNH, "dbnh", F6, 0, 0, STEP_OVER) +DEFINE_EASY_OPCODE_EX(DBE, "dbe", F6, 0, 0, STEP_OVER) +DEFINE_EASY_OPCODE_EX(DBNE, "dbne", F6, 0, 0, STEP_OVER) +DEFINE_EASY_OPCODE_EX(DBV, "dbe", F6, 0, 0, STEP_OVER) +DEFINE_EASY_OPCODE_EX(DBNV, "dbne", F6, 0, 0, STEP_OVER) +DEFINE_EASY_OPCODE_EX(DBN, "dbn", F6, 0, 0, STEP_OVER) +DEFINE_EASY_OPCODE_EX(DBP, "dbp", F6, 0, 0, STEP_OVER) +DEFINE_EASY_OPCODE_EX(DBR, "dbr", F6, 0, 0, STEP_OVER) DEFINE_TRIPLE_OPCODE(DEC, "dec", F3) DEFINE_EASY_OPCODE(DISPOSE, "dispose", F5, 0, 0) DEFINE_TRIPLE_OPCODE(DIV, "div", F1F2) @@ -754,7 +733,7 @@ DEFINE_TRIPLE_OPCODE(INC, "inc", F3) DEFINE_EASY_OPCODE(INSBFL, "insbfl", F7c, 2, 0x82) DEFINE_EASY_OPCODE(INSBFR, "insbfr", F7c, 2, 0x82) DEFINE_EASY_OPCODE(JMP, "jmp", F3, 0, 0) -DEFINE_EASY_OPCODE_EX(JSR, "jsr", F3, 0, 0, DASMFLAG_STEP_OVER) +DEFINE_EASY_OPCODE_EX(JSR, "jsr", F3, 0, 0, STEP_OVER) DEFINE_EASY_OPCODE(LDPR, "ldpr", F1F2, 2, 2) DEFINE_EASY_OPCODE(LDTASK, "ldtask", F1F2, 2, 2) DEFINE_TRIPLE_OPCODE(MOV, "mov", F1F2) @@ -804,16 +783,16 @@ DEFINE_EASY_OPCODE(PUSH, "push", F3, 2, 0) DEFINE_EASY_OPCODE(PUSHM, "pushm", F3, 2, 0) DEFINE_TRIPLE_OPCODE(REM, "rem", F1F2) DEFINE_TRIPLE_OPCODE(REMU, "remu", F1F2) -DEFINE_EASY_OPCODE_EX(RET, "ret", F3, 2, 0, DASMFLAG_STEP_OUT) -DEFINE_EASY_OPCODE_EX(RETIU, "retiu", F3, 1, 0, DASMFLAG_STEP_OUT) -DEFINE_EASY_OPCODE_EX(RETIS, "retis", F3, 1, 0, DASMFLAG_STEP_OUT) +DEFINE_EASY_OPCODE_EX(RET, "ret", F3, 2, 0, STEP_OUT) +DEFINE_EASY_OPCODE_EX(RETIU, "retiu", F3, 1, 0, STEP_OUT) +DEFINE_EASY_OPCODE_EX(RETIS, "retis", F3, 1, 0, STEP_OUT) DEFINE_EASY_OPCODE(ROTB, "rot.b", F1F2, 0, 0) DEFINE_EASY_OPCODE(ROTH, "rot.h", F1F2, 0, 1) DEFINE_EASY_OPCODE(ROTW, "rot.w", F1F2, 0, 2) DEFINE_EASY_OPCODE(ROTCB, "rotc.b", F1F2, 0, 0) DEFINE_EASY_OPCODE(ROTCH, "rotc.h", F1F2, 0, 1) DEFINE_EASY_OPCODE(ROTCW, "rotc.w", F1F2, 0, 2) -DEFINE_EASY_OPCODE_EX(RSR, "rsr", F5, 0, 0, DASMFLAG_STEP_OUT) +DEFINE_EASY_OPCODE_EX(RSR, "rsr", F5, 0, 0, STEP_OUT) DEFINE_EASY_OPCODE(RVBIT, "rvbit", F1F2, 0, 0) DEFINE_EASY_OPCODE(RVBYT, "rvbyt", F1F2, 2, 2) DEFINE_EASY_OPCODE(SCH0BSU, "sch0bsu", F7b, 0x80, 2) @@ -849,7 +828,7 @@ DEFINE_EASY_OPCODE(TASI, "tasi", F3, 0, 0) DEFINE_EASY_OPCODE(TB, "tb", F6, 0, 0) DEFINE_TRIPLE_OPCODE(TEST, "test", F3) DEFINE_EASY_OPCODE(TEST1, "test1", F1F2, 2, 2) -DEFINE_EASY_OPCODE_EX(TRAP, "trap", F3, 0, 0, DASMFLAG_STEP_OVER) +DEFINE_EASY_OPCODE_EX(TRAP, "trap", F3, 0, 0, STEP_OVER) DEFINE_EASY_OPCODE(TRAPFL, "trapfl", F5, 0, 0) DEFINE_EASY_OPCODE(UPDATE, "update", F1F2, 0, 3) // ? DEFINE_EASY_OPCODE(UPDPSWH, "updpsw.h", F1F2, 2, 2) @@ -862,638 +841,634 @@ DEFINE_EASY_OPCODE(XORBSD, "xorbsd", F7b, 0x80, 0x80) DEFINE_EASY_OPCODE(XORNBSU, "xornbsu", F7b, 0x80, 0x80) DEFINE_EASY_OPCODE(XORNBSD, "xornbsd", F7b, 0x80, 0x80) -static int (*const dasm_optable_58[32])(unsigned ipc, unsigned pc, std::ostream &stream) = -{ - /* 0x00 */ dopCMPCB, - /* 0x01 */ dopCMPCFB, - /* 0x02 */ dopCMPCSB, - /* 0x03 */ dop58UNHANDLED, - /* 0x04 */ dop58UNHANDLED, - /* 0x05 */ dop58UNHANDLED, - /* 0x06 */ dop58UNHANDLED, - /* 0x07 */ dop58UNHANDLED, - /* 0x08 */ dopMOVCUB, - /* 0x09 */ dopMOVCDB, - /* 0x0A */ dopMOVCFUB, - /* 0x0B */ dopMOVCFDB, - /* 0x0C */ dopMOVCSB, - /* 0x0D */ dop58UNHANDLED, - /* 0x0E */ dop58UNHANDLED, - /* 0x0F */ dop58UNHANDLED, - /* 0x10 */ dop58UNHANDLED, - /* 0x11 */ dop58UNHANDLED, - /* 0x12 */ dop58UNHANDLED, - /* 0x13 */ dop58UNHANDLED, - /* 0x14 */ dop58UNHANDLED, - /* 0x15 */ dop58UNHANDLED, - /* 0x16 */ dop58UNHANDLED, - /* 0x17 */ dop58UNHANDLED, - /* 0x18 */ dopSCHCUB, - /* 0x19 */ dopSCHCDB, - /* 0x1A */ dopSKPCUB, - /* 0x1B */ dopSKPCDB, - /* 0x1C */ dop58UNHANDLED, - /* 0x1D */ dop58UNHANDLED, - /* 0x1E */ dop58UNHANDLED, - /* 0x1F */ dop58UNHANDLED +u32 (v60_disassembler::*const v60_disassembler::dasm_optable_58[32])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) = +{ + /* 0x00 */ &v60_disassembler::dopCMPCB, + /* 0x01 */ &v60_disassembler::dopCMPCFB, + /* 0x02 */ &v60_disassembler::dopCMPCSB, + /* 0x03 */ &v60_disassembler::dop58UNHANDLED, + /* 0x04 */ &v60_disassembler::dop58UNHANDLED, + /* 0x05 */ &v60_disassembler::dop58UNHANDLED, + /* 0x06 */ &v60_disassembler::dop58UNHANDLED, + /* 0x07 */ &v60_disassembler::dop58UNHANDLED, + /* 0x08 */ &v60_disassembler::dopMOVCUB, + /* 0x09 */ &v60_disassembler::dopMOVCDB, + /* 0x0A */ &v60_disassembler::dopMOVCFUB, + /* 0x0B */ &v60_disassembler::dopMOVCFDB, + /* 0x0C */ &v60_disassembler::dopMOVCSB, + /* 0x0D */ &v60_disassembler::dop58UNHANDLED, + /* 0x0E */ &v60_disassembler::dop58UNHANDLED, + /* 0x0F */ &v60_disassembler::dop58UNHANDLED, + /* 0x10 */ &v60_disassembler::dop58UNHANDLED, + /* 0x11 */ &v60_disassembler::dop58UNHANDLED, + /* 0x12 */ &v60_disassembler::dop58UNHANDLED, + /* 0x13 */ &v60_disassembler::dop58UNHANDLED, + /* 0x14 */ &v60_disassembler::dop58UNHANDLED, + /* 0x15 */ &v60_disassembler::dop58UNHANDLED, + /* 0x16 */ &v60_disassembler::dop58UNHANDLED, + /* 0x17 */ &v60_disassembler::dop58UNHANDLED, + /* 0x18 */ &v60_disassembler::dopSCHCUB, + /* 0x19 */ &v60_disassembler::dopSCHCDB, + /* 0x1A */ &v60_disassembler::dopSKPCUB, + /* 0x1B */ &v60_disassembler::dopSKPCDB, + /* 0x1C */ &v60_disassembler::dop58UNHANDLED, + /* 0x1D */ &v60_disassembler::dop58UNHANDLED, + /* 0x1E */ &v60_disassembler::dop58UNHANDLED, + /* 0x1F */ &v60_disassembler::dop58UNHANDLED }; -static int (*const dasm_optable_59[32])(unsigned ipc, unsigned pc, std::ostream &stream) = -{ - /* 0x00 */ dopADDDC, - /* 0x01 */ dopSUBDC, - /* 0x02 */ dopSUBRDC, - /* 0x03 */ dop59UNHANDLED, - /* 0x04 */ dop59UNHANDLED, - /* 0x05 */ dop59UNHANDLED, - /* 0x06 */ dop59UNHANDLED, - /* 0x07 */ dop59UNHANDLED, - /* 0x08 */ dop59UNHANDLED, - /* 0x09 */ dop59UNHANDLED, - /* 0x0A */ dop59UNHANDLED, - /* 0x0B */ dop59UNHANDLED, - /* 0x0C */ dop59UNHANDLED, - /* 0x0D */ dop59UNHANDLED, - /* 0x0E */ dop59UNHANDLED, - /* 0x0F */ dop59UNHANDLED, - /* 0x10 */ dopCVTDPZ, - /* 0x11 */ dop59UNHANDLED, - /* 0x12 */ dop59UNHANDLED, - /* 0x13 */ dop59UNHANDLED, - /* 0x14 */ dop59UNHANDLED, - /* 0x15 */ dop59UNHANDLED, - /* 0x16 */ dop59UNHANDLED, - /* 0x17 */ dop59UNHANDLED, - /* 0x18 */ dopCVTDZP, - /* 0x19 */ dop59UNHANDLED, - /* 0x1A */ dop59UNHANDLED, - /* 0x1B */ dop59UNHANDLED, - /* 0x1C */ dop59UNHANDLED, - /* 0x1D */ dop59UNHANDLED, - /* 0x1E */ dop59UNHANDLED, - /* 0x1F */ dop59UNHANDLED +u32 (v60_disassembler::*const v60_disassembler::dasm_optable_59[32])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) = +{ + /* 0x00 */ &v60_disassembler::dopADDDC, + /* 0x01 */ &v60_disassembler::dopSUBDC, + /* 0x02 */ &v60_disassembler::dopSUBRDC, + /* 0x03 */ &v60_disassembler::dop59UNHANDLED, + /* 0x04 */ &v60_disassembler::dop59UNHANDLED, + /* 0x05 */ &v60_disassembler::dop59UNHANDLED, + /* 0x06 */ &v60_disassembler::dop59UNHANDLED, + /* 0x07 */ &v60_disassembler::dop59UNHANDLED, + /* 0x08 */ &v60_disassembler::dop59UNHANDLED, + /* 0x09 */ &v60_disassembler::dop59UNHANDLED, + /* 0x0A */ &v60_disassembler::dop59UNHANDLED, + /* 0x0B */ &v60_disassembler::dop59UNHANDLED, + /* 0x0C */ &v60_disassembler::dop59UNHANDLED, + /* 0x0D */ &v60_disassembler::dop59UNHANDLED, + /* 0x0E */ &v60_disassembler::dop59UNHANDLED, + /* 0x0F */ &v60_disassembler::dop59UNHANDLED, + /* 0x10 */ &v60_disassembler::dopCVTDPZ, + /* 0x11 */ &v60_disassembler::dop59UNHANDLED, + /* 0x12 */ &v60_disassembler::dop59UNHANDLED, + /* 0x13 */ &v60_disassembler::dop59UNHANDLED, + /* 0x14 */ &v60_disassembler::dop59UNHANDLED, + /* 0x15 */ &v60_disassembler::dop59UNHANDLED, + /* 0x16 */ &v60_disassembler::dop59UNHANDLED, + /* 0x17 */ &v60_disassembler::dop59UNHANDLED, + /* 0x18 */ &v60_disassembler::dopCVTDZP, + /* 0x19 */ &v60_disassembler::dop59UNHANDLED, + /* 0x1A */ &v60_disassembler::dop59UNHANDLED, + /* 0x1B */ &v60_disassembler::dop59UNHANDLED, + /* 0x1C */ &v60_disassembler::dop59UNHANDLED, + /* 0x1D */ &v60_disassembler::dop59UNHANDLED, + /* 0x1E */ &v60_disassembler::dop59UNHANDLED, + /* 0x1F */ &v60_disassembler::dop59UNHANDLED }; -static int (*const dasm_optable_5A[32])(unsigned ipc, unsigned pc, std::ostream &stream) = -{ - /* 0x00 */ dopCMPCH, - /* 0x01 */ dopCMPCFH, - /* 0x02 */ dopCMPCSH, - /* 0x03 */ dop5AUNHANDLED, - /* 0x04 */ dop5AUNHANDLED, - /* 0x05 */ dop5AUNHANDLED, - /* 0x06 */ dop5AUNHANDLED, - /* 0x07 */ dop5AUNHANDLED, - /* 0x08 */ dopMOVCUH, - /* 0x09 */ dopMOVCDH, - /* 0x0A */ dopMOVCFUH, - /* 0x0B */ dopMOVCFDH, - /* 0x0C */ dopMOVCSH, - /* 0x0D */ dop5AUNHANDLED, - /* 0x0E */ dop5AUNHANDLED, - /* 0x0F */ dop5AUNHANDLED, - /* 0x10 */ dop5AUNHANDLED, - /* 0x11 */ dop5AUNHANDLED, - /* 0x12 */ dop5AUNHANDLED, - /* 0x13 */ dop5AUNHANDLED, - /* 0x14 */ dop5AUNHANDLED, - /* 0x15 */ dop5AUNHANDLED, - /* 0x16 */ dop5AUNHANDLED, - /* 0x17 */ dop5AUNHANDLED, - /* 0x18 */ dopSCHCUH, - /* 0x19 */ dopSCHCDH, - /* 0x1A */ dopSKPCUH, - /* 0x1B */ dopSKPCDH, - /* 0x1C */ dop5AUNHANDLED, - /* 0x1D */ dop5AUNHANDLED, - /* 0x1E */ dop5AUNHANDLED, - /* 0x1F */ dop5AUNHANDLED +u32 (v60_disassembler::*const v60_disassembler::dasm_optable_5A[32])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) = +{ + /* 0x00 */ &v60_disassembler::dopCMPCH, + /* 0x01 */ &v60_disassembler::dopCMPCFH, + /* 0x02 */ &v60_disassembler::dopCMPCSH, + /* 0x03 */ &v60_disassembler::dop5AUNHANDLED, + /* 0x04 */ &v60_disassembler::dop5AUNHANDLED, + /* 0x05 */ &v60_disassembler::dop5AUNHANDLED, + /* 0x06 */ &v60_disassembler::dop5AUNHANDLED, + /* 0x07 */ &v60_disassembler::dop5AUNHANDLED, + /* 0x08 */ &v60_disassembler::dopMOVCUH, + /* 0x09 */ &v60_disassembler::dopMOVCDH, + /* 0x0A */ &v60_disassembler::dopMOVCFUH, + /* 0x0B */ &v60_disassembler::dopMOVCFDH, + /* 0x0C */ &v60_disassembler::dopMOVCSH, + /* 0x0D */ &v60_disassembler::dop5AUNHANDLED, + /* 0x0E */ &v60_disassembler::dop5AUNHANDLED, + /* 0x0F */ &v60_disassembler::dop5AUNHANDLED, + /* 0x10 */ &v60_disassembler::dop5AUNHANDLED, + /* 0x11 */ &v60_disassembler::dop5AUNHANDLED, + /* 0x12 */ &v60_disassembler::dop5AUNHANDLED, + /* 0x13 */ &v60_disassembler::dop5AUNHANDLED, + /* 0x14 */ &v60_disassembler::dop5AUNHANDLED, + /* 0x15 */ &v60_disassembler::dop5AUNHANDLED, + /* 0x16 */ &v60_disassembler::dop5AUNHANDLED, + /* 0x17 */ &v60_disassembler::dop5AUNHANDLED, + /* 0x18 */ &v60_disassembler::dopSCHCUH, + /* 0x19 */ &v60_disassembler::dopSCHCDH, + /* 0x1A */ &v60_disassembler::dopSKPCUH, + /* 0x1B */ &v60_disassembler::dopSKPCDH, + /* 0x1C */ &v60_disassembler::dop5AUNHANDLED, + /* 0x1D */ &v60_disassembler::dop5AUNHANDLED, + /* 0x1E */ &v60_disassembler::dop5AUNHANDLED, + /* 0x1F */ &v60_disassembler::dop5AUNHANDLED }; -static int (*const dasm_optable_5B[32])(unsigned ipc, unsigned pc, std::ostream &stream) = -{ - /* 0x00 */ dopSCH0BSU, - /* 0x01 */ dopSCH0BSD, - /* 0x02 */ dopSCH1BSU, - /* 0x03 */ dopSCH1BSD, - /* 0x04 */ dop5BUNHANDLED, - /* 0x05 */ dop5BUNHANDLED, - /* 0x06 */ dop5BUNHANDLED, - /* 0x07 */ dop5BUNHANDLED, - /* 0x08 */ dopMOVBSU, - /* 0x09 */ dopMOVBSD, - /* 0x0A */ dopNOTBSU, - /* 0x0B */ dopNOTBSD, - /* 0x0C */ dop5BUNHANDLED, - /* 0x0D */ dop5BUNHANDLED, - /* 0x0E */ dop5BUNHANDLED, - /* 0x0F */ dop5BUNHANDLED, - /* 0x10 */ dopANDBSU, - /* 0x11 */ dopANDBSD, - /* 0x12 */ dopANDNBSU, - /* 0x13 */ dopANDNBSD, - /* 0x14 */ dopORBSU, - /* 0x15 */ dopORBSD, - /* 0x16 */ dopORNBSU, - /* 0x17 */ dopORNBSD, - /* 0x18 */ dopXORBSU, - /* 0x19 */ dopXORBSD, - /* 0x1A */ dopXORNBSU, - /* 0x1B */ dopXORNBSD, - /* 0x1C */ dop5BUNHANDLED, - /* 0x1D */ dop5BUNHANDLED, - /* 0x1E */ dop5BUNHANDLED, - /* 0x1F */ dop5BUNHANDLED +u32 (v60_disassembler::*const v60_disassembler::dasm_optable_5B[32])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) = +{ + /* 0x00 */ &v60_disassembler::dopSCH0BSU, + /* 0x01 */ &v60_disassembler::dopSCH0BSD, + /* 0x02 */ &v60_disassembler::dopSCH1BSU, + /* 0x03 */ &v60_disassembler::dopSCH1BSD, + /* 0x04 */ &v60_disassembler::dop5BUNHANDLED, + /* 0x05 */ &v60_disassembler::dop5BUNHANDLED, + /* 0x06 */ &v60_disassembler::dop5BUNHANDLED, + /* 0x07 */ &v60_disassembler::dop5BUNHANDLED, + /* 0x08 */ &v60_disassembler::dopMOVBSU, + /* 0x09 */ &v60_disassembler::dopMOVBSD, + /* 0x0A */ &v60_disassembler::dopNOTBSU, + /* 0x0B */ &v60_disassembler::dopNOTBSD, + /* 0x0C */ &v60_disassembler::dop5BUNHANDLED, + /* 0x0D */ &v60_disassembler::dop5BUNHANDLED, + /* 0x0E */ &v60_disassembler::dop5BUNHANDLED, + /* 0x0F */ &v60_disassembler::dop5BUNHANDLED, + /* 0x10 */ &v60_disassembler::dopANDBSU, + /* 0x11 */ &v60_disassembler::dopANDBSD, + /* 0x12 */ &v60_disassembler::dopANDNBSU, + /* 0x13 */ &v60_disassembler::dopANDNBSD, + /* 0x14 */ &v60_disassembler::dopORBSU, + /* 0x15 */ &v60_disassembler::dopORBSD, + /* 0x16 */ &v60_disassembler::dopORNBSU, + /* 0x17 */ &v60_disassembler::dopORNBSD, + /* 0x18 */ &v60_disassembler::dopXORBSU, + /* 0x19 */ &v60_disassembler::dopXORBSD, + /* 0x1A */ &v60_disassembler::dopXORNBSU, + /* 0x1B */ &v60_disassembler::dopXORNBSD, + /* 0x1C */ &v60_disassembler::dop5BUNHANDLED, + /* 0x1D */ &v60_disassembler::dop5BUNHANDLED, + /* 0x1E */ &v60_disassembler::dop5BUNHANDLED, + /* 0x1F */ &v60_disassembler::dop5BUNHANDLED }; -static int (*const dasm_optable_5C[32])(unsigned ipc, unsigned pc, std::ostream &stream) = -{ - /* 0x00 */ dopCMPFS, - /* 0x01 */ dop5CUNHANDLED, - /* 0x02 */ dop5CUNHANDLED, - /* 0x03 */ dop5CUNHANDLED, - /* 0x04 */ dop5CUNHANDLED, - /* 0x05 */ dop5CUNHANDLED, - /* 0x06 */ dop5CUNHANDLED, - /* 0x07 */ dop5CUNHANDLED, - /* 0x08 */ dopMOVFS, - /* 0x09 */ dopNEGFS, - /* 0x0A */ dopABSFS, - /* 0x0B */ dop5CUNHANDLED, - /* 0x0C */ dop5CUNHANDLED, - /* 0x0D */ dop5CUNHANDLED, - /* 0x0E */ dop5CUNHANDLED, - /* 0x0F */ dop5CUNHANDLED, - /* 0x10 */ dopSCLFS, - /* 0x11 */ dop5CUNHANDLED, - /* 0x12 */ dop5CUNHANDLED, - /* 0x13 */ dop5CUNHANDLED, - /* 0x14 */ dop5CUNHANDLED, - /* 0x15 */ dop5CUNHANDLED, - /* 0x16 */ dop5CUNHANDLED, - /* 0x17 */ dop5CUNHANDLED, - /* 0x18 */ dopADDFS, - /* 0x19 */ dopSUBFS, - /* 0x1A */ dopMULFS, - /* 0x1B */ dopDIVFS, - /* 0x1C */ dop5CUNHANDLED, - /* 0x1D */ dop5CUNHANDLED, - /* 0x1E */ dop5CUNHANDLED, - /* 0x1F */ dop5CUNHANDLED +u32 (v60_disassembler::*const v60_disassembler::dasm_optable_5C[32])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) = +{ + /* 0x00 */ &v60_disassembler::dopCMPFS, + /* 0x01 */ &v60_disassembler::dop5CUNHANDLED, + /* 0x02 */ &v60_disassembler::dop5CUNHANDLED, + /* 0x03 */ &v60_disassembler::dop5CUNHANDLED, + /* 0x04 */ &v60_disassembler::dop5CUNHANDLED, + /* 0x05 */ &v60_disassembler::dop5CUNHANDLED, + /* 0x06 */ &v60_disassembler::dop5CUNHANDLED, + /* 0x07 */ &v60_disassembler::dop5CUNHANDLED, + /* 0x08 */ &v60_disassembler::dopMOVFS, + /* 0x09 */ &v60_disassembler::dopNEGFS, + /* 0x0A */ &v60_disassembler::dopABSFS, + /* 0x0B */ &v60_disassembler::dop5CUNHANDLED, + /* 0x0C */ &v60_disassembler::dop5CUNHANDLED, + /* 0x0D */ &v60_disassembler::dop5CUNHANDLED, + /* 0x0E */ &v60_disassembler::dop5CUNHANDLED, + /* 0x0F */ &v60_disassembler::dop5CUNHANDLED, + /* 0x10 */ &v60_disassembler::dopSCLFS, + /* 0x11 */ &v60_disassembler::dop5CUNHANDLED, + /* 0x12 */ &v60_disassembler::dop5CUNHANDLED, + /* 0x13 */ &v60_disassembler::dop5CUNHANDLED, + /* 0x14 */ &v60_disassembler::dop5CUNHANDLED, + /* 0x15 */ &v60_disassembler::dop5CUNHANDLED, + /* 0x16 */ &v60_disassembler::dop5CUNHANDLED, + /* 0x17 */ &v60_disassembler::dop5CUNHANDLED, + /* 0x18 */ &v60_disassembler::dopADDFS, + /* 0x19 */ &v60_disassembler::dopSUBFS, + /* 0x1A */ &v60_disassembler::dopMULFS, + /* 0x1B */ &v60_disassembler::dopDIVFS, + /* 0x1C */ &v60_disassembler::dop5CUNHANDLED, + /* 0x1D */ &v60_disassembler::dop5CUNHANDLED, + /* 0x1E */ &v60_disassembler::dop5CUNHANDLED, + /* 0x1F */ &v60_disassembler::dop5CUNHANDLED }; -static int (*const dasm_optable_5D[32])(unsigned ipc, unsigned pc, std::ostream &stream) = -{ - /* 0x00 */ dopCMPBFS, - /* 0x01 */ dopCMPBFZ, - /* 0x02 */ dopCMPBFL, - /* 0x03 */ dop5DUNHANDLED, - /* 0x04 */ dop5DUNHANDLED, - /* 0x05 */ dop5DUNHANDLED, - /* 0x06 */ dop5DUNHANDLED, - /* 0x07 */ dop5DUNHANDLED, - /* 0x08 */ dopEXTBFS, - /* 0x09 */ dopEXTBFZ, - /* 0x0A */ dopEXTBFL, - /* 0x0B */ dop5DUNHANDLED, - /* 0x0C */ dop5DUNHANDLED, - /* 0x0D */ dop5DUNHANDLED, - /* 0x0E */ dop5DUNHANDLED, - /* 0x0F */ dop5DUNHANDLED, - /* 0x10 */ dop5DUNHANDLED, - /* 0x11 */ dop5DUNHANDLED, - /* 0x12 */ dop5DUNHANDLED, - /* 0x13 */ dop5DUNHANDLED, - /* 0x14 */ dop5DUNHANDLED, - /* 0x15 */ dop5DUNHANDLED, - /* 0x16 */ dop5DUNHANDLED, - /* 0x17 */ dop5DUNHANDLED, - /* 0x18 */ dopINSBFR, - /* 0x19 */ dopINSBFL, - /* 0x1A */ dop5DUNHANDLED, - /* 0x1B */ dop5DUNHANDLED, - /* 0x1C */ dop5DUNHANDLED, - /* 0x1D */ dop5DUNHANDLED, - /* 0x1E */ dop5DUNHANDLED, - /* 0x1F */ dop5DUNHANDLED +u32 (v60_disassembler::*const v60_disassembler::dasm_optable_5D[32])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) = +{ + /* 0x00 */ &v60_disassembler::dopCMPBFS, + /* 0x01 */ &v60_disassembler::dopCMPBFZ, + /* 0x02 */ &v60_disassembler::dopCMPBFL, + /* 0x03 */ &v60_disassembler::dop5DUNHANDLED, + /* 0x04 */ &v60_disassembler::dop5DUNHANDLED, + /* 0x05 */ &v60_disassembler::dop5DUNHANDLED, + /* 0x06 */ &v60_disassembler::dop5DUNHANDLED, + /* 0x07 */ &v60_disassembler::dop5DUNHANDLED, + /* 0x08 */ &v60_disassembler::dopEXTBFS, + /* 0x09 */ &v60_disassembler::dopEXTBFZ, + /* 0x0A */ &v60_disassembler::dopEXTBFL, + /* 0x0B */ &v60_disassembler::dop5DUNHANDLED, + /* 0x0C */ &v60_disassembler::dop5DUNHANDLED, + /* 0x0D */ &v60_disassembler::dop5DUNHANDLED, + /* 0x0E */ &v60_disassembler::dop5DUNHANDLED, + /* 0x0F */ &v60_disassembler::dop5DUNHANDLED, + /* 0x10 */ &v60_disassembler::dop5DUNHANDLED, + /* 0x11 */ &v60_disassembler::dop5DUNHANDLED, + /* 0x12 */ &v60_disassembler::dop5DUNHANDLED, + /* 0x13 */ &v60_disassembler::dop5DUNHANDLED, + /* 0x14 */ &v60_disassembler::dop5DUNHANDLED, + /* 0x15 */ &v60_disassembler::dop5DUNHANDLED, + /* 0x16 */ &v60_disassembler::dop5DUNHANDLED, + /* 0x17 */ &v60_disassembler::dop5DUNHANDLED, + /* 0x18 */ &v60_disassembler::dopINSBFR, + /* 0x19 */ &v60_disassembler::dopINSBFL, + /* 0x1A */ &v60_disassembler::dop5DUNHANDLED, + /* 0x1B */ &v60_disassembler::dop5DUNHANDLED, + /* 0x1C */ &v60_disassembler::dop5DUNHANDLED, + /* 0x1D */ &v60_disassembler::dop5DUNHANDLED, + /* 0x1E */ &v60_disassembler::dop5DUNHANDLED, + /* 0x1F */ &v60_disassembler::dop5DUNHANDLED }; -static int (*const dasm_optable_5E[32])(unsigned ipc, unsigned pc, std::ostream &stream) = -{ - /* 0x00 */ dopCMPFL, - /* 0x01 */ dop5EUNHANDLED, - /* 0x02 */ dop5EUNHANDLED, - /* 0x03 */ dop5EUNHANDLED, - /* 0x04 */ dop5EUNHANDLED, - /* 0x05 */ dop5EUNHANDLED, - /* 0x06 */ dop5EUNHANDLED, - /* 0x07 */ dop5EUNHANDLED, - /* 0x08 */ dopMOVFL, - /* 0x09 */ dopNEGFL, - /* 0x0A */ dopABSFL, - /* 0x0B */ dop5EUNHANDLED, - /* 0x0C */ dop5EUNHANDLED, - /* 0x0D */ dop5EUNHANDLED, - /* 0x0E */ dop5EUNHANDLED, - /* 0x0F */ dop5EUNHANDLED, - /* 0x10 */ dopSCLFL, - /* 0x11 */ dop5EUNHANDLED, - /* 0x12 */ dop5EUNHANDLED, - /* 0x13 */ dop5EUNHANDLED, - /* 0x14 */ dop5EUNHANDLED, - /* 0x15 */ dop5EUNHANDLED, - /* 0x16 */ dop5EUNHANDLED, - /* 0x17 */ dop5EUNHANDLED, - /* 0x18 */ dopADDFL, - /* 0x19 */ dopSUBFL, - /* 0x1A */ dopMULFL, - /* 0x1B */ dopDIVFL, - /* 0x1C */ dop5EUNHANDLED, - /* 0x1D */ dop5EUNHANDLED, - /* 0x1E */ dop5EUNHANDLED, - /* 0x1F */ dop5EUNHANDLED +u32 (v60_disassembler::*const v60_disassembler::dasm_optable_5E[32])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) = +{ + /* 0x00 */ &v60_disassembler::dopCMPFL, + /* 0x01 */ &v60_disassembler::dop5EUNHANDLED, + /* 0x02 */ &v60_disassembler::dop5EUNHANDLED, + /* 0x03 */ &v60_disassembler::dop5EUNHANDLED, + /* 0x04 */ &v60_disassembler::dop5EUNHANDLED, + /* 0x05 */ &v60_disassembler::dop5EUNHANDLED, + /* 0x06 */ &v60_disassembler::dop5EUNHANDLED, + /* 0x07 */ &v60_disassembler::dop5EUNHANDLED, + /* 0x08 */ &v60_disassembler::dopMOVFL, + /* 0x09 */ &v60_disassembler::dopNEGFL, + /* 0x0A */ &v60_disassembler::dopABSFL, + /* 0x0B */ &v60_disassembler::dop5EUNHANDLED, + /* 0x0C */ &v60_disassembler::dop5EUNHANDLED, + /* 0x0D */ &v60_disassembler::dop5EUNHANDLED, + /* 0x0E */ &v60_disassembler::dop5EUNHANDLED, + /* 0x0F */ &v60_disassembler::dop5EUNHANDLED, + /* 0x10 */ &v60_disassembler::dopSCLFL, + /* 0x11 */ &v60_disassembler::dop5EUNHANDLED, + /* 0x12 */ &v60_disassembler::dop5EUNHANDLED, + /* 0x13 */ &v60_disassembler::dop5EUNHANDLED, + /* 0x14 */ &v60_disassembler::dop5EUNHANDLED, + /* 0x15 */ &v60_disassembler::dop5EUNHANDLED, + /* 0x16 */ &v60_disassembler::dop5EUNHANDLED, + /* 0x17 */ &v60_disassembler::dop5EUNHANDLED, + /* 0x18 */ &v60_disassembler::dopADDFL, + /* 0x19 */ &v60_disassembler::dopSUBFL, + /* 0x1A */ &v60_disassembler::dopMULFL, + /* 0x1B */ &v60_disassembler::dopDIVFL, + /* 0x1C */ &v60_disassembler::dop5EUNHANDLED, + /* 0x1D */ &v60_disassembler::dop5EUNHANDLED, + /* 0x1E */ &v60_disassembler::dop5EUNHANDLED, + /* 0x1F */ &v60_disassembler::dop5EUNHANDLED }; -static int (*const dasm_optable_5F[32])(unsigned ipc, unsigned pc, std::ostream &stream) = -{ - /* 0x00 */ dopCVTWS, - /* 0x01 */ dopCVTSW, - /* 0x02 */ dop5FUNHANDLED, - /* 0x03 */ dop5FUNHANDLED, - /* 0x04 */ dop5FUNHANDLED, - /* 0x05 */ dop5FUNHANDLED, - /* 0x06 */ dop5FUNHANDLED, - /* 0x07 */ dop5FUNHANDLED, - /* 0x08 */ dopCVTLS, - /* 0x09 */ dopCVTLW, - /* 0x0A */ dop5FUNHANDLED, - /* 0x0B */ dop5FUNHANDLED, - /* 0x0C */ dop5FUNHANDLED, - /* 0x0D */ dop5FUNHANDLED, - /* 0x0E */ dop5FUNHANDLED, - /* 0x0F */ dop5FUNHANDLED, - /* 0x10 */ dopCVTSL, - /* 0x11 */ dopCVTWL, - /* 0x12 */ dop5FUNHANDLED, - /* 0x13 */ dop5FUNHANDLED, - /* 0x14 */ dop5FUNHANDLED, - /* 0x15 */ dop5FUNHANDLED, - /* 0x16 */ dop5FUNHANDLED, - /* 0x17 */ dop5FUNHANDLED, - /* 0x18 */ dop5FUNHANDLED, - /* 0x19 */ dop5FUNHANDLED, - /* 0x1A */ dop5FUNHANDLED, - /* 0x1B */ dop5FUNHANDLED, - /* 0x1C */ dop5FUNHANDLED, - /* 0x1D */ dop5FUNHANDLED, - /* 0x1E */ dop5FUNHANDLED, - /* 0x1F */ dop5FUNHANDLED +u32 (v60_disassembler::*const v60_disassembler::dasm_optable_5F[32])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) = +{ + /* 0x00 */ &v60_disassembler::dopCVTWS, + /* 0x01 */ &v60_disassembler::dopCVTSW, + /* 0x02 */ &v60_disassembler::dop5FUNHANDLED, + /* 0x03 */ &v60_disassembler::dop5FUNHANDLED, + /* 0x04 */ &v60_disassembler::dop5FUNHANDLED, + /* 0x05 */ &v60_disassembler::dop5FUNHANDLED, + /* 0x06 */ &v60_disassembler::dop5FUNHANDLED, + /* 0x07 */ &v60_disassembler::dop5FUNHANDLED, + /* 0x08 */ &v60_disassembler::dopCVTLS, + /* 0x09 */ &v60_disassembler::dopCVTLW, + /* 0x0A */ &v60_disassembler::dop5FUNHANDLED, + /* 0x0B */ &v60_disassembler::dop5FUNHANDLED, + /* 0x0C */ &v60_disassembler::dop5FUNHANDLED, + /* 0x0D */ &v60_disassembler::dop5FUNHANDLED, + /* 0x0E */ &v60_disassembler::dop5FUNHANDLED, + /* 0x0F */ &v60_disassembler::dop5FUNHANDLED, + /* 0x10 */ &v60_disassembler::dopCVTSL, + /* 0x11 */ &v60_disassembler::dopCVTWL, + /* 0x12 */ &v60_disassembler::dop5FUNHANDLED, + /* 0x13 */ &v60_disassembler::dop5FUNHANDLED, + /* 0x14 */ &v60_disassembler::dop5FUNHANDLED, + /* 0x15 */ &v60_disassembler::dop5FUNHANDLED, + /* 0x16 */ &v60_disassembler::dop5FUNHANDLED, + /* 0x17 */ &v60_disassembler::dop5FUNHANDLED, + /* 0x18 */ &v60_disassembler::dop5FUNHANDLED, + /* 0x19 */ &v60_disassembler::dop5FUNHANDLED, + /* 0x1A */ &v60_disassembler::dop5FUNHANDLED, + /* 0x1B */ &v60_disassembler::dop5FUNHANDLED, + /* 0x1C */ &v60_disassembler::dop5FUNHANDLED, + /* 0x1D */ &v60_disassembler::dop5FUNHANDLED, + /* 0x1E */ &v60_disassembler::dop5FUNHANDLED, + /* 0x1F */ &v60_disassembler::dop5FUNHANDLED }; -static int (*const dasm_optable_C6[8])(unsigned ipc, unsigned pc, std::ostream &stream) = +u32 (v60_disassembler::*const v60_disassembler::dasm_optable_C6[8])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) = { - /* 0x0 */ dopDBV, - /* 0x1 */ dopDBL, - /* 0x2 */ dopDBE, - /* 0x3 */ dopDBNH, - /* 0x4 */ dopDBN, - /* 0x5 */ dopDBR, - /* 0x6 */ dopDBLT, - /* 0x7 */ dopDBLE + /* 0x0 */ &v60_disassembler::dopDBV, + /* 0x1 */ &v60_disassembler::dopDBL, + /* 0x2 */ &v60_disassembler::dopDBE, + /* 0x3 */ &v60_disassembler::dopDBNH, + /* 0x4 */ &v60_disassembler::dopDBN, + /* 0x5 */ &v60_disassembler::dopDBR, + /* 0x6 */ &v60_disassembler::dopDBLT, + /* 0x7 */ &v60_disassembler::dopDBLE }; -static int (*const dasm_optable_C7[8])(unsigned ipc, unsigned pc, std::ostream &stream) = +u32 (v60_disassembler::*const v60_disassembler::dasm_optable_C7[8])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) = { - /* 0x0 */ dopDBNV, - /* 0x1 */ dopDBNL, - /* 0x2 */ dopDBNE, - /* 0x3 */ dopDBH, - /* 0x4 */ dopDBP, - /* 0x5 */ dopTB, - /* 0x6 */ dopDBGE, - /* 0x7 */ dopDBGT + /* 0x0 */ &v60_disassembler::dopDBNV, + /* 0x1 */ &v60_disassembler::dopDBNL, + /* 0x2 */ &v60_disassembler::dopDBNE, + /* 0x3 */ &v60_disassembler::dopDBH, + /* 0x4 */ &v60_disassembler::dopDBP, + /* 0x5 */ &v60_disassembler::dopTB, + /* 0x6 */ &v60_disassembler::dopDBGE, + /* 0x7 */ &v60_disassembler::dopDBGT }; -static int dop58(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dop58(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { - return dasm_optable_58[readop(pc) & 0x1f](ipc, pc, stream); + return (this->*dasm_optable_58[opcodes.r8(pc) & 0x1f])(ipc, pc, opcodes, stream); } -static int dop59(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dop59(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { - return dasm_optable_59[readop(pc) & 0x1f](ipc, pc, stream); + return (this->*dasm_optable_59[opcodes.r8(pc) & 0x1f])(ipc, pc, opcodes, stream); } -static int dop5A(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dop5A(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { - return dasm_optable_5A[readop(pc) & 0x1f](ipc, pc, stream); + return (this->*dasm_optable_5A[opcodes.r8(pc) & 0x1f])(ipc, pc, opcodes, stream); } -static int dop5B(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dop5B(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { - return dasm_optable_5B[readop(pc) & 0x1f](ipc, pc, stream); + return (this->*dasm_optable_5B[opcodes.r8(pc) & 0x1f])(ipc, pc, opcodes, stream); } -static int dop5C(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dop5C(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { - return dasm_optable_5C[readop(pc) & 0x1f](ipc, pc, stream); + return (this->*dasm_optable_5C[opcodes.r8(pc) & 0x1f])(ipc, pc, opcodes, stream); } -static int dop5D(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dop5D(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { - return dasm_optable_5D[readop(pc) & 0x1f](ipc, pc, stream); + return (this->*dasm_optable_5D[opcodes.r8(pc) & 0x1f])(ipc, pc, opcodes, stream); } -static int dop5E(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dop5E(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { - return dasm_optable_5E[readop(pc) & 0x1f](ipc, pc, stream); + return (this->*dasm_optable_5E[opcodes.r8(pc) & 0x1f])(ipc, pc, opcodes, stream); } -static int dop5F(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dop5F(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { - return dasm_optable_5F[readop(pc) & 0x1f](ipc, pc, stream); + return (this->*dasm_optable_5F[opcodes.r8(pc) & 0x1f])(ipc, pc, opcodes, stream); } -static int dopC6(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dopC6(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { - return dasm_optable_C6[readop(pc) >> 5](ipc, pc, stream); + return (this->*dasm_optable_C6[opcodes.r8(pc) >> 5])(ipc, pc, opcodes, stream); } -static int dopC7(unsigned ipc, unsigned pc, std::ostream &stream) +u32 v60_disassembler::dopC7(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) { - return dasm_optable_C7[readop(pc) >> 5](ipc, pc, stream); + return (this->*dasm_optable_C7[opcodes.r8(pc) >> 5])(ipc, pc, opcodes, stream); } -static int (*const dasm_optable[256])(unsigned ipc, unsigned pc, std::ostream &stream) = -{ - /* 0x00 */ dopHALT, - /* 0x01 */ dopLDTASK, - /* 0x02 */ dopSTPR, - /* 0x03 */ dopGETRA, - /* 0x04 */ dopGETPTE, - /* 0x05 */ dopGETATE, - /* 0x06 */ dopUNHANDLED, - /* 0x07 */ dopUNHANDLED, - /* 0x08 */ dopRVBIT, - /* 0x09 */ dopMOVB, - /* 0x0A */ dopMOVSBH, - /* 0x0B */ dopMOVZBH, - /* 0x0C */ dopMOVSBW, - /* 0x0D */ dopMOVZBW, - /* 0x0E */ dopUNHANDLED, - /* 0x0F */ dopUNHANDLED, - /* 0x10 */ dopCLRTLBA, - /* 0x11 */ dopUNHANDLED, - /* 0x12 */ dopLDPR, - /* 0x13 */ dopUPDPSWW, - /* 0x14 */ dopUPDPTE, - /* 0x15 */ dopUPDATE, - /* 0x16 */ dopUNHANDLED, - /* 0x17 */ dopUNHANDLED, - /* 0x18 */ dopUNHANDLED, - /* 0x19 */ dopMOVTHB, - /* 0x1A */ dopUNHANDLED, - /* 0x1B */ dopMOVH, - /* 0x1C */ dopMOVSHW, - /* 0x1D */ dopMOVZHW, - /* 0x1E */ dopUNHANDLED, - /* 0x1F */ dopUNHANDLED, - /* 0x20 */ dopINB, - /* 0x21 */ dopOUTB, - /* 0x22 */ dopINH, - /* 0x23 */ dopOUTH, - /* 0x24 */ dopINW, - /* 0x25 */ dopOUTW, - /* 0x26 */ dopUNHANDLED, - /* 0x27 */ dopUNHANDLED, - /* 0x28 */ dopUNHANDLED, - /* 0x29 */ dopMOVTWB, - /* 0x2A */ dopUNHANDLED, - /* 0x2B */ dopMOVTWH, - /* 0x2C */ dopRVBYT, - /* 0x2D */ dopMOVW, - /* 0x2E */ dopUNHANDLED, - /* 0x2F */ dopUNHANDLED, - /* 0x30 */ dopUNHANDLED, - /* 0x31 */ dopUNHANDLED, - /* 0x32 */ dopUNHANDLED, - /* 0x33 */ dopUNHANDLED, - /* 0x34 */ dopUNHANDLED, - /* 0x35 */ dopUNHANDLED, - /* 0x36 */ dopUNHANDLED, - /* 0x37 */ dopUNHANDLED, - /* 0x38 */ dopNOTB, - /* 0x39 */ dopNEGB, - /* 0x3A */ dopNOTH, - /* 0x3B */ dopNEGH, - /* 0x3C */ dopNOTW, - /* 0x3D */ dopNEGW, - /* 0x3E */ dopUNHANDLED, - /* 0x3F */ dopMOVD, - /* 0x40 */ dopMOVEAB, - /* 0x41 */ dopXCHB, - /* 0x42 */ dopMOVEAH, - /* 0x43 */ dopXCHH, - /* 0x44 */ dopMOVEAW, - /* 0x45 */ dopXCHW, - /* 0x46 */ dopUNHANDLED, - /* 0x47 */ dopSETF, - /* 0x48 */ dopBSR, - /* 0x49 */ dopCALL, - /* 0x4A */ dopUPDPSWH, - /* 0x4B */ dopCHLVL, - /* 0x4C */ dopCAXI, - /* 0x4D */ dopCHKAR, - /* 0x4E */ dopCHKAW, - /* 0x4F */ dopCHKAE, - /* 0x50 */ dopREMB, - /* 0x51 */ dopREMUB, - /* 0x52 */ dopREMH, - /* 0x53 */ dopREMUH, - /* 0x54 */ dopREMW, - /* 0x55 */ dopREMUW, - /* 0x56 */ dopUNHANDLED, - /* 0x57 */ dopUNHANDLED, - /* 0x58 */ dop58, - /* 0x59 */ dop59, - /* 0x5A */ dop5A, - /* 0x5B */ dop5B, - /* 0x5C */ dop5C, - /* 0x5D */ dop5D, - /* 0x5E */ dop5E, - /* 0x5F */ dop5F, - /* 0x60 */ dopBV8, - /* 0x61 */ dopBNV8, - /* 0x62 */ dopBL8, - /* 0x63 */ dopBNL8, - /* 0x64 */ dopBE8, - /* 0x65 */ dopBNE8, - /* 0x66 */ dopBNH8, - /* 0x67 */ dopBH8, - /* 0x68 */ dopBN8, - /* 0x69 */ dopBP8, - /* 0x6A */ dopBR8, - /* 0x6B */ dopUNHANDLED, - /* 0x6C */ dopBLT8, - /* 0x6D */ dopBGE8, - /* 0x6E */ dopBLE8, - /* 0x6F */ dopBGT8, - /* 0x70 */ dopBV16, - /* 0x71 */ dopBNV16, - /* 0x72 */ dopBL16, - /* 0x73 */ dopBNL16, - /* 0x74 */ dopBE16, - /* 0x75 */ dopBNE16, - /* 0x76 */ dopBNH16, - /* 0x77 */ dopBH16, - /* 0x78 */ dopBN16, - /* 0x79 */ dopBP16, - /* 0x7A */ dopBR16, - /* 0x7B */ dopUNHANDLED, - /* 0x7C */ dopBLT16, - /* 0x7D */ dopBGE16, - /* 0x7E */ dopBLE16, - /* 0x7F */ dopBGT16, - /* 0x80 */ dopADDB, - /* 0x81 */ dopMULB, - /* 0x82 */ dopADDH, - /* 0x83 */ dopMULH, - /* 0x84 */ dopADDW, - /* 0x85 */ dopMULW, - /* 0x86 */ dopMULX, - /* 0x87 */ dopTEST1, - /* 0x88 */ dopORB, - /* 0x89 */ dopROTB, - /* 0x8A */ dopORH, - /* 0x8B */ dopROTH, - /* 0x8C */ dopORW, - /* 0x8D */ dopROTW, - /* 0x8E */ dopUNHANDLED, - /* 0x8F */ dopUNHANDLED, - /* 0x90 */ dopADDCB, - /* 0x91 */ dopMULUB, - /* 0x92 */ dopADDCH, - /* 0x93 */ dopMULUH, - /* 0x94 */ dopADDCW, - /* 0x95 */ dopMULUW, - /* 0x96 */ dopMULUX, - /* 0x97 */ dopSET1, - /* 0x98 */ dopSUBCB, - /* 0x99 */ dopROTCB, - /* 0x9A */ dopSUBCH, - /* 0x9B */ dopROTCH, - /* 0x9C */ dopSUBCW, - /* 0x9D */ dopROTCW, - /* 0x9E */ dopUNHANDLED, - /* 0x9F */ dopUNHANDLED, - /* 0xA0 */ dopANDB, - /* 0xA1 */ dopDIVB, - /* 0xA2 */ dopANDH, - /* 0xA3 */ dopDIVH, - /* 0xA4 */ dopANDW, - /* 0xA5 */ dopDIVW, - /* 0xA6 */ dopDIVX, - /* 0xA7 */ dopCLR1, - /* 0xA8 */ dopSUBB, - /* 0xA9 */ dopSHLB, - /* 0xAA */ dopSUBH, - /* 0xAB */ dopSHLH, - /* 0xAC */ dopSUBW, - /* 0xAD */ dopSHLW, - /* 0xAE */ dopUNHANDLED, - /* 0xAF */ dopUNHANDLED, - /* 0xB0 */ dopXORB, - /* 0xB1 */ dopDIVUB, - /* 0xB2 */ dopXORH, - /* 0xB3 */ dopDIVUH, - /* 0xB4 */ dopXORW, - /* 0xB5 */ dopDIVUW, - /* 0xB6 */ dopDIVUX, - /* 0xB7 */ dopNOT1, - /* 0xB8 */ dopCMPB, - /* 0xB9 */ dopSHAB, - /* 0xBA */ dopCMPH, - /* 0xBB */ dopSHAH, - /* 0xBC */ dopCMPW, - /* 0xBD */ dopSHAW, - /* 0xBE */ dopUNHANDLED, - /* 0xBF */ dopUNHANDLED, - /* 0xC0 */ dopUNHANDLED, - /* 0xC1 */ dopUNHANDLED, - /* 0xC2 */ dopUNHANDLED, - /* 0xC3 */ dopUNHANDLED, - /* 0xC4 */ dopUNHANDLED, - /* 0xC5 */ dopUNHANDLED, - /* 0xC6 */ dopC6, - /* 0xC7 */ dopC7, - /* 0xC8 */ dopBRK, - /* 0xC9 */ dopBRKV, - /* 0xCA */ dopRSR, - /* 0xCB */ dopTRAPFL, - /* 0xCC */ dopDISPOSE, - /* 0xCD */ dopNOP, - /* 0xCE */ dopUNHANDLED, - /* 0xCF */ dopUNHANDLED, - /* 0xD0 */ dopDECB, - /* 0xD1 */ dopDECB, - /* 0xD2 */ dopDECH, - /* 0xD3 */ dopDECH, - /* 0xD4 */ dopDECW, - /* 0xD5 */ dopDECW, - /* 0xD6 */ dopJMP, - /* 0xD7 */ dopJMP, - /* 0xD8 */ dopINCB, - /* 0xD9 */ dopINCB, - /* 0xDA */ dopINCH, - /* 0xDB */ dopINCH, - /* 0xDC */ dopINCW, - /* 0xDD */ dopINCW, - /* 0xDE */ dopPREPARE, - /* 0xDF */ dopPREPARE, - /* 0xE0 */ dopTASI, - /* 0xE1 */ dopTASI, - /* 0xE2 */ dopRET, - /* 0xE3 */ dopRET, - /* 0xE4 */ dopPOPM, - /* 0xE5 */ dopPOPM, - /* 0xE6 */ dopPOP, - /* 0xE7 */ dopPOP, - /* 0xE8 */ dopJSR, - /* 0xE9 */ dopJSR, - /* 0xEA */ dopRETIU, - /* 0xEB */ dopRETIU, - /* 0xEC */ dopPUSHM, - /* 0xED */ dopPUSHM, - /* 0xEE */ dopPUSH, - /* 0xEF */ dopPUSH, - /* 0xF0 */ dopTESTB, - /* 0xF1 */ dopTESTB, - /* 0xF2 */ dopTESTH, - /* 0xF3 */ dopTESTH, - /* 0xF4 */ dopTESTW, - /* 0xF5 */ dopTESTW, - /* 0xF6 */ dopGETPSW, - /* 0xF7 */ dopGETPSW, - /* 0xF8 */ dopTRAP, - /* 0xF9 */ dopTRAP, - /* 0xFA */ dopRETIS, - /* 0xFB */ dopRETIS, - /* 0xFC */ dopSTTASK, - /* 0xFD */ dopSTTASK, - /* 0xFE */ dopCLRTLB, - /* 0xFF */ dopCLRTLB +u32 (v60_disassembler::*const v60_disassembler::dasm_optable[256])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream) = +{ + /* 0x00 */ &v60_disassembler::dopHALT, + /* 0x01 */ &v60_disassembler::dopLDTASK, + /* 0x02 */ &v60_disassembler::dopSTPR, + /* 0x03 */ &v60_disassembler::dopGETRA, + /* 0x04 */ &v60_disassembler::dopGETPTE, + /* 0x05 */ &v60_disassembler::dopGETATE, + /* 0x06 */ &v60_disassembler::dopUNHANDLED, + /* 0x07 */ &v60_disassembler::dopUNHANDLED, + /* 0x08 */ &v60_disassembler::dopRVBIT, + /* 0x09 */ &v60_disassembler::dopMOVB, + /* 0x0A */ &v60_disassembler::dopMOVSBH, + /* 0x0B */ &v60_disassembler::dopMOVZBH, + /* 0x0C */ &v60_disassembler::dopMOVSBW, + /* 0x0D */ &v60_disassembler::dopMOVZBW, + /* 0x0E */ &v60_disassembler::dopUNHANDLED, + /* 0x0F */ &v60_disassembler::dopUNHANDLED, + /* 0x10 */ &v60_disassembler::dopCLRTLBA, + /* 0x11 */ &v60_disassembler::dopUNHANDLED, + /* 0x12 */ &v60_disassembler::dopLDPR, + /* 0x13 */ &v60_disassembler::dopUPDPSWW, + /* 0x14 */ &v60_disassembler::dopUPDPTE, + /* 0x15 */ &v60_disassembler::dopUPDATE, + /* 0x16 */ &v60_disassembler::dopUNHANDLED, + /* 0x17 */ &v60_disassembler::dopUNHANDLED, + /* 0x18 */ &v60_disassembler::dopUNHANDLED, + /* 0x19 */ &v60_disassembler::dopMOVTHB, + /* 0x1A */ &v60_disassembler::dopUNHANDLED, + /* 0x1B */ &v60_disassembler::dopMOVH, + /* 0x1C */ &v60_disassembler::dopMOVSHW, + /* 0x1D */ &v60_disassembler::dopMOVZHW, + /* 0x1E */ &v60_disassembler::dopUNHANDLED, + /* 0x1F */ &v60_disassembler::dopUNHANDLED, + /* 0x20 */ &v60_disassembler::dopINB, + /* 0x21 */ &v60_disassembler::dopOUTB, + /* 0x22 */ &v60_disassembler::dopINH, + /* 0x23 */ &v60_disassembler::dopOUTH, + /* 0x24 */ &v60_disassembler::dopINW, + /* 0x25 */ &v60_disassembler::dopOUTW, + /* 0x26 */ &v60_disassembler::dopUNHANDLED, + /* 0x27 */ &v60_disassembler::dopUNHANDLED, + /* 0x28 */ &v60_disassembler::dopUNHANDLED, + /* 0x29 */ &v60_disassembler::dopMOVTWB, + /* 0x2A */ &v60_disassembler::dopUNHANDLED, + /* 0x2B */ &v60_disassembler::dopMOVTWH, + /* 0x2C */ &v60_disassembler::dopRVBYT, + /* 0x2D */ &v60_disassembler::dopMOVW, + /* 0x2E */ &v60_disassembler::dopUNHANDLED, + /* 0x2F */ &v60_disassembler::dopUNHANDLED, + /* 0x30 */ &v60_disassembler::dopUNHANDLED, + /* 0x31 */ &v60_disassembler::dopUNHANDLED, + /* 0x32 */ &v60_disassembler::dopUNHANDLED, + /* 0x33 */ &v60_disassembler::dopUNHANDLED, + /* 0x34 */ &v60_disassembler::dopUNHANDLED, + /* 0x35 */ &v60_disassembler::dopUNHANDLED, + /* 0x36 */ &v60_disassembler::dopUNHANDLED, + /* 0x37 */ &v60_disassembler::dopUNHANDLED, + /* 0x38 */ &v60_disassembler::dopNOTB, + /* 0x39 */ &v60_disassembler::dopNEGB, + /* 0x3A */ &v60_disassembler::dopNOTH, + /* 0x3B */ &v60_disassembler::dopNEGH, + /* 0x3C */ &v60_disassembler::dopNOTW, + /* 0x3D */ &v60_disassembler::dopNEGW, + /* 0x3E */ &v60_disassembler::dopUNHANDLED, + /* 0x3F */ &v60_disassembler::dopMOVD, + /* 0x40 */ &v60_disassembler::dopMOVEAB, + /* 0x41 */ &v60_disassembler::dopXCHB, + /* 0x42 */ &v60_disassembler::dopMOVEAH, + /* 0x43 */ &v60_disassembler::dopXCHH, + /* 0x44 */ &v60_disassembler::dopMOVEAW, + /* 0x45 */ &v60_disassembler::dopXCHW, + /* 0x46 */ &v60_disassembler::dopUNHANDLED, + /* 0x47 */ &v60_disassembler::dopSETF, + /* 0x48 */ &v60_disassembler::dopBSR, + /* 0x49 */ &v60_disassembler::dopCALL, + /* 0x4A */ &v60_disassembler::dopUPDPSWH, + /* 0x4B */ &v60_disassembler::dopCHLVL, + /* 0x4C */ &v60_disassembler::dopCAXI, + /* 0x4D */ &v60_disassembler::dopCHKAR, + /* 0x4E */ &v60_disassembler::dopCHKAW, + /* 0x4F */ &v60_disassembler::dopCHKAE, + /* 0x50 */ &v60_disassembler::dopREMB, + /* 0x51 */ &v60_disassembler::dopREMUB, + /* 0x52 */ &v60_disassembler::dopREMH, + /* 0x53 */ &v60_disassembler::dopREMUH, + /* 0x54 */ &v60_disassembler::dopREMW, + /* 0x55 */ &v60_disassembler::dopREMUW, + /* 0x56 */ &v60_disassembler::dopUNHANDLED, + /* 0x57 */ &v60_disassembler::dopUNHANDLED, + /* 0x58 */ &v60_disassembler::dop58, + /* 0x59 */ &v60_disassembler::dop59, + /* 0x5A */ &v60_disassembler::dop5A, + /* 0x5B */ &v60_disassembler::dop5B, + /* 0x5C */ &v60_disassembler::dop5C, + /* 0x5D */ &v60_disassembler::dop5D, + /* 0x5E */ &v60_disassembler::dop5E, + /* 0x5F */ &v60_disassembler::dop5F, + /* 0x60 */ &v60_disassembler::dopBV8, + /* 0x61 */ &v60_disassembler::dopBNV8, + /* 0x62 */ &v60_disassembler::dopBL8, + /* 0x63 */ &v60_disassembler::dopBNL8, + /* 0x64 */ &v60_disassembler::dopBE8, + /* 0x65 */ &v60_disassembler::dopBNE8, + /* 0x66 */ &v60_disassembler::dopBNH8, + /* 0x67 */ &v60_disassembler::dopBH8, + /* 0x68 */ &v60_disassembler::dopBN8, + /* 0x69 */ &v60_disassembler::dopBP8, + /* 0x6A */ &v60_disassembler::dopBR8, + /* 0x6B */ &v60_disassembler::dopUNHANDLED, + /* 0x6C */ &v60_disassembler::dopBLT8, + /* 0x6D */ &v60_disassembler::dopBGE8, + /* 0x6E */ &v60_disassembler::dopBLE8, + /* 0x6F */ &v60_disassembler::dopBGT8, + /* 0x70 */ &v60_disassembler::dopBV16, + /* 0x71 */ &v60_disassembler::dopBNV16, + /* 0x72 */ &v60_disassembler::dopBL16, + /* 0x73 */ &v60_disassembler::dopBNL16, + /* 0x74 */ &v60_disassembler::dopBE16, + /* 0x75 */ &v60_disassembler::dopBNE16, + /* 0x76 */ &v60_disassembler::dopBNH16, + /* 0x77 */ &v60_disassembler::dopBH16, + /* 0x78 */ &v60_disassembler::dopBN16, + /* 0x79 */ &v60_disassembler::dopBP16, + /* 0x7A */ &v60_disassembler::dopBR16, + /* 0x7B */ &v60_disassembler::dopUNHANDLED, + /* 0x7C */ &v60_disassembler::dopBLT16, + /* 0x7D */ &v60_disassembler::dopBGE16, + /* 0x7E */ &v60_disassembler::dopBLE16, + /* 0x7F */ &v60_disassembler::dopBGT16, + /* 0x80 */ &v60_disassembler::dopADDB, + /* 0x81 */ &v60_disassembler::dopMULB, + /* 0x82 */ &v60_disassembler::dopADDH, + /* 0x83 */ &v60_disassembler::dopMULH, + /* 0x84 */ &v60_disassembler::dopADDW, + /* 0x85 */ &v60_disassembler::dopMULW, + /* 0x86 */ &v60_disassembler::dopMULX, + /* 0x87 */ &v60_disassembler::dopTEST1, + /* 0x88 */ &v60_disassembler::dopORB, + /* 0x89 */ &v60_disassembler::dopROTB, + /* 0x8A */ &v60_disassembler::dopORH, + /* 0x8B */ &v60_disassembler::dopROTH, + /* 0x8C */ &v60_disassembler::dopORW, + /* 0x8D */ &v60_disassembler::dopROTW, + /* 0x8E */ &v60_disassembler::dopUNHANDLED, + /* 0x8F */ &v60_disassembler::dopUNHANDLED, + /* 0x90 */ &v60_disassembler::dopADDCB, + /* 0x91 */ &v60_disassembler::dopMULUB, + /* 0x92 */ &v60_disassembler::dopADDCH, + /* 0x93 */ &v60_disassembler::dopMULUH, + /* 0x94 */ &v60_disassembler::dopADDCW, + /* 0x95 */ &v60_disassembler::dopMULUW, + /* 0x96 */ &v60_disassembler::dopMULUX, + /* 0x97 */ &v60_disassembler::dopSET1, + /* 0x98 */ &v60_disassembler::dopSUBCB, + /* 0x99 */ &v60_disassembler::dopROTCB, + /* 0x9A */ &v60_disassembler::dopSUBCH, + /* 0x9B */ &v60_disassembler::dopROTCH, + /* 0x9C */ &v60_disassembler::dopSUBCW, + /* 0x9D */ &v60_disassembler::dopROTCW, + /* 0x9E */ &v60_disassembler::dopUNHANDLED, + /* 0x9F */ &v60_disassembler::dopUNHANDLED, + /* 0xA0 */ &v60_disassembler::dopANDB, + /* 0xA1 */ &v60_disassembler::dopDIVB, + /* 0xA2 */ &v60_disassembler::dopANDH, + /* 0xA3 */ &v60_disassembler::dopDIVH, + /* 0xA4 */ &v60_disassembler::dopANDW, + /* 0xA5 */ &v60_disassembler::dopDIVW, + /* 0xA6 */ &v60_disassembler::dopDIVX, + /* 0xA7 */ &v60_disassembler::dopCLR1, + /* 0xA8 */ &v60_disassembler::dopSUBB, + /* 0xA9 */ &v60_disassembler::dopSHLB, + /* 0xAA */ &v60_disassembler::dopSUBH, + /* 0xAB */ &v60_disassembler::dopSHLH, + /* 0xAC */ &v60_disassembler::dopSUBW, + /* 0xAD */ &v60_disassembler::dopSHLW, + /* 0xAE */ &v60_disassembler::dopUNHANDLED, + /* 0xAF */ &v60_disassembler::dopUNHANDLED, + /* 0xB0 */ &v60_disassembler::dopXORB, + /* 0xB1 */ &v60_disassembler::dopDIVUB, + /* 0xB2 */ &v60_disassembler::dopXORH, + /* 0xB3 */ &v60_disassembler::dopDIVUH, + /* 0xB4 */ &v60_disassembler::dopXORW, + /* 0xB5 */ &v60_disassembler::dopDIVUW, + /* 0xB6 */ &v60_disassembler::dopDIVUX, + /* 0xB7 */ &v60_disassembler::dopNOT1, + /* 0xB8 */ &v60_disassembler::dopCMPB, + /* 0xB9 */ &v60_disassembler::dopSHAB, + /* 0xBA */ &v60_disassembler::dopCMPH, + /* 0xBB */ &v60_disassembler::dopSHAH, + /* 0xBC */ &v60_disassembler::dopCMPW, + /* 0xBD */ &v60_disassembler::dopSHAW, + /* 0xBE */ &v60_disassembler::dopUNHANDLED, + /* 0xBF */ &v60_disassembler::dopUNHANDLED, + /* 0xC0 */ &v60_disassembler::dopUNHANDLED, + /* 0xC1 */ &v60_disassembler::dopUNHANDLED, + /* 0xC2 */ &v60_disassembler::dopUNHANDLED, + /* 0xC3 */ &v60_disassembler::dopUNHANDLED, + /* 0xC4 */ &v60_disassembler::dopUNHANDLED, + /* 0xC5 */ &v60_disassembler::dopUNHANDLED, + /* 0xC6 */ &v60_disassembler::dopC6, + /* 0xC7 */ &v60_disassembler::dopC7, + /* 0xC8 */ &v60_disassembler::dopBRK, + /* 0xC9 */ &v60_disassembler::dopBRKV, + /* 0xCA */ &v60_disassembler::dopRSR, + /* 0xCB */ &v60_disassembler::dopTRAPFL, + /* 0xCC */ &v60_disassembler::dopDISPOSE, + /* 0xCD */ &v60_disassembler::dopNOP, + /* 0xCE */ &v60_disassembler::dopUNHANDLED, + /* 0xCF */ &v60_disassembler::dopUNHANDLED, + /* 0xD0 */ &v60_disassembler::dopDECB, + /* 0xD1 */ &v60_disassembler::dopDECB, + /* 0xD2 */ &v60_disassembler::dopDECH, + /* 0xD3 */ &v60_disassembler::dopDECH, + /* 0xD4 */ &v60_disassembler::dopDECW, + /* 0xD5 */ &v60_disassembler::dopDECW, + /* 0xD6 */ &v60_disassembler::dopJMP, + /* 0xD7 */ &v60_disassembler::dopJMP, + /* 0xD8 */ &v60_disassembler::dopINCB, + /* 0xD9 */ &v60_disassembler::dopINCB, + /* 0xDA */ &v60_disassembler::dopINCH, + /* 0xDB */ &v60_disassembler::dopINCH, + /* 0xDC */ &v60_disassembler::dopINCW, + /* 0xDD */ &v60_disassembler::dopINCW, + /* 0xDE */ &v60_disassembler::dopPREPARE, + /* 0xDF */ &v60_disassembler::dopPREPARE, + /* 0xE0 */ &v60_disassembler::dopTASI, + /* 0xE1 */ &v60_disassembler::dopTASI, + /* 0xE2 */ &v60_disassembler::dopRET, + /* 0xE3 */ &v60_disassembler::dopRET, + /* 0xE4 */ &v60_disassembler::dopPOPM, + /* 0xE5 */ &v60_disassembler::dopPOPM, + /* 0xE6 */ &v60_disassembler::dopPOP, + /* 0xE7 */ &v60_disassembler::dopPOP, + /* 0xE8 */ &v60_disassembler::dopJSR, + /* 0xE9 */ &v60_disassembler::dopJSR, + /* 0xEA */ &v60_disassembler::dopRETIU, + /* 0xEB */ &v60_disassembler::dopRETIU, + /* 0xEC */ &v60_disassembler::dopPUSHM, + /* 0xED */ &v60_disassembler::dopPUSHM, + /* 0xEE */ &v60_disassembler::dopPUSH, + /* 0xEF */ &v60_disassembler::dopPUSH, + /* 0xF0 */ &v60_disassembler::dopTESTB, + /* 0xF1 */ &v60_disassembler::dopTESTB, + /* 0xF2 */ &v60_disassembler::dopTESTH, + /* 0xF3 */ &v60_disassembler::dopTESTH, + /* 0xF4 */ &v60_disassembler::dopTESTW, + /* 0xF5 */ &v60_disassembler::dopTESTW, + /* 0xF6 */ &v60_disassembler::dopGETPSW, + /* 0xF7 */ &v60_disassembler::dopGETPSW, + /* 0xF8 */ &v60_disassembler::dopTRAP, + /* 0xF9 */ &v60_disassembler::dopTRAP, + /* 0xFA */ &v60_disassembler::dopRETIS, + /* 0xFB */ &v60_disassembler::dopRETIS, + /* 0xFC */ &v60_disassembler::dopSTTASK, + /* 0xFD */ &v60_disassembler::dopSTTASK, + /* 0xFE */ &v60_disassembler::dopCLRTLB, + /* 0xFF */ &v60_disassembler::dopCLRTLB }; -CPU_DISASSEMBLE(v60) +offs_t v60_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - rombase = oprom; - pcbase = pc; - return dasm_optable[oprom[0]](pc, pc+1, stream) | DASMFLAG_SUPPORTED; + return (this->*dasm_optable[opcodes.r8(pc)])(pc, pc+1, opcodes, stream) | SUPPORTED; } -CPU_DISASSEMBLE(v70) +u32 v60_disassembler::opcode_alignment() const { - rombase = oprom; - pcbase = pc; - return dasm_optable[oprom[0]](pc, pc+1, stream) | DASMFLAG_SUPPORTED; + return 1; } diff --git a/src/devices/cpu/v60/v60d.h b/src/devices/cpu/v60/v60d.h new file mode 100644 index 00000000000..6bbef76f47c --- /dev/null +++ b/src/devices/cpu/v60/v60d.h @@ -0,0 +1,359 @@ +// license:BSD-3-Clause +// copyright-holders:Farfetch'd, R. Belmont + +#ifndef MAME_CPU_V60_V60D_H +#define MAME_CPU_V60_V60D_H + +#pragma once + +class v60_disassembler : public util::disasm_interface +{ +public: + v60_disassembler() = default; + virtual ~v60_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *const v60_reg_names[69]; + static u32 (v60_disassembler::*const dasm_optable_58[32])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + static u32 (v60_disassembler::*const dasm_optable_59[32])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + static u32 (v60_disassembler::*const dasm_optable_5A[32])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + static u32 (v60_disassembler::*const dasm_optable_5B[32])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + static u32 (v60_disassembler::*const dasm_optable_5C[32])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + static u32 (v60_disassembler::*const dasm_optable_5D[32])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + static u32 (v60_disassembler::*const dasm_optable_5E[32])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + static u32 (v60_disassembler::*const dasm_optable_5F[32])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + static u32 (v60_disassembler::*const dasm_optable_C6[8])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + static u32 (v60_disassembler::*const dasm_optable_C7[8])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + static u32 (v60_disassembler::*const dasm_optable[256])(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + + u32 dop58(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dop58UNHANDLED(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dop59(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dop59UNHANDLED(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dop5A(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dop5AUNHANDLED(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dop5B(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dop5BUNHANDLED(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dop5C(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dop5CUNHANDLED(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dop5D(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dop5DUNHANDLED(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dop5E(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dop5EUNHANDLED(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dop5F(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dop5FUNHANDLED(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopABSFL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopABSFS(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopADDB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopADDCB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopADDCH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopADDCW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopADDDC(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopADDFL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopADDFS(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopADDH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopADDW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopANDB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopANDBSD(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopANDBSU(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopANDH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopANDNBSD(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopANDNBSU(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopANDW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBE16(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBE8(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBGE16(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBGE8(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBGT16(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBGT8(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBH16(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBH8(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBL16(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBL8(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBLE16(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBLE8(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBLT16(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBLT8(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBN16(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBN8(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBNE16(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBNE8(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBNH16(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBNH8(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBNL16(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBNL8(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBNV16(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBNV8(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBP16(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBP8(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBR16(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBR8(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBRK(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBRKV(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBSR(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBV16(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopBV8(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopC6(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopC7(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCALL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCAXI(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCHKAE(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCHKAR(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCHKAW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCHLVL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCLR1(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCLRTLB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCLRTLBA(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCMPB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCMPBFL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCMPBFS(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCMPBFZ(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCMPCB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCMPCFB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCMPCFH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCMPCH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCMPCSB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCMPCSH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCMPFL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCMPFS(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCMPH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCMPW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCVTDPZ(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCVTDZP(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCVTLS(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCVTLW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCVTSL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCVTSW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCVTWL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopCVTWS(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDBE(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDBGE(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDBGT(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDBH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDBL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDBLE(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDBLT(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDBN(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDBNE(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDBNH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDBNL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDBNV(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDBP(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDBR(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDBV(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDECB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDECH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDECW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDISPOSE(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDIVB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDIVFL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDIVFS(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDIVH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDIVUB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDIVUH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDIVUW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDIVUX(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDIVW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopDIVX(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopEXTBFL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopEXTBFS(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopEXTBFZ(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopGETATE(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopGETPSW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopGETPTE(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopGETRA(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopHALT(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopINB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopINCB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopINCH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopINCW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopINH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopINSBFL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopINSBFR(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopINW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopJMP(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopJSR(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopLDPR(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopLDTASK(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVBSD(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVBSU(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVCDB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVCDH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVCFDB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVCFDH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVCFUB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVCFUH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVCSB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVCSH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVCUB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVCUH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVD(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVEAB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVEAH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVEAW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVFL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVFS(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVSBH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVSBW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVSHW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVTHB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVTWB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVTWH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVZBH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVZBW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMOVZHW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMULB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMULFL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMULFS(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMULH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMULUB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMULUH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMULUW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMULUX(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMULW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopMULX(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopNEGB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopNEGFL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopNEGFS(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopNEGH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopNEGW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopNOP(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopNOT1(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopNOTB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopNOTBSD(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopNOTBSU(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopNOTH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopNOTW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopORB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopORBSD(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopORBSU(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopORH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopORNBSD(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopORNBSU(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopORW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopOUTB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopOUTH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopOUTW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopPOP(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopPOPM(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopPREPARE(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopPUSH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopPUSHM(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopREMB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopREMH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopREMUB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopREMUH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopREMUW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopREMW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopRET(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopRETIS(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopRETIU(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopROTB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopROTCB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopROTCH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopROTCW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopROTH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopROTW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopRSR(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopRVBIT(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopRVBYT(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSCH0BSD(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSCH0BSU(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSCH1BSD(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSCH1BSU(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSCHCDB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSCHCDH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSCHCUB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSCHCUH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSCLFL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSCLFS(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSET1(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSETF(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSHAB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSHAH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSHAW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSHLB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSHLH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSHLW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSKPCDB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSKPCDH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSKPCUB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSKPCUH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSTPR(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSTTASK(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSUBB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSUBCB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSUBCH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSUBCW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSUBDC(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSUBFL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSUBFS(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSUBH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSUBRDC(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopSUBW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopTASI(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopTB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopTEST1(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopTESTB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopTESTH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopTESTW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopTRAP(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopTRAPFL(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopUNHANDLED(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopUPDATE(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopUPDPSWH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopUPDPSWW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopUPDPTE(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopXCHB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopXCHH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopXCHW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopXORB(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopXORBSD(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopXORBSU(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopXORH(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopXORNBSD(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopXORNBSU(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 dopXORW(unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + + void out_AM_Register(int reg, std::ostream &stream); + void out_AM_RegisterIndirect(int reg, int opsize, std::ostream &stream); + void out_AM_RegisterIndirectIndexed(int rn, int rx, int opsize, std::ostream &stream); + void out_AM_Autoincrement(int reg, int opsize, std::ostream &stream); + void out_AM_Autodecrement(int reg, int opsize, std::ostream &stream); + void out_AM_Displacement(int reg, int disp, int opsize, std::ostream &stream); + void out_AM_DisplacementIndexed(int rn, int rx, int disp, int opsize, std::ostream &stream); + void out_AM_PCDisplacement(offs_t pc, int disp, int opsize, std::ostream &stream); + void out_AM_PCDisplacementIndexed(offs_t pc, int disp, int rx, int opsize, std::ostream &stream); + void out_AM_DisplacementIndirect(int reg, int disp, int opsize, std::ostream &stream); + void out_AM_DisplacementIndirectIndexed(int rn, int rx, int disp, int opsize, std::ostream &stream); + void out_AM_PCDisplacementIndirect(offs_t pc, int disp, int opsize, std::ostream &stream); + void out_AM_PCDisplacementIndirectIndexed(offs_t pc, int disp, int rx, int opsize, std::ostream &stream); + void out_AM_DoubleDisplacement(int reg, int disp2, int disp1, int opsize, std::ostream &stream); + void out_AM_PCDoubleDisplacement(offs_t pc, int disp2, int disp1, int opsize, std::ostream &stream); + void out_AM_DirectAddress(unsigned addr, int opsize, std::ostream &stream); + void out_AM_DirectAddressIndexed(unsigned addr, int rx, int opsize, std::ostream &stream); + void out_AM_DirectAddressDeferred(unsigned addr, int opsize, std::ostream &stream); + void out_AM_DirectAddressDeferredIndexed(unsigned addr, int rx, int opsize, std::ostream &stream); + void out_AM_Immediate(unsigned value, int opsize, std::ostream &stream); + u32 decode_AM(unsigned ipc, offs_t pc, int m, int opsize, const data_buffer &opcodes, std::ostream &stream); + u32 decode_F1(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 decode_F2(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 decode_F1F2(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 decode_F3(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 decode_F4a(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 decode_F4b(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 decode_F5(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 decode_F6(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 decode_F7a(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 decode_F7b(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + u32 decode_F7c(const char *opnm, int opsize1, int opsize2, unsigned ipc, offs_t pc, const data_buffer &opcodes, std::ostream &stream); + +}; + +#endif diff --git a/src/devices/cpu/v810/v810.cpp b/src/devices/cpu/v810/v810.cpp index fc6aa5897fe..7b12378961f 100644 --- a/src/devices/cpu/v810/v810.cpp +++ b/src/devices/cpu/v810/v810.cpp @@ -29,6 +29,7 @@ #include "emu.h" #include "v810.h" +#include "v810dasm.h" #include "debugger.h" #define clkIF 3 @@ -54,10 +55,9 @@ device_memory_interface::space_config_vector v810_device::memory_space_config() } -offs_t v810_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *v810_device::create_disassembler() { - extern CPU_DISASSEMBLE( v810 ); - return CPU_DISASSEMBLE_NAME(v810)(this, stream, pc, oprom, opram, options); + return new v810_disassembler; } diff --git a/src/devices/cpu/v810/v810.h b/src/devices/cpu/v810/v810.h index e136259cc4a..2794c629a16 100644 --- a/src/devices/cpu/v810/v810.h +++ b/src/devices/cpu/v810/v810.h @@ -104,9 +104,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: typedef uint32_t (v810_device::*opcode_func)(uint32_t op); diff --git a/src/devices/cpu/v810/v810dasm.cpp b/src/devices/cpu/v810/v810dasm.cpp index b88600d353e..3e8410881d5 100644 --- a/src/devices/cpu/v810/v810dasm.cpp +++ b/src/devices/cpu/v810/v810dasm.cpp @@ -6,8 +6,7 @@ *******************************************/ #include "emu.h" -#include "debugger.h" -#include "v810.h" +#include "v810dasm.h" #define I5(x) (((x)&0x1f)|(((x)&0x10)?0xffffffe0:0)) #define UI5(x) ((x)&0x1f) @@ -17,7 +16,7 @@ #define D26(x,y) ((y)|((x&0x3ff)<<16 )|((x&0x200)?0xfc000000:0)) #define D9(x) ((x&0x1ff)|((x&0x100)?0xfffffe00:0)) -static const char *const dRegs[]= +const char *const v810_disassembler::dRegs[]= { "R0","R1","R2","SP","R4", "R5","R6","R7","R8","R9", @@ -39,13 +38,18 @@ static const char *const dRegs[]= #define GET2s(opcode) dRegs[((opcode)>>5)&0x1f] #define GETRs(opcode) dRegs[32+((opcode)&0x1f)] -CPU_DISASSEMBLE(v810) +u32 v810_disassembler::opcode_alignment() const +{ + return 2; +} + +offs_t v810_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { uint32_t flags = 0; uint32_t opc,opc2; unsigned size; - opc = oprom[0] | (oprom[1] << 8); - opc2 = oprom[2] | (oprom[3] << 8); + opc = opcodes.r16(pc); + opc2 = opcodes.r16(pc+2); switch(opc>>10) { @@ -55,7 +59,7 @@ CPU_DISASSEMBLE(v810) case 0x03: util::stream_format(stream,"CMP %s,%s",GET1s(opc),GET2s(opc)); size=2; break; case 0x04: util::stream_format(stream,"SHL %s,%s",GET1s(opc),GET2s(opc)); size=2; break; case 0x05: util::stream_format(stream,"SHR %s,%s",GET1s(opc),GET2s(opc)); size=2; break; - case 0x06: util::stream_format(stream,"JMP [%s]",GET1s(opc)); size=2; if ((opc&0x1f) == 31) flags = DASMFLAG_STEP_OUT; break; + case 0x06: util::stream_format(stream,"JMP [%s]",GET1s(opc)); size=2; if ((opc&0x1f) == 31) flags = STEP_OUT; break; case 0x07: util::stream_format(stream,"SAR %s,%s",GET1s(opc),GET2s(opc)); size=2; break; case 0x08: util::stream_format(stream,"MUL %s,%s",GET1s(opc),GET2s(opc)); size=2; break; case 0x09: util::stream_format(stream,"DIV %s,%s",GET1s(opc),GET2s(opc)); size=2; break; @@ -74,7 +78,7 @@ CPU_DISASSEMBLE(v810) case 0x16: util::stream_format(stream,"EI"); size=2; break; case 0x17: util::stream_format(stream,"SAR %X,%s",UI5(opc),GET2s(opc)); size=2; break; case 0x18: util::stream_format(stream,"TRAP %X",I5(opc)); size=2; break; - case 0x19: util::stream_format(stream,"RETI"); size=2; flags = DASMFLAG_STEP_OUT; break; + case 0x19: util::stream_format(stream,"RETI"); size=2; flags = STEP_OUT; break; case 0x1a: util::stream_format(stream,"HALT"); size=2; break; case 0x1b: util::stream_format(stream,"Unk 0x1B"); size=2; break; case 0x1c: util::stream_format(stream,"LDSR %s,%s",GET2s(opc),GETRs(opc));size=2; break; @@ -134,7 +138,7 @@ CPU_DISASSEMBLE(v810) case 0x28: util::stream_format(stream,"MOVEA %X, %s, %s",I16(opc2),GET1s(opc),GET2s(opc));size=4; break; case 0x29: util::stream_format(stream,"ADDI %X, %s, %s",I16(opc2),GET1s(opc),GET2s(opc));size=4; break; case 0x2a: util::stream_format(stream,"JR %X",pc+D26(opc,opc2));size=4; break; - case 0x2b: util::stream_format(stream,"JAL %X",pc+D26(opc,opc2));size=4; flags = DASMFLAG_STEP_OVER; break; + case 0x2b: util::stream_format(stream,"JAL %X",pc+D26(opc,opc2));size=4; flags = STEP_OVER; break; case 0x2c: util::stream_format(stream,"ORI %X, %s, %s",UI16(opc2),GET1s(opc),GET2s(opc));size=4; break; case 0x2d: util::stream_format(stream,"ANDI %X, %s, %s",UI16(opc2),GET1s(opc),GET2s(opc));size=4; break; case 0x2e: util::stream_format(stream,"XORI %X, %s, %s",UI16(opc2),GET1s(opc),GET2s(opc));size=4; break; @@ -173,5 +177,5 @@ CPU_DISASSEMBLE(v810) default : size=2; } - return size | flags | DASMFLAG_SUPPORTED; + return size | flags | SUPPORTED; } diff --git a/src/devices/cpu/v810/v810dasm.h b/src/devices/cpu/v810/v810dasm.h new file mode 100644 index 00000000000..3daed05a131 --- /dev/null +++ b/src/devices/cpu/v810/v810dasm.h @@ -0,0 +1,27 @@ +// license:BSD-3-Clause +// copyright-holders:Tomasz Slanina +/******************************************** + NEC V810 (upd70732) disassembler + Tomasz Slanina - analog[at]op.pl +*******************************************/ + + +#ifndef MAME_CPU_V810_V810DASM_H +#define MAME_CPU_V810_V810DASM_H + +#pragma once + +class v810_disassembler : public util::disasm_interface +{ +public: + v810_disassembler() = default; + virtual ~v810_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *const dRegs[]; +}; + +#endif diff --git a/src/devices/cpu/x86log.cpp b/src/devices/cpu/x86log.cpp index 03552877128..b97f2553f11 100644 --- a/src/devices/cpu/x86log.cpp +++ b/src/devices/cpu/x86log.cpp @@ -96,6 +96,30 @@ void x86log_mark_as_data(x86log_context *log, x86code *base, x86code *end, int s of code and reset accumulated information -------------------------------------------------*/ +namespace { + class x86_buf : public util::disasm_interface::data_buffer { + public: + x86_buf(offs_t _base_pc, const u8 *_buf) : base_pc(_base_pc), buf(_buf) {} + ~x86_buf() = default; + + // We know we're on a x86, so we can go short + virtual u8 r8 (offs_t pc) const override { return *(u8 *)(buf + pc - base_pc); } + virtual u16 r16(offs_t pc) const override { return *(u16 *)(buf + pc - base_pc); } + virtual u32 r32(offs_t pc) const override { return *(u32 *)(buf + pc - base_pc); } + virtual u64 r64(offs_t pc) const override { return *(u64 *)(buf + pc - base_pc); } + + private: + offs_t base_pc; + const u8 *buf; + }; + + class x86_config : public i386_disassembler::config { + public: + ~x86_config() = default; + virtual int get_mode() const override { return sizeof(void *) * 8; }; + }; +} + void x86log_disasm_code_range(x86log_context *log, const char *label, x86code *start, x86code *stop) { const log_comment *lastcomment = &log->comment_list[log->comment_count]; @@ -147,7 +171,11 @@ void x86log_disasm_code_range(x86log_context *log, const char *label, x86code *s else { std::stringstream strbuffer; - bytes = i386_dasm_one_ex(strbuffer, (uintptr_t)cur, cur, sizeof(void *) * 8) & DASMFLAG_LENGTHMASK; + offs_t pc = (uintptr_t)cur; + x86_buf buf(pc, cur); + x86_config conf; + i386_disassembler dis(&conf); + bytes = dis.disassemble(strbuffer, pc, buf, buf) & util::disasm_interface::LENGTHMASK; buffer = strbuffer.str(); } diff --git a/src/devices/cpu/z180/z180.cpp b/src/devices/cpu/z180/z180.cpp index b1abdef1c4b..560f267e7a1 100644 --- a/src/devices/cpu/z180/z180.cpp +++ b/src/devices/cpu/z180/z180.cpp @@ -52,6 +52,7 @@ Hitachi HD647180 series: #include "emu.h" #include "z180.h" +#include "z180dasm.h" #include "debugger.h" //#define VERBOSE 1 @@ -89,14 +90,11 @@ z180_device::z180_device(const machine_config &mconfig, const char *tag, device_ { } - -offs_t z180_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *z180_device::create_disassembler() { - extern CPU_DISASSEMBLE( z180 ); - return CPU_DISASSEMBLE_NAME(z180)(this, stream, pc, oprom, opram, options); + return new z180_disassembler; } - #define CF 0x01 #define NF 0x02 #define PF 0x04 diff --git a/src/devices/cpu/z180/z180.h b/src/devices/cpu/z180/z180.h index dca5c963539..b13940b8364 100644 --- a/src/devices/cpu/z180/z180.h +++ b/src/devices/cpu/z180/z180.h @@ -158,9 +158,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; private: address_space_config m_program_config; diff --git a/src/devices/cpu/z180/z180dasm.cpp b/src/devices/cpu/z180/z180dasm.cpp index c5a3d9f0186..521ec1bfe41 100644 --- a/src/devices/cpu/z180/z180dasm.cpp +++ b/src/devices/cpu/z180/z180dasm.cpp @@ -8,23 +8,9 @@ *****************************************************************************/ #include "emu.h" -#include "debugger.h" -#include "z180.h" +#include "z180dasm.h" -enum e_mnemonics { - zADC ,zADD ,zAND ,zBIT ,zCALL ,zCCF ,zCP ,zCPD , - zCPDR ,zCPI ,zCPIR ,zCPL ,zDAA ,zDB ,zDEC ,zDI , - zDJNZ ,zEI ,zEX ,zEXX ,zHLT ,zIM ,zIN ,zIN0 , - zINC ,zIND ,zINDR ,zINI ,zINIR ,zJP ,zJR ,zLD , - zLDD ,zLDDR ,zLDI ,zLDIR ,zMLT ,zNEG ,zNOP ,zOR , - zOTDM ,zOTDMR ,zOTDR ,zOTIM ,zOTIMR ,zOTIR ,zOUT ,zOUT0 , - zOUTD ,zOUTI ,zPOP ,zPUSH ,zRES ,zRET ,zRETI ,zRETN , - zRL ,zRLA ,zRLC ,zRLCA ,zRLD ,zRR ,zRRA ,zRRC , - zRRCA ,zRRD ,zRST ,zSBC ,zSCF ,zSET ,zSLA ,zSLL , - zSLP ,zSRA ,zSRL ,zSUB ,zTST ,zTSTIO ,zXOR -}; - -static const char *const s_mnemonic[] = { +const char *const z180_disassembler::s_mnemonic[] = { "adc" ,"add" ,"and" ,"bit" ,"call" ,"ccf" ,"cp" ,"cpd" , "cpdr" ,"cpi" ,"cpir" ,"cpl" ,"daa" ,"db" ,"dec" ,"di" , "djnz" ,"ei" ,"ex" ,"exx" ,"halt" ,"im" ,"in" ,"in0" , @@ -37,12 +23,7 @@ static const char *const s_mnemonic[] = { "slp" ,"sra" ,"srl" ,"sub" ,"tst" ,"tstio","xor " }; -struct z80dasm { - uint8_t mnemonic; - const char *arguments; -}; - -static const z80dasm mnemonic_xx_cb[256]= { +const z180_disassembler::z80dasm z180_disassembler::mnemonic_xx_cb[256]= { {zRLC,"b=Y"}, {zRLC,"c=Y"}, {zRLC,"d=Y"}, {zRLC,"e=Y"}, {zRLC,"h=Y"}, {zRLC,"l=Y"}, {zRLC,"Y"}, {zRLC,"a=Y"}, {zRRC,"b=Y"}, {zRRC,"c=Y"}, {zRRC,"d=Y"}, {zRRC,"e=Y"}, @@ -109,7 +90,7 @@ static const z80dasm mnemonic_xx_cb[256]= { {zSET,"h=7,Y"}, {zSET,"l=7,Y"}, {zSET,"7,Y"}, {zSET,"a=7,Y"} }; -static const z80dasm mnemonic_cb[256] = { +const z180_disassembler::z80dasm z180_disassembler::mnemonic_cb[256] = { {zRLC,"b"}, {zRLC,"c"}, {zRLC,"d"}, {zRLC,"e"}, {zRLC,"h"}, {zRLC,"l"}, {zRLC,"(hl)"}, {zRLC,"a"}, {zRRC,"b"}, {zRRC,"c"}, {zRRC,"d"}, {zRRC,"e"}, @@ -176,7 +157,7 @@ static const z80dasm mnemonic_cb[256] = { {zSET,"7,h"}, {zSET,"7,l"}, {zSET,"7,(hl)"},{zSET,"7,a"} }; -static const z80dasm mnemonic_ed[256]= { +const z180_disassembler::z80dasm z180_disassembler::mnemonic_ed[256]= { {zIN0,"b,(B)"}, {zOUT0,"(B),b"},{zDB,"?"}, {zDB,"?"}, {zTST,"b"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zIN0,"c,(B)"}, {zOUT0,"(B),c"},{zDB,"?"}, {zDB,"?"}, @@ -243,7 +224,7 @@ static const z80dasm mnemonic_ed[256]= { {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"} }; -static const z80dasm mnemonic_xx[256]= { +const z180_disassembler::z80dasm z180_disassembler::mnemonic_xx[256]= { {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zADD,"I,bc"}, {zDB,"?"}, {zDB,"?"}, @@ -310,7 +291,7 @@ static const z80dasm mnemonic_xx[256]= { {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"} }; -static const z80dasm mnemonic_main[256]= { +const z180_disassembler::z80dasm z180_disassembler::mnemonic_main[256]= { {zNOP,nullptr}, {zLD,"bc,N"}, {zLD,"(bc),a"}, {zINC,"bc"}, {zINC,"b"}, {zDEC,"b"}, {zLD,"b,B"}, {zRLCA,nullptr}, {zEX,"af,af'"}, {zADD,"hl,bc"}, {zLD,"a,(bc)"}, {zDEC,"bc"}, @@ -377,12 +358,12 @@ static const z80dasm mnemonic_main[256]= { {zCALL,"m,A"}, {zDB,"fd"}, {zCP,"B"}, {zRST,"V"} }; -static char sign(int8_t offset) +char z180_disassembler::sign(int8_t offset) { return (offset < 0)? '-':'+'; } -static int offs(int8_t offset) +int z180_disassembler::offs(int8_t offset) { if (offset < 0) return -offset; return offset; @@ -391,49 +372,48 @@ static int offs(int8_t offset) /**************************************************************************** * Disassemble opcode at PC and return number of bytes it takes ****************************************************************************/ -CPU_DISASSEMBLE(z180) +offs_t z180_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { const z80dasm *d; const char *src, *ixy; - unsigned PC = pc; int8_t offset = 0; uint8_t op, op1 = 0; uint16_t ea; - int pos = 0; + offs_t pos = pc; uint32_t flags = 0; ixy = "oops!!"; - op = oprom[pos++]; + op = opcodes.r8(pos++); switch (op) { case 0xcb: - op = oprom[pos++]; + op = opcodes.r8(pos++); d = &mnemonic_cb[op]; break; case 0xed: - op1 = oprom[pos++]; + op1 = opcodes.r8(pos++); d = &mnemonic_ed[op1]; break; case 0xdd: ixy = "ix"; - op1 = oprom[pos++]; + op1 = opcodes.r8(pos++); if( op1 == 0xcb ) { - offset = (int8_t) opram[pos++]; - op1 = opram[pos++]; /* fourth byte from opbase.ram! */ + offset = (int8_t) params.r8(pos++); + op1 = params.r8(pos++); /* fourth byte from opbase.ram! */ d = &mnemonic_xx_cb[op1]; } else d = &mnemonic_xx[op1]; break; case 0xfd: ixy = "iy"; - op1 = oprom[pos++]; + op1 = opcodes.r8(pos++); if( op1 == 0xcb ) { - offset = (int8_t) opram[pos++]; - op1 = opram[pos++]; /* fourth byte from opbase.ram! */ + offset = (int8_t) params.r8(pos++); + op1 = params.r8(pos++); /* fourth byte from opbase.ram! */ d = &mnemonic_xx_cb[op1]; } else d = &mnemonic_xx[op1]; @@ -455,25 +435,25 @@ CPU_DISASSEMBLE(z180) util::stream_format(stream, "$%02x,$%02x", op, op1); break; case 'A': - ea = opram[pos] + (opram[pos+1] << 8); + ea = params.r16(pos); pos += 2; util::stream_format(stream, "$%04X", ea); break; case 'B': /* Byte op arg */ - ea = opram[pos++]; + ea = params.r8(pos++); util::stream_format(stream, "$%02X", ea); break; case 'N': /* Immediate 16 bit */ - ea = opram[pos] + ( opram[pos+1] << 8 ); + ea = params.r16(pos); pos += 2; util::stream_format(stream, "$%04X", ea); break; case 'O': /* Offset relative to PC */ - offset = (int8_t) opram[pos++]; - util::stream_format(stream, "$%05X", PC + offset + 2); + offset = (int8_t) params.r8(pos++); + util::stream_format(stream, "$%05X", pc + offset + 2); break; case 'P': /* Port number */ - ea = opram[pos++]; + ea = params.r8(pos++); util::stream_format(stream, "$%02X", ea); break; case 'V': /* Restart vector */ @@ -481,12 +461,12 @@ CPU_DISASSEMBLE(z180) util::stream_format(stream, "$%02X", ea); break; case 'W': /* Memory address word */ - ea = opram[pos] + (opram[pos+1] << 8); + ea = params.r16(pos); pos += 2; util::stream_format(stream, "$%05X", ea); break; case 'X': - offset = (int8_t) opram[pos++]; + offset = (int8_t) params.r8(pos++); case 'Y': util::stream_format(stream,"(%s%c$%02x)", ixy, sign(offset), offs(offset)); break; @@ -507,9 +487,14 @@ CPU_DISASSEMBLE(z180) if (d->mnemonic == zCALL || d->mnemonic == zCPDR || d->mnemonic == zCPIR || d->mnemonic == zDJNZ || d->mnemonic == zHLT || d->mnemonic == zINDR || d->mnemonic == zINIR || d->mnemonic == zLDDR || d->mnemonic == zLDIR || d->mnemonic == zOTDR || d->mnemonic == zOTIR || d->mnemonic == zRST) - flags = DASMFLAG_STEP_OVER; + flags = STEP_OVER; else if (d->mnemonic == zRETN || d->mnemonic == zRET || d->mnemonic == zRETI) - flags = DASMFLAG_STEP_OUT; + flags = STEP_OUT; - return pos | flags | DASMFLAG_SUPPORTED; + return (pos - pc) | flags | SUPPORTED; +} + +u32 z180_disassembler::opcode_alignment() const +{ + return 1; } diff --git a/src/devices/cpu/z180/z180dasm.h b/src/devices/cpu/z180/z180dasm.h new file mode 100644 index 00000000000..a13c7d92fe1 --- /dev/null +++ b/src/devices/cpu/z180/z180dasm.h @@ -0,0 +1,54 @@ +// license:BSD-3-Clause +// copyright-holders:Juergen Buchmueller +/***************************************************************************** + * + * z180dasm.c + * Portable Z8x180 disassembler + * + *****************************************************************************/ + +#ifndef MAME_CPU_Z180_Z180DASM_H +#define MAME_CPU_Z180_Z180DASM_H + +#pragma once + +class z180_disassembler : public util::disasm_interface +{ +public: + z180_disassembler() = default; + virtual ~z180_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + struct z80dasm { + uint8_t mnemonic; + const char *arguments; + }; + + enum e_mnemonics { + zADC ,zADD ,zAND ,zBIT ,zCALL ,zCCF ,zCP ,zCPD , + zCPDR ,zCPI ,zCPIR ,zCPL ,zDAA ,zDB ,zDEC ,zDI , + zDJNZ ,zEI ,zEX ,zEXX ,zHLT ,zIM ,zIN ,zIN0 , + zINC ,zIND ,zINDR ,zINI ,zINIR ,zJP ,zJR ,zLD , + zLDD ,zLDDR ,zLDI ,zLDIR ,zMLT ,zNEG ,zNOP ,zOR , + zOTDM ,zOTDMR ,zOTDR ,zOTIM ,zOTIMR ,zOTIR ,zOUT ,zOUT0 , + zOUTD ,zOUTI ,zPOP ,zPUSH ,zRES ,zRET ,zRETI ,zRETN , + zRL ,zRLA ,zRLC ,zRLCA ,zRLD ,zRR ,zRRA ,zRRC , + zRRCA ,zRRD ,zRST ,zSBC ,zSCF ,zSET ,zSLA ,zSLL , + zSLP ,zSRA ,zSRL ,zSUB ,zTST ,zTSTIO ,zXOR + }; + + static const char *const s_mnemonic[]; + static const z80dasm mnemonic_xx_cb[256]; + static const z80dasm mnemonic_cb[256]; + static const z80dasm mnemonic_ed[256]; + static const z80dasm mnemonic_xx[256]; + static const z80dasm mnemonic_main[256]; + + static char sign(int8_t offset); + static int offs(int8_t offset); +}; + +#endif diff --git a/src/devices/cpu/z8/z8.cpp b/src/devices/cpu/z8/z8.cpp index 5ef2c5c505d..8a81643a4e2 100644 --- a/src/devices/cpu/z8/z8.cpp +++ b/src/devices/cpu/z8/z8.cpp @@ -22,6 +22,7 @@ #include "emu.h" #include "z8.h" +#include "z8dasm.h" #include "debugger.h" /*************************************************************************** @@ -207,13 +208,12 @@ z8681_device::z8681_device(const machine_config &mconfig, const char *tag, devic { } - -offs_t z8_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +util::disasm_interface *z8_device::create_disassembler() { - extern CPU_DISASSEMBLE( z8 ); - return CPU_DISASSEMBLE_NAME(z8)(this, stream, pc, oprom, opram, options); + return new z8_disassembler; } + device_memory_interface::space_config_vector z8_device::memory_space_config() const { // Separate data space is optional diff --git a/src/devices/cpu/z8/z8.h b/src/devices/cpu/z8/z8.h index b7064c82ae7..c5aad5f4e6f 100644 --- a/src/devices/cpu/z8/z8.h +++ b/src/devices/cpu/z8/z8.h @@ -91,9 +91,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 3; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; DECLARE_ADDRESS_MAP(program_2kb, 8); DECLARE_ADDRESS_MAP(program_4kb, 8); diff --git a/src/devices/cpu/z8/z8dasm.cpp b/src/devices/cpu/z8/z8dasm.cpp index 8cd29344f2a..a832dab8fe9 100644 --- a/src/devices/cpu/z8/z8dasm.cpp +++ b/src/devices/cpu/z8/z8dasm.cpp @@ -1,14 +1,14 @@ // license:BSD-3-Clause // copyright-holders:Curt Coder + #include "emu.h" -#include "debugger.h" -#include "z8.h" +#include "z8dasm.h" /*************************************************************************** CONSTANTS ***************************************************************************/ -static const char *const REGISTER_NAME[256] = +const char *const z8_disassembler::REGISTER_NAME[256] = { "P0", "P1", "P2", "P3", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", "", @@ -28,7 +28,7 @@ static const char *const REGISTER_NAME[256] = "SIO", "TMR", "T1", "PRE1", "T0", "PRE0", "P2M", "P3M", "P01M", "IPR", "IRQ", "IMR", "FLAGS", "RP", "SPH", "SPL" }; -static const char *const CONDITION_CODE[16] = +const char *const z8_disassembler::CONDITION_CODE[16] = { "F", "LT", "LE", "ULE", "OV", "MI", "Z", "C", "", "GE", "GT", "UGT", "NOV", "PL", "NZ", "NC" @@ -50,8 +50,8 @@ static const char *const CONDITION_CODE[16] = #define DA "%04Xh" #define RA "%04Xh" -#define B0 oprom[0] -#define B1 oprom[1] +#define B0 opcodes.r8(pos) +#define B1 opcodes.r8(pos+1) #define B0H (B0 >> 4) #define B0L (B0 & 0x0f) #define OPH (opcode >> 4) @@ -74,19 +74,24 @@ static const char *const CONDITION_CODE[16] = #define illegal util::stream_format(stream, "Illegal") #define mnemonic(_mnemonic) util::stream_format(stream, "%-5s", _mnemonic) -#define bytes(_count) oprom += (_count - 1) -#define step_over flags = DASMFLAG_STEP_OVER -#define step_out flags = DASMFLAG_STEP_OUT +#define bytes(_count) pos += (_count - 1) +#define step_over flags = STEP_OVER +#define step_out flags = STEP_OUT /*************************************************************************** DISASSEMBLER ***************************************************************************/ -CPU_DISASSEMBLE(z8) +u32 z8_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t z8_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - const uint8_t *startrom = oprom; + offs_t pos = pc; uint32_t flags = 0; - uint8_t opcode = *oprom++; + uint8_t opcode = opcodes.r8(pos++); int argc = 0; switch (pc) @@ -97,7 +102,7 @@ CPU_DISASSEMBLE(z8) case 0x0006: case 0x0008: case 0x000a: - util::stream_format(stream, "IRQ%u Vector %04Xh", pc / 2, opcode << 8 | *oprom++); break; + util::stream_format(stream, "IRQ%u Vector %04Xh", pc / 2, opcode << 8 | opcodes.r8(pos++)); break; default: switch (opcode) { @@ -375,5 +380,5 @@ CPU_DISASSEMBLE(z8) } } - return (oprom - startrom) | flags | DASMFLAG_SUPPORTED; + return (pos - pc) | flags | SUPPORTED; } diff --git a/src/devices/cpu/z8/z8dasm.h b/src/devices/cpu/z8/z8dasm.h new file mode 100644 index 00000000000..653b6e0cb26 --- /dev/null +++ b/src/devices/cpu/z8/z8dasm.h @@ -0,0 +1,24 @@ +// license:BSD-3-Clause +// copyright-holders:Curt Coder + +#ifndef MAME_CPU_Z8_Z8DASM_H +#define MAME_CPU_Z8_Z8DASM_H + +#pragma once + +class z8_disassembler : public util::disasm_interface +{ +public: + z8_disassembler() = default; + virtual ~z8_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + static const char *const REGISTER_NAME[256]; + static const char *const CONDITION_CODE[16]; + +}; + +#endif diff --git a/src/devices/cpu/z80/z80.cpp b/src/devices/cpu/z80/z80.cpp index bae1c4f9398..64f6cebfd11 100644 --- a/src/devices/cpu/z80/z80.cpp +++ b/src/devices/cpu/z80/z80.cpp @@ -110,6 +110,7 @@ #include "emu.h" #include "debugger.h" #include "z80.h" +#include "z80dasm.h" #define VERBOSE 0 @@ -3667,14 +3668,13 @@ void z80_device::state_string_export(const device_state_entry &entry, std::strin } //------------------------------------------------- -// disasm_disassemble - call the disassembly +// disassemble - call the disassembly // helper function //------------------------------------------------- -offs_t z80_device::disasm_disassemble( std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options ) +util::disasm_interface *z80_device::create_disassembler() { - extern CPU_DISASSEMBLE( z80 ); - return CPU_DISASSEMBLE_NAME(z80)(this, stream, pc, oprom, opram, options); + return new z80_disassembler; } diff --git a/src/devices/cpu/z80/z80.h b/src/devices/cpu/z80/z80.h index dba8c294040..2ad3f865d7e 100644 --- a/src/devices/cpu/z80/z80.h +++ b/src/devices/cpu/z80/z80.h @@ -70,9 +70,7 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; #undef PROTOTYPES #define PROTOTYPES(prefix) \ diff --git a/src/devices/cpu/z80/z80dasm.cpp b/src/devices/cpu/z80/z80dasm.cpp index 2af88954943..b59b3a38eb6 100644 --- a/src/devices/cpu/z80/z80dasm.cpp +++ b/src/devices/cpu/z80/z80dasm.cpp @@ -9,20 +9,8 @@ #include "emu.h" #include "debugger.h" -#include "z80.h" +#include "z80dasm.h" -enum e_mnemonics -{ - zADC ,zADD ,zAND ,zBIT ,zCALL ,zCCF ,zCP ,zCPD , - zCPDR ,zCPI ,zCPIR ,zCPL ,zDAA ,zDB ,zDEC ,zDI , - zDJNZ ,zEI ,zEX ,zEXX ,zHLT ,zIM ,zIN ,zINC , - zIND ,zINDR ,zINI ,zINIR ,zJP ,zJR ,zLD ,zLDD , - zLDDR ,zLDI ,zLDIR ,zNEG ,zNOP ,zOR ,zOTDR ,zOTIR , - zOUT ,zOUTD ,zOUTI ,zPOP ,zPUSH ,zRES ,zRET ,zRETI , - zRETN ,zRL ,zRLA ,zRLC ,zRLCA ,zRLD ,zRR ,zRRA , - zRRC ,zRRCA ,zRRD ,zRST ,zSBC ,zSCF ,zSET ,zSLA , - zSLL ,zSRA ,zSRL ,zSUB ,zXOR -}; static const char *const s_mnemonic[] = { @@ -37,29 +25,20 @@ static const char *const s_mnemonic[] = "sll" ,"sra" ,"srl" ,"sub" ,"xor " }; -#define _OVER DASMFLAG_STEP_OVER -#define _OUT DASMFLAG_STEP_OUT - -static const uint32_t s_flags[] = -{ - 0 ,0 ,0 ,0 ,_OVER,0 ,0 ,0 , - _OVER,0 ,_OVER,0 ,0 ,0 ,0 ,0 , - _OVER,0 ,0 ,0 ,_OVER,0 ,0 ,0 , - 0 ,_OVER,0 ,_OVER,0 ,0 ,0 ,0 , - _OVER,0 ,_OVER,0 ,0 ,0 ,_OVER,_OVER, - 0 ,0 ,0 ,0 ,0 ,0 ,_OUT ,_OUT , - _OUT ,0 ,0 ,0 ,0 ,0 ,0 ,0 , - 0 ,0 ,0 ,_OVER,0 ,0 ,0 ,0 , - 0 ,0 ,0 ,0 ,0 -}; - -struct z80dasm +const u32 z80_disassembler::s_flags[] = { - uint8_t mnemonic; - const char *arguments; + 0 ,0 ,0 ,0 ,STEP_OVER,0 ,0 ,0 , + STEP_OVER,0 ,STEP_OVER,0 ,0 ,0 ,0 ,0 , + STEP_OVER,0 ,0 ,0 ,STEP_OVER,0 ,0 ,0 , + 0 ,STEP_OVER,0 ,STEP_OVER,0 ,0 ,0 ,0 , + STEP_OVER,0 ,STEP_OVER,0 ,0 ,0 ,STEP_OVER,STEP_OVER, + 0 ,0 ,0 ,0 ,0 ,0 ,STEP_OUT ,STEP_OUT , + STEP_OUT ,0 ,0 ,0 ,0 ,0 ,0 ,0 , + 0 ,0 ,0 ,STEP_OVER,0 ,0 ,0 ,0 , + 0 ,0 ,0 ,0 ,0 }; -static const z80dasm mnemonic_xx_cb[256] = +const z80_disassembler::z80dasm z80_disassembler::mnemonic_xx_cb[256] = { {zRLC,"b=Y"}, {zRLC,"c=Y"}, {zRLC,"d=Y"}, {zRLC,"e=Y"}, {zRLC,"h=Y"}, {zRLC,"l=Y"}, {zRLC,"Y"}, {zRLC,"a=Y"}, @@ -127,7 +106,7 @@ static const z80dasm mnemonic_xx_cb[256] = {zSET,"h=7,Y"}, {zSET,"l=7,Y"}, {zSET,"7,Y"}, {zSET,"a=7,Y"} }; -static const z80dasm mnemonic_cb[256] = +const z80_disassembler::z80dasm z80_disassembler::mnemonic_cb[256] = { {zRLC,"b"}, {zRLC,"c"}, {zRLC,"d"}, {zRLC,"e"}, {zRLC,"h"}, {zRLC,"l"}, {zRLC,"(hl)"}, {zRLC,"a"}, @@ -195,7 +174,7 @@ static const z80dasm mnemonic_cb[256] = {zSET,"7,h"}, {zSET,"7,l"}, {zSET,"7,(hl)"},{zSET,"7,a"} }; -static const z80dasm mnemonic_ed[256] = +const z80_disassembler::z80dasm z80_disassembler::mnemonic_ed[256] = { {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, @@ -214,21 +193,21 @@ static const z80dasm mnemonic_ed[256] = {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zIN,"b,(c)"}, {zOUT,"(c),b"}, {zSBC,"hl,bc"}, {zLD,"(W),bc"}, - {zNEG,nullptr}, {zRETN,nullptr}, {zIM,"0"}, {zLD,"i,a"}, + {zNEG,nullptr}, {zRETN,nullptr},{zIM,"0"}, {zLD,"i,a"}, {zIN,"c,(c)"}, {zOUT,"(c),c"}, {zADC,"hl,bc"}, {zLD,"bc,(W)"}, - {zNEG,"*"}, {zRETI,nullptr}, {zIM,"0"}, {zLD,"r,a"}, + {zNEG,"*"}, {zRETI,nullptr},{zIM,"0"}, {zLD,"r,a"}, {zIN,"d,(c)"}, {zOUT,"(c),d"}, {zSBC,"hl,de"}, {zLD,"(W),de"}, - {zNEG,"*"}, {zRETN,nullptr}, {zIM,"1"}, {zLD,"a,i"}, + {zNEG,"*"}, {zRETN,nullptr},{zIM,"1"}, {zLD,"a,i"}, {zIN,"e,(c)"}, {zOUT,"(c),e"}, {zADC,"hl,de"}, {zLD,"de,(W)"}, - {zNEG,"*"}, {zRETI,nullptr}, {zIM,"2"}, {zLD,"a,r"}, + {zNEG,"*"}, {zRETI,nullptr},{zIM,"2"}, {zLD,"a,r"}, {zIN,"h,(c)"}, {zOUT,"(c),h"}, {zSBC,"hl,hl"}, {zLD,"(W),hl"}, - {zNEG,"*"}, {zRETN,nullptr}, {zIM,"0"}, {zRRD,"(hl)"}, + {zNEG,"*"}, {zRETN,nullptr},{zIM,"0"}, {zRRD,"(hl)"}, {zIN,"l,(c)"}, {zOUT,"(c),l"}, {zADC,"hl,hl"}, {zLD,"hl,(W)"}, - {zNEG,"*"}, {zRETI,nullptr}, {zIM,"0"}, {zRLD,"(hl)"}, + {zNEG,"*"}, {zRETI,nullptr},{zIM,"0"}, {zRLD,"(hl)"}, {zIN,"0,(c)"}, {zOUT,"(c),0"}, {zSBC,"hl,sp"}, {zLD,"(W),sp"}, - {zNEG,"*"}, {zRETN,nullptr}, {zIM,"1"}, {zDB,"?"}, + {zNEG,"*"}, {zRETN,nullptr},{zIM,"1"}, {zDB,"?"}, {zIN,"a,(c)"}, {zOUT,"(c),a"}, {zADC,"hl,sp"}, {zLD,"sp,(W)"}, - {zNEG,"*"}, {zRETI,nullptr}, {zIM,"2"}, {zDB,"?"}, + {zNEG,"*"}, {zRETI,nullptr},{zIM,"2"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, @@ -263,7 +242,7 @@ static const z80dasm mnemonic_ed[256] = {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"} }; -static const z80dasm mnemonic_xx[256] = +const z80_disassembler::z80dasm z80_disassembler::mnemonic_xx[256] = { {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, @@ -331,9 +310,9 @@ static const z80dasm mnemonic_xx[256] = {zDB,"?"}, {zDB,"?"}, {zDB,"?"}, {zDB,"?"} }; -static const z80dasm mnemonic_main[256] = +const z80_disassembler::z80dasm z80_disassembler::mnemonic_main[256] = { - {zNOP,nullptr}, {zLD,"bc,N"}, {zLD,"(bc),a"}, {zINC,"bc"}, + {zNOP,nullptr}, {zLD,"bc,N"}, {zLD,"(bc),a"}, {zINC,"bc"}, {zINC,"b"}, {zDEC,"b"}, {zLD,"b,B"}, {zRLCA,nullptr}, {zEX,"af,af'"}, {zADD,"hl,bc"}, {zLD,"a,(bc)"}, {zDEC,"bc"}, {zINC,"c"}, {zDEC,"c"}, {zLD,"c,B"}, {zRRCA,nullptr}, @@ -383,11 +362,11 @@ static const z80dasm mnemonic_main[256] = {zCP,"h"}, {zCP,"l"}, {zCP,"(hl)"}, {zCP,"a"}, {zRET,"nz"}, {zPOP,"bc"}, {zJP,"nz,A"}, {zJP,"A"}, {zCALL,"nz,A"}, {zPUSH,"bc"}, {zADD,"a,B"}, {zRST,"V"}, - {zRET,"z"}, {zRET,nullptr}, {zJP,"z,A"}, {zDB,"cb"}, + {zRET,"z"}, {zRET,nullptr}, {zJP,"z,A"}, {zDB,"cb"}, {zCALL,"z,A"}, {zCALL,"A"}, {zADC,"a,B"}, {zRST,"V"}, {zRET,"nc"}, {zPOP,"de"}, {zJP,"nc,A"}, {zOUT,"(P),a"}, {zCALL,"nc,A"}, {zPUSH,"de"}, {zSUB,"B"}, {zRST,"V"}, - {zRET,"c"}, {zEXX,nullptr}, {zJP,"c,A"}, {zIN,"a,(P)"}, + {zRET,"c"}, {zEXX,nullptr}, {zJP,"c,A"}, {zIN,"a,(P)"}, {zCALL,"c,A"}, {zDB,"dd"}, {zSBC,"a,B"}, {zRST,"V"}, {zRET,"po"}, {zPOP,"hl"}, {zJP,"po,A"}, {zEX,"(sp),hl"}, {zCALL,"po,A"}, {zPUSH,"hl"}, {zAND,"B"}, {zRST,"V"}, @@ -399,65 +378,73 @@ static const z80dasm mnemonic_main[256] = {zCALL,"m,A"}, {zDB,"fd"}, {zCP,"B"}, {zRST,"V"} }; -static char sign(int8_t offset) +char z80_disassembler::sign(s8 offset) { return (offset < 0)? '-':'+'; } -static int offs(int8_t offset) +u32 z80_disassembler::offs(s8 offset) { - if (offset < 0) return -offset; + if (offset < 0) + return -offset; return offset; } -/**************************************************************************** - * Disassemble opcode at PC and return number of bytes it takes - ****************************************************************************/ -CPU_DISASSEMBLE(z80) +z80_disassembler::z80_disassembler() { - const z80dasm *d; - const char *src, *ixy; - int8_t offset = 0; - uint8_t op, op1 = 0; - uint16_t ea; - int pos = 0; +} - ixy = "oops!!"; +u32 z80_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t z80_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + s8 offset = 0; - op = oprom[pos++]; + offs_t pos = pc; + std::string ixy = "oops!!"; + const z80dasm *d = nullptr; + u8 op = opcodes.r8(pos++); switch (op) { case 0xcb: - op = oprom[pos++]; + op = opcodes.r8(pos++); d = &mnemonic_cb[op]; break; case 0xed: - op1 = oprom[pos++]; - d = &mnemonic_ed[op1]; + d = &mnemonic_ed[opcodes.r8(pos++)]; break; case 0xdd: + { ixy = "ix"; - op1 = oprom[pos++]; + u8 op1 = opcodes.r8(pos++); if( op1 == 0xcb ) { - offset = (int8_t) opram[pos++]; - op1 = opram[pos++]; /* fourth byte from opbase.ram! */ + offset = params.r8(pos++); + op1 = params.r8(pos++); d = &mnemonic_xx_cb[op1]; } - else d = &mnemonic_xx[op1]; + else + d = &mnemonic_xx[op1]; break; + } case 0xfd: + { ixy = "iy"; - op1 = oprom[pos++]; + u8 op1 = opcodes.r8(pos++); if( op1 == 0xcb ) { - offset = (int8_t) opram[pos++]; - op1 = opram[pos++]; /* fourth byte from opbase.ram! */ + offset = params.r8(pos++); + op1 = params.r8(pos++); d = &mnemonic_xx_cb[op1]; } - else d = &mnemonic_xx[op1]; + else + d = &mnemonic_xx[op1]; break; + } default: d = &mnemonic_main[op]; break; @@ -466,47 +453,40 @@ CPU_DISASSEMBLE(z80) if( d->arguments ) { util::stream_format(stream, "%-4s ", s_mnemonic[d->mnemonic]); - src = d->arguments; + const char *src = d->arguments; while( *src ) { switch( *src ) { case '?': /* illegal opcode */ - util::stream_format(stream, "$%02x,$%02x", op, op1 ); + util::stream_format(stream, "$%02x", op ); break; case 'A': - ea = opram[pos+0] + ( opram[pos+1] << 8 ); + util::stream_format(stream, "$%04X", params.r16(pos) ); pos += 2; - util::stream_format(stream, "$%04X", ea ); break; case 'B': /* Byte op arg */ - ea = opram[pos++]; - util::stream_format(stream, "$%02X", ea ); + util::stream_format(stream, "$%02X", params.r8(pos++) ); break; case 'N': /* Immediate 16 bit */ - ea = opram[pos+0] + ( opram[pos+1] << 8 ); + util::stream_format(stream, "$%04X", params.r16(pos) ); pos += 2; - util::stream_format(stream, "$%04X", ea ); break; case 'O': /* Offset relative to PC */ - offset = (int8_t) opram[pos++]; - util::stream_format(stream, "$%04X", (pc + offset + 2) & 0xffff); + util::stream_format(stream, "$%04X", (pc + s8(params.r8(pos++)) + 2) & 0xffff); break; case 'P': /* Port number */ - ea = opram[pos++]; - util::stream_format(stream, "$%02X", ea ); + util::stream_format(stream, "$%02X", params.r8(pos++) ); break; case 'V': /* Restart vector */ - ea = op & 0x38; - util::stream_format(stream, "$%02X", ea ); + util::stream_format(stream, "$%02X", op & 0x38 ); break; case 'W': /* Memory address word */ - ea = opram[pos+0] + ( opram[pos+1] << 8 ); + util::stream_format(stream, "$%04X", params.r16(pos) ); pos += 2; - util::stream_format(stream, "$%04X", ea ); break; case 'X': - offset = (int8_t) opram[pos++]; + offset = params.r8(pos++); /* fall through */ case 'Y': util::stream_format(stream,"(%s%c$%02x)", ixy, sign(offset), offs(offset) ); @@ -525,5 +505,5 @@ CPU_DISASSEMBLE(z80) util::stream_format(stream, "%s", s_mnemonic[d->mnemonic]); } - return pos | s_flags[d->mnemonic] | DASMFLAG_SUPPORTED; + return (pos - pc) | s_flags[d->mnemonic] | SUPPORTED; } diff --git a/src/devices/cpu/z80/z80dasm.h b/src/devices/cpu/z80/z80dasm.h new file mode 100644 index 00000000000..774f4df89a8 --- /dev/null +++ b/src/devices/cpu/z80/z80dasm.h @@ -0,0 +1,56 @@ +// license:BSD-3-Clause +// copyright-holders:Juergen Buchmueller +/***************************************************************************** + * + * z80dasm.h + * Portable Z80 disassembler + * + *****************************************************************************/ + +#ifndef MAME_CPU_Z80_Z80DASM_H +#define MAME_CPU_Z80_Z80DASM_H + +#pragma once + +class z80_disassembler : public util::disasm_interface +{ +public: + z80_disassembler(); + virtual ~z80_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +protected: + struct z80dasm + { + u8 mnemonic; + const char *arguments; + }; + + enum e_mnemonics + { + zADC ,zADD ,zAND ,zBIT ,zCALL ,zCCF ,zCP ,zCPD , + zCPDR ,zCPI ,zCPIR ,zCPL ,zDAA ,zDB ,zDEC ,zDI , + zDJNZ ,zEI ,zEX ,zEXX ,zHLT ,zIM ,zIN ,zINC , + zIND ,zINDR ,zINI ,zINIR ,zJP ,zJR ,zLD ,zLDD , + zLDDR ,zLDI ,zLDIR ,zNEG ,zNOP ,zOR ,zOTDR ,zOTIR , + zOUT ,zOUTD ,zOUTI ,zPOP ,zPUSH ,zRES ,zRET ,zRETI , + zRETN ,zRL ,zRLA ,zRLC ,zRLCA ,zRLD ,zRR ,zRRA , + zRRC ,zRRCA ,zRRD ,zRST ,zSBC ,zSCF ,zSET ,zSLA , + zSLL ,zSRA ,zSRL ,zSUB ,zXOR + }; + + static inline char sign(s8 offset); + static inline u32 offs(s8 offset); + + static const u32 s_flags[]; + static const z80dasm mnemonic_xx_cb[256]; + static const z80dasm mnemonic_cb[256]; + static const z80dasm mnemonic_ed[256]; + static const z80dasm mnemonic_xx[256]; + static const z80dasm mnemonic_main[256]; + +}; + +#endif diff --git a/src/devices/cpu/z8000/8000dasm.cpp b/src/devices/cpu/z8000/8000dasm.cpp index a84d5d285e8..a258a25ed92 100644 --- a/src/devices/cpu/z8000/8000dasm.cpp +++ b/src/devices/cpu/z8000/8000dasm.cpp @@ -9,21 +9,543 @@ *****************************************************************************/ #include "emu.h" -#include "z8000.h" -#include "z8000cpu.h" +#include "8000dasm.h" -#include "debugger.h" -#include "debug/debugvw.h" -#include "debug/debugcon.h" +const z8000_disassembler::opcode z8000_disassembler::table[] = { + { 0x0000, 0xffff, 1, 1, ".word %#w0", 0 }, + { 0x0000, 0x000f, 1, 2, "addb %rb3,%#b3", 0 }, + { 0x0010, 0x00ff, 1, 1, "addb %rb3,@%rw2", 0 }, + { 0x0100, 0x010f, 1, 2, "add %rw3,%#w1", 0 }, + { 0x0110, 0x01ff, 1, 1, "add %rw3,@%rw2", 0 }, + { 0x0200, 0x020f, 1, 2, "subb %rb3,%#b3", 0 }, + { 0x0210, 0x02ff, 1, 1, "subb %rb3,@%rw2", 0 }, + { 0x0300, 0x030f, 1, 2, "sub %rw3,%#w1", 0 }, + { 0x0310, 0x03ff, 1, 1, "sub %rw3,@%rw2", 0 }, + { 0x0400, 0x040f, 1, 2, "orb %rb3,%#b3", 0 }, + { 0x0410, 0x04ff, 1, 1, "orb %rb3,@%rw2", 0 }, + { 0x0500, 0x050f, 1, 2, "or %rw3,%#w1", 0 }, + { 0x0510, 0x05ff, 1, 1, "or %rw3,@%rw2", 0 }, + { 0x0600, 0x060f, 1, 2, "andb %rb3,%#b3", 0 }, + { 0x0610, 0x06ff, 1, 1, "andb %rb3,@%rw2", 0 }, + { 0x0700, 0x070f, 1, 2, "and %rw3,%#w1", 0 }, + { 0x0710, 0x07ff, 1, 1, "and %rw3,@%rw2", 0 }, + { 0x0800, 0x080f, 1, 2, "xorb %rb3,%#b3", 0 }, + { 0x0810, 0x08ff, 1, 1, "xorb %rb3,@%rw2", 0 }, + { 0x0900, 0x090f, 1, 2, "xor %rw3,%#w1", 0 }, + { 0x0910, 0x09ff, 1, 1, "xor %rw3,@%rw2", 0 }, + { 0x0a00, 0x0a0f, 1, 2, "cpb %rb3,%#b3", 0 }, + { 0x0a10, 0x0aff, 1, 1, "cpb %rb3,@%rw2", 0 }, + { 0x0b00, 0x0b0f, 1, 2, "cp %rw3,%#w1", 0 }, + { 0x0b10, 0x0bff, 1, 1, "cp %rw3,@%rw2", 0 }, + { 0x0c10, 0x0cf0, 16, 1, "comb @%rw2", 0 }, + { 0x0c11, 0x0cf1, 16, 2, "cpb @%rw2,%#b3", 0 }, + { 0x0c12, 0x0cf2, 16, 1, "negb @%rw2", 0 }, + { 0x0c14, 0x0cf4, 16, 1, "testb @%rw2", 0 }, + { 0x0c15, 0x0cf5, 16, 2, "ldb @%rw2,%#b3", 0 }, + { 0x0c16, 0x0cf6, 16, 1, "tsetb @%rw2", 0 }, + { 0x0c18, 0x0cf8, 16, 1, "clrb @%rw2", 0 }, + { 0x0d10, 0x0df0, 16, 1, "com @%rw2", 0 }, + { 0x0d11, 0x0df1, 16, 2, "cp @%rw2,%#w1", 0 }, + { 0x0d12, 0x0df2, 16, 1, "neg @%rw2", 0 }, + { 0x0d14, 0x0df4, 16, 1, "test @%rw2", 0 }, + { 0x0d15, 0x0df5, 16, 2, "ld @%rw2,%#w1", 0 }, + { 0x0d16, 0x0df6, 16, 1, "tset @%rw2", 0 }, + { 0x0d18, 0x0df8, 16, 1, "clr @%rw2", 0 }, + { 0x0d19, 0x0df9, 16, 2, "push @%rw2,%#w1", 0 }, + { 0x0e00, 0x0eff, 1, 1, "ext0e %#b1", 0 }, + { 0x0f00, 0x0fff, 1, 1, "ext0f %#b1", 0 }, + { 0x1000, 0x100f, 1, 3, "cpl %rl3,%#l1", 0 }, + { 0x1010, 0x10ff, 1, 1, "cpl %rl3,@%rw2", 0 }, + { 0x1111, 0x11ff, 1, 1, "pushl @%rw2,@%rw3", 0 }, + { 0x1200, 0x120f, 1, 3, "subl %rl3,%#l1", 0 }, + { 0x1210, 0x12ff, 1, 1, "subl %rl3,@%rw2", 0 }, + { 0x1311, 0x13ff, 1, 1, "push @%rw2,@%rw3", 0 }, + { 0x1400, 0x140f, 1, 3, "ldl %rl3,%#l1", 0 }, + { 0x1410, 0x14ff, 1, 1, "ldl %rl3,@%rw2", 0 }, + { 0x1511, 0x15ff, 1, 1, "popl @%rw3,@%rw2", 0 }, + { 0x1600, 0x160f, 1, 3, "addl %rl3,%#l1", 0 }, + { 0x1610, 0x16ff, 1, 1, "addl %rl3,@%rw2", 0 }, + { 0x1711, 0x17ff, 1, 1, "pop @%rw3,@%rw2", 0 }, + { 0x1800, 0x180f, 1, 1, "multl %rq3,@%l#1", 0 }, + { 0x1810, 0x18ff, 1, 1, "multl %rq3,@%rw2", 0 }, + { 0x1900, 0x190f, 1, 2, "mult %rl3,%#w1", 0 }, + { 0x1910, 0x19ff, 1, 1, "mult %rl3,@%rw2", 0 }, + { 0x1a00, 0x1a0f, 1, 3, "divl %rq3,%#l1", 0 }, + { 0x1a10, 0x1aff, 1, 1, "divl %rq3,@%rw2", 0 }, + { 0x1b00, 0x1b0f, 1, 2, "div %rl3,%#w1", 0 }, + { 0x1b10, 0x1bff, 1, 1, "div %rl3,@%rw2", 0 }, + { 0x1c11, 0x1cf1, 16, 2, "ldm %rw5,@%rw2,#%n", 0 }, + { 0x1c18, 0x1cf8, 16, 1, "testl @%rw2", 0 }, + { 0x1c19, 0x1cf9, 16, 2, "ldm @%rw2,%rw5,#%n", 0 }, + { 0x1d10, 0x1dff, 1, 1, "ldl @%rw2,%rl3", 0 }, + { 0x1e10, 0x1eff, 1, 1, "jp %c3,@%rl2", 0 }, + { 0x1f10, 0x1ff0, 16, 1, "call %rw2", STEP_OVER }, + { 0x2000, 0x200f, 1, 2, "ldb %rb3,%#b3", 0 }, + { 0x2010, 0x20ff, 1, 1, "ldb %rb3,@%rw2", 0 }, + { 0x2100, 0x210f, 1, 2, "ld %rw3,%#w1", 0 }, + { 0x2110, 0x21ff, 1, 1, "ld %rw3,@%rw2", 0 }, + { 0x2200, 0x220f, 1, 2, "resb %rb5,%rw3", 0 }, + { 0x2210, 0x22ff, 1, 1, "resb @%rw2,%3", 0 }, + { 0x2300, 0x230f, 1, 2, "res %rw5,%rw3", 0 }, + { 0x2310, 0x23ff, 1, 1, "res @%rw2,%3", 0 }, + { 0x2400, 0x240f, 1, 2, "setb %rb5,%rw3", 0 }, + { 0x2410, 0x24ff, 1, 1, "setb @%rw2,%3", 0 }, + { 0x2500, 0x250f, 1, 2, "set %rw5,%rw3", 0 }, + { 0x2510, 0x25ff, 1, 1, "set @%rw2,%3", 0 }, + { 0x2600, 0x260f, 1, 2, "bitb %rb5,%rw3", 0 }, + { 0x2610, 0x26ff, 1, 1, "bitb @%rw2,%3", 0 }, + { 0x2700, 0x270f, 1, 2, "bit %rw5,%rw3", 0 }, + { 0x2710, 0x27ff, 1, 1, "bit @%rw2,%3", 0 }, + { 0x2810, 0x28ff, 1, 1, "incb @%rw2,%+3", 0 }, + { 0x2910, 0x29ff, 1, 1, "inc @%rw2,%+3", 0 }, + { 0x2a10, 0x2aff, 1, 1, "decb @%rw2,%+3", 0 }, + { 0x2b10, 0x2bff, 1, 1, "dec @%rw2,%+3", 0 }, + { 0x2c10, 0x2cff, 1, 1, "exb %rb3,@%rw2", 0 }, + { 0x2d10, 0x2dff, 1, 1, "ex %rw3,@%rw2", 0 }, + { 0x2e10, 0x2eff, 1, 1, "ldb @%rw2,%rb3", 0 }, + { 0x2f10, 0x2fff, 1, 1, "ld @%rw2,%rw3", 0 }, + { 0x3000, 0x300f, 1, 2, "ldrb %rb3,%p1", 0 }, + { 0x3010, 0x30ff, 1, 2, "ldb %rb3,%rw2(%#w1)", 0 }, + { 0x3100, 0x310f, 1, 2, "ldr %rw3,%p1", 0 }, + { 0x3110, 0x31ff, 1, 2, "ld %rw3,%rw2(%#w1)", 0 }, + { 0x3200, 0x320f, 1, 2, "ldrb %p1,%rb3", 0 }, + { 0x3210, 0x32ff, 1, 2, "ldb %rw2(%#w1),%rb3", 0 }, + { 0x3300, 0x330f, 1, 2, "ldr %p1,%rw3", 0 }, + { 0x3310, 0x33ff, 1, 2, "ld %rw2(%#w1),%rw3", 0 }, + { 0x3400, 0x340f, 1, 2, "ldar p%rw3,%p1", 0 }, + { 0x3410, 0x34ff, 1, 2, "lda p%rw3,%rw2(%#w1)", 0 }, + { 0x3500, 0x350f, 1, 2, "ldrl %rl3,%p1", 0 }, + { 0x3510, 0x35ff, 1, 2, "ldl %rl3,%rw2(%#w1)", 0 }, + { 0x3600, 0x3600, 1, 1, "bpt", 0 }, + { 0x3601, 0x36ff, 1, 1, "rsvd36", 0 }, + { 0x3700, 0x370f, 1, 2, "ldrl %p1,%rl3", 0 }, + { 0x3710, 0x37ff, 1, 2, "ldl %rw2(%#w1),%rl3", 0 }, + { 0x3800, 0x38ff, 1, 1, "rsvd38", 0 }, + { 0x3910, 0x39f0, 16, 1, "ldps @%rw2", 0 }, + { 0x3a00, 0x3af0, 16, 2, "%R @%rw6,@%rw2,%rw5", 0 }, + { 0x3a01, 0x3af1, 16, 2, "%R @%rw6,@%rw2,%rw5", 0 }, + { 0x3a02, 0x3af2, 16, 2, "%R @%rw6,@%rw2,%rw5", 0 }, + { 0x3a03, 0x3af3, 16, 2, "%R @%rw6,@%rw2,%rw5", 0 }, + { 0x3a04, 0x3af4, 16, 2, "%R %rb2,%#w1", 0 }, + { 0x3a05, 0x3af5, 16, 2, "%R %rb2,%#w1", 0 }, + { 0x3a06, 0x3af6, 16, 2, "%R %#w1,%rb2", 0 }, + { 0x3a07, 0x3af7, 16, 2, "%R %#w1,%rb2", 0 }, + { 0x3a08, 0x3af8, 16, 2, "%R @%rw6,@%rw2,%rw5", 0 }, + { 0x3a09, 0x3af9, 16, 2, "%R @%rw6,@%rw2,%rw5", 0 }, + { 0x3a0a, 0x3afa, 16, 2, "%R @%rw6,@%rw2,%rw5", 0 }, + { 0x3a0b, 0x3afb, 16, 2, "%R @%rw6,@%rw2,%rw5", 0 }, + { 0x3b00, 0x3bf0, 16, 2, "%R @%rw6,@%rw2,%rw5", 0 }, + { 0x3b01, 0x3bf1, 16, 2, "%R @%rw6,@%rw2,%rw5", 0 }, + { 0x3b02, 0x3bf2, 16, 2, "%R @%rw6,@%rw2,%rw5", 0 }, + { 0x3b03, 0x3bf3, 16, 2, "%R @%rw6,@%rw2,%rw5", 0 }, + { 0x3b04, 0x3bf4, 16, 2, "%R %rw2,%#w1", 0 }, + { 0x3b05, 0x3bf5, 16, 2, "%R %rw2,%#w1", 0 }, + { 0x3b06, 0x3bf6, 16, 2, "%R %#w1,%rw2", 0 }, + { 0x3b07, 0x3bf7, 16, 2, "%R %#w1,%rw2", 0 }, + { 0x3b08, 0x3bf8, 16, 2, "%R @%rw6,@%rw2,%rw5", 0 }, + { 0x3b09, 0x3bf9, 16, 2, "%R @%rw6,@%rw2,%rw5", 0 }, + { 0x3b0a, 0x3bfa, 16, 2, "%R @%rw6,@%rw2,%rb5", 0 }, + { 0x3b0b, 0x3bfb, 16, 2, "%R @%rw6,@%rw2,%rb5", 0 }, + { 0x3c00, 0x3cff, 1, 1, "inb %rb3,@%rw2", 0 }, + { 0x3d00, 0x3dff, 1, 1, "in %rw3,@%rw2", 0 }, + { 0x3e00, 0x3eff, 1, 1, "outb @%rw2,%rb3", 0 }, + { 0x3f00, 0x3fff, 1, 1, "out @%rw2,%rw3", 0 }, + { 0x4000, 0x400f, 1, 2, "addb %rb3,%a1", 0 }, + { 0x4010, 0x40ff, 1, 2, "addb %rb3,%a1(%rw2)", 0 }, + { 0x4100, 0x410f, 1, 2, "add %rw3,%a1", 0 }, + { 0x4110, 0x41ff, 1, 2, "add %rw3,%a1(%rw2)", 0 }, + { 0x4200, 0x420f, 1, 2, "subb %rb3,%a1", 0 }, + { 0x4210, 0x42ff, 1, 2, "subb %rb3,%a1(%rw2)", 0 }, + { 0x4300, 0x430f, 1, 2, "sub %rw3,%a1", 0 }, + { 0x4310, 0x43ff, 1, 2, "sub %rw3,%a1(%rw2)", 0 }, + { 0x4400, 0x440f, 1, 2, "orb %rb3,%a1", 0 }, + { 0x4410, 0x44ff, 1, 2, "orb %rb3,%a1(%rw2)", 0 }, + { 0x4500, 0x450f, 1, 2, "or %rw3,%a1", 0 }, + { 0x4510, 0x45ff, 1, 2, "or %rw3,%a1(%rw2)", 0 }, + { 0x4600, 0x460f, 1, 2, "andb %rb3,%a1", 0 }, + { 0x4610, 0x46ff, 1, 2, "andb %rb3,%a1(%rw2)", 0 }, + { 0x4700, 0x470f, 1, 2, "and %rw3,%a1", 0 }, + { 0x4710, 0x47ff, 1, 2, "and %rw3,%a1(%rw2)", 0 }, + { 0x4800, 0x480f, 1, 2, "xorb %rb3,%a1", 0 }, + { 0x4810, 0x48ff, 1, 2, "xorb %rb3,%a1(%rw2)", 0 }, + { 0x4900, 0x490f, 1, 2, "xor %rw3,%a1", 0 }, + { 0x4910, 0x49ff, 1, 2, "xor %rw3,%a1(%rw2)", 0 }, + { 0x4a00, 0x4a0f, 1, 2, "cpb %rb3,%a1", 0 }, + { 0x4a10, 0x4aff, 1, 2, "cpb %rb3,%a1(%rw2)", 0 }, + { 0x4b00, 0x4b0f, 1, 2, "cp %rw3,%a1", 0 }, + { 0x4b10, 0x4bff, 1, 2, "cp %rw3,%a1(%rw2)", 0 }, + { 0x4c00, 0x4c00, 1, 2, "comb %a1", 0 }, + { 0x4c01, 0x4c01, 1, 3, "cpb %a1,%#b3", 0 }, + { 0x4c02, 0x4c02, 1, 2, "negb %a1", 0 }, + { 0x4c04, 0x4c04, 1, 2, "testb %a1", 0 }, + { 0x4c05, 0x4c05, 1, 3, "ldb %a1,%#b3", 0 }, + { 0x4c06, 0x4c06, 1, 2, "tsetb %a1", 0 }, + { 0x4c08, 0x4c08, 1, 2, "clrb %a1", 0 }, + { 0x4c10, 0x4cf0, 16, 2, "comb %a1(%rw2)", 0 }, + { 0x4c11, 0x4cf1, 16, 3, "cpb %a1(%rw2),%#b3", 0 }, + { 0x4c12, 0x4cf2, 16, 2, "negb %a1(%rw2)", 0 }, + { 0x4c14, 0x4cf4, 16, 2, "testb %a1(%rw2)", 0 }, + { 0x4c15, 0x4cf5, 16, 3, "ldb %a1(%rw2),%#b3", 0 }, + { 0x4c16, 0x4cf6, 16, 2, "tsetb %a1(%rw2)", 0 }, + { 0x4c18, 0x4cf8, 16, 2, "clrb %a1(%rw2)", 0 }, + { 0x4d00, 0x4d00, 1, 2, "com %a1", 0 }, + { 0x4d01, 0x4d01, 1, 3, "cp %a1,%#w2", 0 }, + { 0x4d02, 0x4d02, 1, 2, "neg %a1", 0 }, + { 0x4d04, 0x4d04, 1, 2, "test %a1", 0 }, + { 0x4d05, 0x4d05, 1, 3, "ld %a1,%#w2", 0 }, + { 0x4d06, 0x4d06, 1, 2, "tset %a1", 0 }, + { 0x4d08, 0x4d08, 1, 2, "clr %a1", 0 }, + { 0x4d10, 0x4df0, 16, 2, "com %a1(%rw2)", 0 }, + { 0x4d11, 0x4df1, 16, 3, "cp %a1(%rw2),%#w2", 0 }, + { 0x4d12, 0x4df2, 16, 2, "neg %a1(%rw2)", 0 }, + { 0x4d14, 0x4df4, 16, 2, "test %a1(%rw2)", 0 }, + { 0x4d15, 0x4df5, 16, 3, "ld %a1(%rw2),%#w2", 0 }, + { 0x4d16, 0x4df6, 16, 2, "tset %a1(%rw2)", 0 }, + { 0x4d18, 0x4df8, 16, 2, "clr %a1(%rw2)", 0 }, + { 0x4e11, 0x4ef0, 16, 2, "ldb %a1(%rw2),%rb3", 0 }, + { 0x5000, 0x500f, 1, 2, "cpl %rl3,%a1", 0 }, + { 0x5010, 0x50ff, 1, 2, "cpl %rl3,%a1(%rw2)", 0 }, + { 0x5110, 0x51f0, 16, 2, "pushl @%rw2,%a1", 0 }, + { 0x5111, 0x51f1, 16, 2, "pushl @%rw2,%a1(%rw3)", 0 }, + { 0x5112, 0x51f2, 16, 2, "pushl @%rw2,%a1(%rw3)", 0 }, + { 0x5113, 0x51f3, 16, 2, "pushl @%rw2,%a1(%rw3)", 0 }, + { 0x5114, 0x51f4, 16, 2, "pushl @%rw2,%a1(%rw3)", 0 }, + { 0x5115, 0x51f5, 16, 2, "pushl @%rw2,%a1(%rw3)", 0 }, + { 0x5116, 0x51f6, 16, 2, "pushl @%rw2,%a1(%rw3)", 0 }, + { 0x5117, 0x51f7, 16, 2, "pushl @%rw2,%a1(%rw3)", 0 }, + { 0x5118, 0x51f8, 16, 2, "pushl @%rw2,%a1(%rw3)", 0 }, + { 0x5119, 0x51f9, 16, 2, "pushl @%rw2,%a1(%rw3)", 0 }, + { 0x511a, 0x51fa, 16, 2, "pushl @%rw2,%a1(%rw3)", 0 }, + { 0x511b, 0x51fb, 16, 2, "pushl @%rw2,%a1(%rw3)", 0 }, + { 0x511c, 0x51fc, 16, 2, "pushl @%rw2,%a1(%rw3)", 0 }, + { 0x511d, 0x51fd, 16, 2, "pushl @%rw2,%a1(%rw3)", 0 }, + { 0x511e, 0x51fe, 16, 2, "pushl @%rw2,%a1(%rw3)", 0 }, + { 0x511f, 0x51ff, 16, 2, "pushl @%rw2,%a1(%rw3)", 0 }, + { 0x5200, 0x520f, 1, 2, "subl %rl3,%a1", 0 }, + { 0x5210, 0x52ff, 1, 2, "subl %rl3,%a1(%rw2)", 0 }, + { 0x5310, 0x53f0, 16, 2, "push @%rw2,%a1", 0 }, + { 0x5311, 0x53f1, 16, 2, "push @%rw2,%a1(%rw3)", 0 }, + { 0x5312, 0x53f2, 16, 2, "push @%rw2,%a1(%rw3)", 0 }, + { 0x5313, 0x53f3, 16, 2, "push @%rw2,%a1(%rw3)", 0 }, + { 0x5314, 0x53f4, 16, 2, "push @%rw2,%a1(%rw3)", 0 }, + { 0x5315, 0x53f5, 16, 2, "push @%rw2,%a1(%rw3)", 0 }, + { 0x5316, 0x53f6, 16, 2, "push @%rw2,%a1(%rw3)", 0 }, + { 0x5317, 0x53f7, 16, 2, "push @%rw2,%a1(%rw3)", 0 }, + { 0x5318, 0x53f8, 16, 2, "push @%rw2,%a1(%rw3)", 0 }, + { 0x5319, 0x53f9, 16, 2, "push @%rw2,%a1(%rw3)", 0 }, + { 0x531a, 0x53fa, 16, 2, "push @%rw2,%a1(%rw3)", 0 }, + { 0x531b, 0x53fb, 16, 2, "push @%rw2,%a1(%rw3)", 0 }, + { 0x531c, 0x53fc, 16, 2, "push @%rw2,%a1(%rw3)", 0 }, + { 0x531d, 0x53fd, 16, 2, "push @%rw2,%a1(%rw3)", 0 }, + { 0x531e, 0x53fe, 16, 2, "push @%rw2,%a1(%rw3)", 0 }, + { 0x531f, 0x53ff, 16, 2, "push @%rw2,%a1(%rw3)", 0 }, + { 0x5400, 0x540f, 1, 2, "ldl %rl3,%a1", 0 }, + { 0x5410, 0x54ff, 1, 2, "ldl %rl3,%a1(%rw2)", 0 }, + { 0x5510, 0x55f0, 16, 2, "popl %a1,@%rw2", 0 }, + { 0x5511, 0x55f1, 16, 2, "popl %a1(%rw3),@%rw2", 0 }, + { 0x5512, 0x55f2, 16, 2, "popl %a1(%rw3),@%rw2", 0 }, + { 0x5513, 0x55f3, 16, 2, "popl %a1(%rw3),@%rw2", 0 }, + { 0x5514, 0x55f4, 16, 2, "popl %a1(%rw3),@%rw2", 0 }, + { 0x5515, 0x55f5, 16, 2, "popl %a1(%rw3),@%rw2", 0 }, + { 0x5516, 0x55f6, 16, 2, "popl %a1(%rw3),@%rw2", 0 }, + { 0x5517, 0x55f7, 16, 2, "popl %a1(%rw3),@%rw2", 0 }, + { 0x5518, 0x55f8, 16, 2, "popl %a1(%rw3),@%rw2", 0 }, + { 0x5519, 0x55f9, 16, 2, "popl %a1(%rw3),@%rw2", 0 }, + { 0x551a, 0x55fa, 16, 2, "popl %a1(%rw3),@%rw2", 0 }, + { 0x551b, 0x55fb, 16, 2, "popl %a1(%rw3),@%rw2", 0 }, + { 0x551c, 0x55fc, 16, 2, "popl %a1(%rw3),@%rw2", 0 }, + { 0x551d, 0x55fd, 16, 2, "popl %a1(%rw3),@%rw2", 0 }, + { 0x551e, 0x55fe, 16, 2, "popl %a1(%rw3),@%rw2", 0 }, + { 0x551f, 0x55ff, 16, 2, "popl %a1(%rw3),@%rw2", 0 }, + { 0x5600, 0x560f, 1, 2, "addl %rl3,%a1", 0 }, + { 0x5610, 0x56ff, 1, 2, "addl %rl3,%a1(%rw2)", 0 }, + { 0x5710, 0x57f0, 16, 2, "pop %a1,@%rw2", 0 }, + { 0x5711, 0x57f1, 16, 2, "pop %a1(%rw3),@%rw2", 0 }, + { 0x5712, 0x57f2, 16, 2, "pop %a1(%rw3),@%rw2", 0 }, + { 0x5713, 0x57f3, 16, 2, "pop %a1(%rw3),@%rw2", 0 }, + { 0x5714, 0x57f4, 16, 2, "pop %a1(%rw3),@%rw2", 0 }, + { 0x5715, 0x57f5, 16, 2, "pop %a1(%rw3),@%rw2", 0 }, + { 0x5716, 0x57f6, 16, 2, "pop %a1(%rw3),@%rw2", 0 }, + { 0x5717, 0x57f7, 16, 2, "pop %a1(%rw3),@%rw2", 0 }, + { 0x5718, 0x57f8, 16, 2, "pop %a1(%rw3),@%rw2", 0 }, + { 0x5719, 0x57f9, 16, 2, "pop %a1(%rw3),@%rw2", 0 }, + { 0x571a, 0x57fa, 16, 2, "pop %a1(%rw3),@%rw2", 0 }, + { 0x571b, 0x57fb, 16, 2, "pop %a1(%rw3),@%rw2", 0 }, + { 0x571c, 0x57fc, 16, 2, "pop %a1(%rw3),@%rw2", 0 }, + { 0x571d, 0x57fd, 16, 2, "pop %a1(%rw3),@%rw2", 0 }, + { 0x571e, 0x57fe, 16, 2, "pop %a1(%rw3),@%rw2", 0 }, + { 0x571f, 0x57ff, 16, 2, "pop %a1(%rw3),@%rw2", 0 }, + { 0x5800, 0x580f, 1, 2, "multl %rq3,%a1", 0 }, + { 0x5810, 0x58ff, 1, 2, "multl %rq3,%a1(%rw2)", 0 }, + { 0x5900, 0x590f, 1, 2, "mult %rl3,%a1", 0 }, + { 0x5910, 0x59ff, 1, 2, "mult %rl3,%a1(%rw2)", 0 }, + { 0x5a00, 0x5a0f, 1, 2, "divl %rq3,%a1", 0 }, + { 0x5a10, 0x5aff, 1, 2, "divl %rq3,%a1(%rw2)", 0 }, + { 0x5b00, 0x5b0f, 1, 2, "div %rl3,%a1", 0 }, + { 0x5b10, 0x5bff, 1, 2, "div %rl3,%a1(%rw2)", 0 }, + { 0x5c01, 0x5c01, 1, 3, "ldm %rw5,%a2,#%n", 0 }, + { 0x5c08, 0x5c08, 1, 2, "testl %a1", 0 }, + { 0x5c09, 0x5c09, 1, 3, "ldm %a2,%rw5,#%n", 0 }, + { 0x5c11, 0x5cf1, 16, 3, "ldm %rw5,%a2(%rw2),#%n", 0 }, + { 0x5c18, 0x5cf8, 16, 2, "testl %a1(%rw2)", 0 }, + { 0x5c19, 0x5cf9, 16, 3, "ldm %a2(%rw2),%rw5,#%n", 0 }, + { 0x5d00, 0x5d0f, 1, 2, "ldl %a1,%rl3", 0 }, + { 0x5d10, 0x5dff, 1, 2, "ldl %a1(%rw2),%rl3", 0 }, + { 0x5e00, 0x5e0f, 1, 2, "jp %c3,%a1", 0 }, + { 0x5e10, 0x5eff, 1, 2, "jp %c3,%a1(%rw2)", 0 }, + { 0x5f00, 0x5f00, 1, 2, "call %a1", STEP_OVER }, + { 0x5f10, 0x5ff0, 16, 2, "call %a1(%rw2)", STEP_OVER }, + { 0x6000, 0x600f, 1, 2, "ldb %rb3,%a1", 0 }, + { 0x6010, 0x60ff, 1, 2, "ldb %rb3,%a1(%rw2)", 0 }, + { 0x6100, 0x610f, 1, 2, "ld %rw3,%a1", 0 }, + { 0x6110, 0x61ff, 1, 2, "ld %rw3,%a1(%rw2)", 0 }, + { 0x6200, 0x620f, 1, 2, "resb %a1,%3", 0 }, + { 0x6210, 0x62ff, 1, 2, "resb %a1(%rw2),%3", 0 }, + { 0x6300, 0x630f, 1, 2, "res %a1,%3", 0 }, + { 0x6310, 0x63ff, 1, 2, "res %a1(%rw2),%3", 0 }, + { 0x6400, 0x640f, 1, 2, "setb %a1,%3", 0 }, + { 0x6410, 0x64ff, 1, 2, "setb %a1(%rw2),%3", 0 }, + { 0x6500, 0x650f, 1, 2, "set %a1,%3", 0 }, + { 0x6510, 0x65ff, 1, 2, "set %a1(%rw2),%3", 0 }, + { 0x6600, 0x660f, 1, 2, "bitb %a1,%3", 0 }, + { 0x6610, 0x66ff, 1, 2, "bitb %a1(%rw2),%3", 0 }, + { 0x6700, 0x670f, 1, 2, "bit %a1,%3", 0 }, + { 0x6710, 0x67ff, 1, 2, "bit %a1(%rw2),%3", 0 }, + { 0x6800, 0x680f, 1, 2, "incb %a1,%+3", 0 }, + { 0x6810, 0x68ff, 1, 2, "incb %a1(%rw2),%+3", 0 }, + { 0x6900, 0x690f, 1, 2, "inc %a1,%+3", 0 }, + { 0x6910, 0x69ff, 1, 2, "inc %a1(%rw2),%+3", 0 }, + { 0x6a00, 0x6a0f, 1, 2, "decb %a1,%+3", 0 }, + { 0x6a10, 0x6aff, 1, 2, "decb %a1(%rw2),%+3", 0 }, + { 0x6b00, 0x6b0f, 1, 2, "dec %a1,%+3", 0 }, + { 0x6b10, 0x6bff, 1, 2, "dec %a1(%rw2),%+3", 0 }, + { 0x6c00, 0x6c0f, 1, 2, "exb %rb3,%a1", 0 }, + { 0x6c10, 0x6cff, 1, 2, "exb %rb3,%a1(%rw2)", 0 }, + { 0x6d00, 0x6d0f, 1, 2, "ex %rw3,%a1", 0 }, + { 0x6d10, 0x6dff, 1, 2, "ex %rw3,%a1(%rw2)", 0 }, + { 0x6e00, 0x6e0f, 1, 2, "ldb %a1,%rb3", 0 }, + { 0x6e10, 0x6eff, 1, 2, "ldb %a1(%rw2),%rb3", 0 }, + { 0x6f00, 0x6f0f, 1, 2, "ld %a1,%rw3", 0 }, + { 0x6f10, 0x6fff, 1, 2, "ld %a1(%rw2),%rw3", 0 }, + { 0x7010, 0x70ff, 1, 2, "ldb %rb3,%rw2(%rw5)", 0 }, + { 0x7110, 0x71ff, 1, 2, "ld %rw3,%rw2(%rw5)", 0 }, + { 0x7210, 0x72ff, 1, 2, "ldb %rw2(%rw5),%rb3", 0 }, + { 0x7310, 0x73ff, 1, 2, "ld %rw2(%rw5),%rw3", 0 }, + { 0x7410, 0x74ff, 1, 2, "lda p%rw3,%rw2(%rw5)", 0 }, + { 0x7510, 0x75ff, 1, 2, "ldl %rl3,%rw2(%rw5)", 0 }, + { 0x7600, 0x760f, 1, 2, "lda p%rw3,%a1", 0 }, + { 0x7610, 0x76ff, 1, 2, "lda p%rw3,%a1(%rw2)", 0 }, + { 0x7710, 0x77ff, 1, 2, "ldl %rw2(%rw5),%rl3", 0 }, + { 0x7800, 0x78ff, 1, 1, "rsvd78", 0 }, + { 0x7900, 0x7900, 1, 2, "ldps %a1", 0 }, + { 0x7910, 0x79f0, 16, 2, "ldps %a1(%rw2)", 0 }, + { 0x7a00, 0x7a00, 1, 1, "halt", STEP_OVER }, + { 0x7b00, 0x7b00, 1, 1, "iret", STEP_OUT }, + { 0x7b08, 0x7b08, 1, 1, "mset", 0 }, + { 0x7b09, 0x7b09, 1, 1, "mres", 0 }, + { 0x7b0a, 0x7b0a, 1, 1, "mbit", 0 }, + { 0x7b0d, 0x7bfd, 16, 1, "mreq %rw2", 0 }, + { 0x7c00, 0x7c03, 1, 1, "di %i3", 0 }, + { 0x7c04, 0x7c07, 1, 1, "ei %i3", 0 }, + { 0x7d00, 0x7df0, 16, 1, "ldctl %rw2,ctrl0", 0 }, + { 0x7d01, 0x7df1, 16, 1, "ldctl %rw2,ctrl1", 0 }, + { 0x7d02, 0x7df2, 16, 1, "ldctl %rw2,fcw", 0 }, + { 0x7d03, 0x7df3, 16, 1, "ldctl %rw2,refresh", 0 }, + { 0x7d04, 0x7df4, 16, 1, "ldctl %rw2,psapseg", 0 }, + { 0x7d05, 0x7df5, 16, 1, "ldctl %rw2,psapoff", 0 }, + { 0x7d06, 0x7df6, 16, 1, "ldctl %rw2,nspseg", 0 }, + { 0x7d07, 0x7df7, 16, 1, "ldctl %rw2,nspoff", 0 }, + { 0x7d08, 0x7df8, 16, 1, "ldctl ctrl0,%rw2", 0 }, + { 0x7d09, 0x7df9, 16, 1, "ldctl ctrl1,%rw2", 0 }, + { 0x7d0a, 0x7dfa, 16, 1, "ldctl fcw,%rw2", 0 }, + { 0x7d0b, 0x7dfb, 16, 1, "ldctl refresh,%rw2", 0 }, + { 0x7d0c, 0x7dfc, 16, 1, "ldctl psapseg,%rw2", 0 }, + { 0x7d0d, 0x7dfd, 16, 1, "ldctl psapoff,%rw2", 0 }, + { 0x7d0e, 0x7dfe, 16, 1, "ldctl nspseg,%rw2", 0 }, + { 0x7d0f, 0x7dff, 16, 1, "ldctl nspoff,%rw2", 0 }, + { 0x7e00, 0x7eff, 1, 1, "rsvd7e %#b1", 0 }, + { 0x7f00, 0x7fff, 1, 1, "sc %#b1", STEP_OVER }, + { 0x8000, 0x80ff, 1, 1, "addb %rb3,%rb2", 0 }, + { 0x8100, 0x81ff, 1, 1, "add %rw3,%rw2", 0 }, + { 0x8200, 0x82ff, 1, 1, "subb %rb3,%rb2", 0 }, + { 0x8300, 0x83ff, 1, 1, "sub %rw3,%rw2", 0 }, + { 0x8400, 0x84ff, 1, 1, "orb %rb3,%rb2", 0 }, + { 0x8500, 0x85ff, 1, 1, "or %rw3,%rw2", 0 }, + { 0x8600, 0x86ff, 1, 1, "andb %rb3,%rb2", 0 }, + { 0x8700, 0x87ff, 1, 1, "and %rw3,%rw2", 0 }, + { 0x8800, 0x88ff, 1, 1, "xorb %rb3,%rb2", 0 }, + { 0x8900, 0x89ff, 1, 1, "xor %rw3,%rw2", 0 }, + { 0x8a00, 0x8aff, 1, 1, "cpb %rb3,%rb2", 0 }, + { 0x8b00, 0x8bff, 1, 1, "cp %rw3,%rw2", 0 }, + { 0x8c00, 0x8cf0, 16, 1, "comb %rb2", 0 }, + { 0x8c02, 0x8cf2, 16, 1, "negb %rb2", 0 }, + { 0x8c04, 0x8cf4, 16, 1, "testb %rb2", 0 }, + { 0x8c06, 0x8cf6, 16, 1, "tsetb %rb2", 0 }, + { 0x8c01, 0x8cf1, 16, 1, "ldctlb %rb2,flags", 0 }, + { 0x8c08, 0x8cf8, 16, 1, "clrb %rb2", 0 }, + { 0x8c09, 0x8cf9, 16, 1, "ldctlb flags,%rb2", 0 }, + { 0x8d00, 0x8df0, 16, 1, "com %rw2", 0 }, + { 0x8d01, 0x8df1, 16, 1, "setflg %f2", 0 }, + { 0x8d02, 0x8df2, 16, 1, "neg %rw2", 0 }, + { 0x8d03, 0x8df3, 16, 1, "resflg %f2", 0 }, + { 0x8d04, 0x8df4, 16, 1, "test %rw2", 0 }, + { 0x8d05, 0x8df5, 16, 1, "comflg %f2", 0 }, + { 0x8d06, 0x8df6, 16, 1, "tset %rw2", 0 }, + { 0x8d07, 0x8d07, 1, 1, "nop", 0 }, + { 0x8d08, 0x8df8, 16, 1, "clr %rw2", 0 }, + { 0x8e00, 0x8eff, 1, 1, "ext8e %#b1", 0 }, + { 0x8f00, 0x8fff, 1, 1, "ext8f %#b1", 0 }, + { 0x9000, 0x90ff, 1, 1, "cpl %rl3,%rl2", 0 }, + { 0x9110, 0x91ff, 1, 1, "pushl @%rw2,%rl3", 0 }, + { 0x9200, 0x92ff, 1, 1, "subl %rl3,%rl2", 0 }, + { 0x9310, 0x93ff, 1, 1, "push @%rw2,%rw3", 0 }, + { 0x9400, 0x94ff, 1, 1, "ldl %rl3,%rl2", 0 }, + { 0x9510, 0x95ff, 1, 1, "popl %rl3,@%rw2", 0 }, + { 0x9600, 0x96ff, 1, 1, "addl %rl3,%rl2", 0 }, + { 0x9710, 0x97ff, 1, 1, "pop %rw3,@%rw2", 0 }, + { 0x9800, 0x98ff, 1, 1, "multl %rq3,%rl2", 0 }, + { 0x9900, 0x99ff, 1, 1, "mult %rl3,%rw2", 0 }, + { 0x9a00, 0x9aff, 1, 1, "divl %rq3,%rl2", 0 }, + { 0x9b00, 0x9bff, 1, 1, "div %rl3,%rw2", 0 }, + { 0x9c00, 0x9cf8, 8, 1, "testl %rl2", 0 }, + { 0x9d00, 0x9dff, 1, 1, "rsvd9d", 0 }, + { 0x9e00, 0x9e0f, 1, 1, "ret %c3", STEP_OUT }, + { 0x9f00, 0x9fff, 1, 1, "rsvd9f", 0 }, + { 0xa000, 0xa0ff, 1, 1, "ldb %rb3,%rb2", 0 }, + { 0xa100, 0xa1ff, 1, 1, "ld %rw3,%rw2", 0 }, + { 0xa200, 0xa2ff, 1, 1, "resb %rb2,%3", 0 }, + { 0xa300, 0xa3ff, 1, 1, "res %rw2,%3", 0 }, + { 0xa400, 0xa4ff, 1, 1, "setb %rb2,%3", 0 }, + { 0xa500, 0xa5ff, 1, 1, "set %rw2,%3", 0 }, + { 0xa600, 0xa6ff, 1, 1, "bitb %rb2,%3", 0 }, + { 0xa700, 0xa7ff, 1, 1, "bit %rw2,%3", 0 }, + { 0xa800, 0xa8ff, 1, 1, "incb %rb2,%+3", 0 }, + { 0xa900, 0xa9ff, 1, 1, "inc %rw2,%+3", 0 }, + { 0xaa00, 0xaaff, 1, 1, "decb %rb2,%+3", 0 }, + { 0xab00, 0xabff, 1, 1, "dec %rw2,%+3", 0 }, + { 0xac00, 0xacff, 1, 1, "exb %rb3,%rb2", 0 }, + { 0xad00, 0xadff, 1, 1, "ex %rw3,%rw2", 0 }, + { 0xae00, 0xaeff, 1, 1, "tccb %c3,%rb2", 0 }, + { 0xaf00, 0xafff, 1, 1, "tcc %c3,%rw2", 0 }, + { 0xb000, 0xb0f0, 16, 1, "dab %rb2", 0 }, + { 0xb100, 0xb1f0, 16, 1, "extsb %rw2", 0 }, + { 0xb107, 0xb1f7, 16, 1, "extsl %rq2", 0 }, + { 0xb10a, 0xb1fa, 16, 1, "exts %rl2", 0 }, + { 0xb200, 0xb2f0, 16, 1, "rlb %rb2,%?3", 0 }, + { 0xb201, 0xb2f1, 16, 2, "s%*lb %rb2,%$3", 0 }, + { 0xb202, 0xb2f2, 16, 1, "rlb %rb2,%?3", 0 }, + { 0xb203, 0xb2f3, 16, 2, "sdlb %rb2,%rw5", 0 }, + { 0xb204, 0xb2f4, 16, 1, "rrb %rb2,%?3", 0 }, + { 0xb206, 0xb2f6, 16, 1, "rrb %rb2,%?3", 0 }, + { 0xb208, 0xb2f8, 16, 1, "rlcb %rb2,%?3", 0 }, + { 0xb209, 0xb2f9, 16, 2, "s%*ab %rb2,%$3", 0 }, + { 0xb20a, 0xb2fa, 16, 1, "rlcb %rb2,%?3", 0 }, + { 0xb20b, 0xb2fb, 16, 2, "sdab %rb2,%rw5", 0 }, + { 0xb20c, 0xb2fc, 16, 1, "rrcb %rb2,%?3", 0 }, + { 0xb20e, 0xb2fe, 16, 1, "rrcb %rb2,%?3", 0 }, + { 0xb300, 0xb3f0, 16, 1, "rl %rw2,%?3", 0 }, + { 0xb301, 0xb3f1, 16, 2, "s%*l %rw2,%$3", 0 }, + { 0xb302, 0xb3f2, 16, 1, "rl %rw2,%?3", 0 }, + { 0xb303, 0xb3f3, 16, 2, "sdl %rw2,%rw5", 0 }, + { 0xb304, 0xb3f4, 16, 1, "rr %rw2,%?3", 0 }, + { 0xb305, 0xb3f5, 16, 2, "s%*ll %rl2,%$3", 0 }, + { 0xb306, 0xb3f6, 16, 1, "rr %rw2,%?3", 0 }, + { 0xb307, 0xb3f7, 16, 2, "sdll %rl2,%rw5", 0 }, + { 0xb308, 0xb3f8, 16, 1, "rlc %rw2,%?3", 0 }, + { 0xb309, 0xb3f9, 16, 2, "s%*a %rw2,%$3", 0 }, + { 0xb30a, 0xb3fa, 16, 1, "rlc %rw2,%?3", 0 }, + { 0xb30b, 0xb3fb, 16, 2, "sda %rw2,%rw5", 0 }, + { 0xb30c, 0xb3fc, 16, 1, "rrc %rw2,%?3", 0 }, + { 0xb30d, 0xb3fd, 16, 2, "s%*al %rl2,%$3", 0 }, + { 0xb30e, 0xb3fe, 16, 1, "rrc %rw2,%?3", 0 }, + { 0xb30f, 0xb3ff, 16, 2, "sdal %rl2,%rw5", 0 }, + { 0xb400, 0xb4ff, 1, 1, "adcb %rb3,%rb2", 0 }, + { 0xb500, 0xb5ff, 1, 1, "adc %rw3,%rw2", 0 }, + { 0xb600, 0xb6ff, 1, 1, "sbcb %rb3,%rb2", 0 }, + { 0xb700, 0xb7ff, 1, 1, "sbc %rw3,%rw2", 0 }, + { 0xb810, 0xb8f0, 16, 2, "trib @%rw2,@%rw6,%rb5", 0 }, + { 0xb812, 0xb8f2, 16, 2, "trtib @%rw2,@%rw6,%rb5", 0 }, + { 0xb814, 0xb8f4, 16, 2, "trirb @%rw2,@%rw6,%rb5", 0 }, + { 0xb816, 0xb8f6, 16, 2, "trtirb @%rw2,@%rw6,%rb5", 0 }, + { 0xb818, 0xb8f8, 16, 2, "trdb @%rw2,@%rw6,%rb5", 0 }, + { 0xb81a, 0xb8fa, 16, 2, "trtrb @%rw2,@%rw6,%rb5", 0 }, + { 0xb81c, 0xb8fc, 16, 2, "trdrb @%rw2,@%rw6,%rb5", 0 }, + { 0xb81e, 0xb8fe, 16, 2, "trtdrb @%rw2,@%rw6,%rb5", 0 }, + { 0xb900, 0xb9ff, 16, 1, "rsvdb9", 0 }, + { 0xba10, 0xbaf0, 16, 2, "cpib %rb6,@%rw2,%rw5,%c7", 0 }, + { 0xba11, 0xbaf1, 16, 2, "ldirb @%rw6,@%rw2,%rw5", STEP_OVER }, + { 0xba12, 0xbaf2, 16, 2, "cpsib @%rw6,@%rw2,%rw5,%c7", 0 }, + { 0xba14, 0xbaf4, 16, 2, "cpirb %rb6,@%rw2,%rw5,%c7", STEP_OVER }, + { 0xba16, 0xbaf6, 16, 2, "cpsirb @%rw6,@%rw2,%rw5,%c7", STEP_OVER }, + { 0xba18, 0xbaf8, 16, 2, "cpdb %rb6,@%rw2,%rw5,%c7", 0 }, + { 0xba19, 0xbaf9, 16, 2, "lddrb @%rw2,@%rw6,%rw5", STEP_OVER }, + { 0xba1a, 0xbafa, 16, 2, "cpsdb @%rw6,@%rw2,%rw5,%c7", 0 }, + { 0xba1c, 0xbafc, 16, 2, "cpdrb %rb6,@%rw2,%rw5,%c7", STEP_OVER }, + { 0xba1e, 0xbafe, 16, 2, "cpsdrb @%rw6,@%rw2,%rw5,%c7", STEP_OVER }, + { 0xbb10, 0xbbf0, 16, 2, "cpi %rw6,@%rw2,%rw5,%c7", 0 }, + { 0xbb11, 0xbbf1, 16, 2, "ldir @%rw6,@%rw2,%rw5", STEP_OVER }, + { 0xbb12, 0xbbf2, 16, 2, "cpsi @%rw6,@%rw2,%rw5,%c7", 0 }, + { 0xbb14, 0xbbf4, 16, 2, "cpir %rw6,@%rw2,%rw5,%c7", STEP_OVER }, + { 0xbb16, 0xbbf6, 16, 2, "cpsir @%rw6,@%rw2,%rw5,%c7", STEP_OVER }, + { 0xbb18, 0xbbf8, 16, 2, "cpd %rw6,@%rw2,%rw5,%c7", 0 }, + { 0xbb19, 0xbbf9, 16, 2, "lddr @%rw2,@%rw6,%rw5", STEP_OVER }, + { 0xbb1a, 0xbbfa, 16, 2, "cpsd @%rw6,@%rw2,%rw5,%c7", 0 }, + { 0xbb1c, 0xbbfc, 16, 2, "cpdr %rw6,@%rw2,%rw5,%c7", STEP_OVER }, + { 0xbb1e, 0xbbfe, 16, 2, "cpsdr @%rw6,@%rw2,%rw5,%c7", STEP_OVER }, + { 0xbc00, 0xbcff, 1, 1, "rrdb %rb3,%rb2", 0 }, + { 0xbd00, 0xbdff, 1, 1, "ldk %rw2,%3", 0 }, + { 0xbe00, 0xbeff, 1, 1, "rldb %rb3,%rb2", 0 }, + { 0xbf00, 0xbfff, 1, 1, "rsvdbf", 0 }, + { 0xc000, 0xcfff, 1, 1, "ldb %rb1,%#b1", 0 }, + { 0xd000, 0xdfff, 1, 1, "calr %d2", STEP_OVER }, + { 0xe000, 0xefff, 1, 1, "jr %c1,%d1", 0 }, + { 0xf000, 0xf07f, 1, 1, "dbjnz %rb1,%d0", STEP_OVER }, + { 0xf100, 0xf17f, 1, 1, "dbjnz %rb1,%d0", STEP_OVER }, + { 0xf200, 0xf27f, 1, 1, "dbjnz %rb1,%d0", STEP_OVER }, + { 0xf300, 0xf37f, 1, 1, "dbjnz %rb1,%d0", STEP_OVER }, + { 0xf400, 0xf47f, 1, 1, "dbjnz %rb1,%d0", STEP_OVER }, + { 0xf500, 0xf57f, 1, 1, "dbjnz %rb1,%d0", STEP_OVER }, + { 0xf600, 0xf67f, 1, 1, "dbjnz %rb1,%d0", STEP_OVER }, + { 0xf700, 0xf77f, 1, 1, "dbjnz %rb1,%d0", STEP_OVER }, + { 0xf800, 0xf87f, 1, 1, "dbjnz %rb1,%d0", STEP_OVER }, + { 0xf900, 0xf97f, 1, 1, "dbjnz %rb1,%d0", STEP_OVER }, + { 0xfa00, 0xfa7f, 1, 1, "dbjnz %rb1,%d0", STEP_OVER }, + { 0xfb00, 0xfb7f, 1, 1, "dbjnz %rb1,%d0", STEP_OVER }, + { 0xfc00, 0xfc7f, 1, 1, "dbjnz %rb1,%d0", STEP_OVER }, + { 0xfd00, 0xfd7f, 1, 1, "dbjnz %rb1,%d0", STEP_OVER }, + { 0xfe00, 0xfe7f, 1, 1, "dbjnz %rb1,%d0", STEP_OVER }, + { 0xff00, 0xff7f, 1, 1, "dbjnz %rb1,%d0", STEP_OVER }, + { 0xf080, 0xf0ff, 1, 1, "djnz %rw1,%d0", STEP_OVER }, + { 0xf180, 0xf1ff, 1, 1, "djnz %rw1,%d0", STEP_OVER }, + { 0xf280, 0xf2ff, 1, 1, "djnz %rw1,%d0", STEP_OVER }, + { 0xf380, 0xf3ff, 1, 1, "djnz %rw1,%d0", STEP_OVER }, + { 0xf480, 0xf4ff, 1, 1, "djnz %rw1,%d0", STEP_OVER }, + { 0xf580, 0xf5ff, 1, 1, "djnz %rw1,%d0", STEP_OVER }, + { 0xf680, 0xf6ff, 1, 1, "djnz %rw1,%d0", STEP_OVER }, + { 0xf780, 0xf7ff, 1, 1, "djnz %rw1,%d0", STEP_OVER }, + { 0xf880, 0xf8ff, 1, 1, "djnz %rw1,%d0", STEP_OVER }, + { 0xf980, 0xf9ff, 1, 1, "djnz %rw1,%d0", STEP_OVER }, + { 0xfa80, 0xfaff, 1, 1, "djnz %rw1,%d0", STEP_OVER }, + { 0xfb80, 0xfbff, 1, 1, "djnz %rw1,%d0", STEP_OVER }, + { 0xfc80, 0xfcff, 1, 1, "djnz %rw1,%d0", STEP_OVER }, + { 0xfd80, 0xfdff, 1, 1, "djnz %rw1,%d0", STEP_OVER }, + { 0xfe80, 0xfeff, 1, 1, "djnz %rw1,%d0", STEP_OVER }, + { 0xff80, 0xffff, 1, 1, "djnz %rw1,%d0", STEP_OVER }, + { 0, 0, 0, 0, nullptr, 0} +}; + +z8000_disassembler::z8000_disassembler(config *conf) : m_config(conf) +{ + for (const opcode *opc = table; opc->size; opc++) + for (u32 val = opc->beg; val <= opc->end; val += opc->step) + oplist[val] = opc - table; +} -static int n[16]; /* opcode nibbles */ -static int b[8]; /* opcode bytes */ -static int w[4]; /* opcode words */ -static void GET_OP(const uint8_t *oprom, int i, unsigned offset) +void z8000_disassembler::get_op(const data_buffer &opcodes, int i, offs_t &new_pc, u16 *w, u8 *b, u8 *n) { - uint16_t opcode = (oprom[offset] << 8) | oprom[offset + 1]; + uint16_t opcode = opcodes.r16(new_pc); w[i] = opcode; b[i*2+0] = opcode >> 8; b[i*2+1] = opcode & 0xff; @@ -31,37 +553,40 @@ static void GET_OP(const uint8_t *oprom, int i, unsigned offset) n[i*4+1] = (opcode >> 8) & 0x0f; n[i*4+2] = (opcode >> 4) & 0x0f; n[i*4+3] = opcode & 0x0f; + new_pc += 2; } -static const char *const cc[16] = { +const char *const z8000_disassembler::cc[16] = { "n", "lt", "le", "ule", "pe/ov", "mi", "eq/z", "c/ult", "a", "ge", "gt", "ugt", "po/nov", "pl", "ne/nz", "nc/uge" }; -static const char *const flg[16] = { +const char *const z8000_disassembler::flg[16] = { "", "p/v", "s", "p/v,s", "z", "p/v,z", "s,z", "p/v,s,z", "c", "p/v,c","s,c", "p/v,s,c", "z,c", "p/v,z,c","s,z,c","p/v,s,z,c" }; -static const char *const ints[4] = { +const char *const z8000_disassembler::ints[4] = { "", "vi", "nvi", "vi,nvi" }; -int z8k_segm; /* Current disassembler mode: 0 - non-segmented, 1 - segmented */ -int z8k_segm_mode = Z8K_SEGM_MODE_AUTO; /* User disassembler mode setting: segmented, non-segmented, auto */ +u32 z8000_disassembler::opcode_alignment() const +{ + return 2; +} -CPU_DISASSEMBLE(z8000) +offs_t z8000_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - int new_pc = pc, i, j, tmp; + u8 n[16]; /* opcode nibbles */ + u8 b[8]; /* opcode bytes */ + u16 w[4]; /* opcode words */ + + offs_t new_pc = pc, i, j, tmp; const char *src; - z8002_device::Z8000_dasm o; uint32_t flags = 0; uint32_t old_w; - z8002_device::init_tables(); - - GET_OP(oprom, 0, new_pc - pc); - new_pc += 2; + get_op(opcodes, 0, new_pc, w, b, n); switch (pc) { case 0x0000: @@ -74,11 +599,14 @@ CPU_DISASSEMBLE(z8000) util::stream_format(stream, ".word #%%%04x ;RST PC", w[0]); break; default: - o = z8002_device::dasm(w[0]); - if (o.size > 1) { GET_OP(oprom, 1, new_pc - pc); new_pc += 2; } - if (o.size > 2) { GET_OP(oprom, 2, new_pc - pc); new_pc += 2; } + { + const opcode &o = table[oplist[w[0]]]; + if (o.size > 1) + get_op(opcodes, 1, new_pc, w, b, n); + if (o.size > 2) + get_op(opcodes, 2, new_pc, w, b, n); src = o.dasm; - flags = o.flags; + flags = o.dasmflags; while (*src) { @@ -139,14 +667,14 @@ CPU_DISASSEMBLE(z8000) tmp = ((n[1] & 0x01) << 8) + (n[3] << 4) + (n[7] & 0x08); switch (tmp) { - case 0x000: util::stream_format(stream, "inirb "); flags = DASMFLAG_STEP_OVER; break; + case 0x000: util::stream_format(stream, "inirb "); flags = STEP_OVER; break; case 0x008: util::stream_format(stream, "inib "); break; - case 0x010: util::stream_format(stream, "sinirb"); flags = DASMFLAG_STEP_OVER; break; + case 0x010: util::stream_format(stream, "sinirb"); flags = STEP_OVER; break; case 0x018: util::stream_format(stream, "sinib "); break; - case 0x020: util::stream_format(stream, "otirb "); flags = DASMFLAG_STEP_OVER; break; + case 0x020: util::stream_format(stream, "otirb "); flags = STEP_OVER; break; case 0x028: util::stream_format(stream, "outib "); break; case 0x030: util::stream_format(stream, "soutib"); break; - case 0x038: util::stream_format(stream, "sotirb"); flags = DASMFLAG_STEP_OVER; break; + case 0x038: util::stream_format(stream, "sotirb"); flags = STEP_OVER; break; case 0x040: util::stream_format(stream, "inb "); break; case 0x048: util::stream_format(stream, "inb "); break; case 0x050: util::stream_format(stream, "sinb "); break; @@ -155,22 +683,22 @@ CPU_DISASSEMBLE(z8000) case 0x068: util::stream_format(stream, "outb "); break; case 0x070: util::stream_format(stream, "soutb "); break; case 0x078: util::stream_format(stream, "soutb "); break; - case 0x080: util::stream_format(stream, "indrb "); flags = DASMFLAG_STEP_OVER; break; + case 0x080: util::stream_format(stream, "indrb "); flags = STEP_OVER; break; case 0x088: util::stream_format(stream, "indb "); break; - case 0x090: util::stream_format(stream, "sindrb"); flags = DASMFLAG_STEP_OVER; break; + case 0x090: util::stream_format(stream, "sindrb"); flags = STEP_OVER; break; case 0x098: util::stream_format(stream, "sindb "); break; - case 0x0a0: util::stream_format(stream, "otdrb "); flags = DASMFLAG_STEP_OVER; break; + case 0x0a0: util::stream_format(stream, "otdrb "); flags = STEP_OVER; break; case 0x0a8: util::stream_format(stream, "outdb "); break; case 0x0b0: util::stream_format(stream, "soutdb"); break; - case 0x0b8: util::stream_format(stream, "sotdrb"); flags = DASMFLAG_STEP_OVER; break; - case 0x100: util::stream_format(stream, "inir "); flags = DASMFLAG_STEP_OVER; break; + case 0x0b8: util::stream_format(stream, "sotdrb"); flags = STEP_OVER; break; + case 0x100: util::stream_format(stream, "inir "); flags = STEP_OVER; break; case 0x108: util::stream_format(stream, "ini "); break; - case 0x110: util::stream_format(stream, "sinir "); flags = DASMFLAG_STEP_OVER; break; + case 0x110: util::stream_format(stream, "sinir "); flags = STEP_OVER; break; case 0x118: util::stream_format(stream, "sini "); break; - case 0x120: util::stream_format(stream, "otir "); flags = DASMFLAG_STEP_OVER; break; + case 0x120: util::stream_format(stream, "otir "); flags = STEP_OVER; break; case 0x128: util::stream_format(stream, "outi "); break; case 0x130: util::stream_format(stream, "souti "); break; - case 0x138: util::stream_format(stream, "sotir "); flags = DASMFLAG_STEP_OVER; break; + case 0x138: util::stream_format(stream, "sotir "); flags = STEP_OVER; break; case 0x140: util::stream_format(stream, "in "); break; case 0x148: util::stream_format(stream, "in "); break; case 0x150: util::stream_format(stream, "sin "); break; @@ -179,14 +707,14 @@ CPU_DISASSEMBLE(z8000) case 0x168: util::stream_format(stream, "out "); break; case 0x170: util::stream_format(stream, "sout "); break; case 0x178: util::stream_format(stream, "sout "); break; - case 0x180: util::stream_format(stream, "indr "); flags = DASMFLAG_STEP_OVER; break; + case 0x180: util::stream_format(stream, "indr "); flags = STEP_OVER; break; case 0x188: util::stream_format(stream, "ind "); break; - case 0x190: util::stream_format(stream, "sindr "); flags = DASMFLAG_STEP_OVER; break; + case 0x190: util::stream_format(stream, "sindr "); flags = STEP_OVER; break; case 0x198: util::stream_format(stream, "sind "); break; - case 0x1a0: util::stream_format(stream, "otdr "); flags = DASMFLAG_STEP_OVER; break; + case 0x1a0: util::stream_format(stream, "otdr "); flags = STEP_OVER; break; case 0x1a8: util::stream_format(stream, "outd "); break; case 0x1b0: util::stream_format(stream, "soutd "); break; - case 0x1b8: util::stream_format(stream, "sotdr "); flags = DASMFLAG_STEP_OVER; break; + case 0x1b8: util::stream_format(stream, "sotdr "); flags = STEP_OVER; break; default: util::stream_format(stream, "unk(0x%x)", tmp); } @@ -195,13 +723,12 @@ CPU_DISASSEMBLE(z8000) /* address */ src++; i = *src++ - '0'; - if (z8k_segm) { + if (m_config->get_segmented_mode()) { if (w[i] & 0x8000) { old_w = w[i]; for (j = i; j < o.size; j++) w[j] = w[j + 1]; - GET_OP(oprom, o.size - 1, new_pc - pc); - new_pc += 2; + get_op(opcodes, o.size - 1, new_pc, w, b, n); w[i] = ((old_w & 0x7f00) << 16) | (w[i] & 0xffff); } else { @@ -244,7 +771,7 @@ CPU_DISASSEMBLE(z8000) tmp = 0; abort(); } - if (z8k_segm) + if (m_config->get_segmented_mode()) util::stream_format(stream, "<%%%02X>%%%04X", (tmp >> 16) & 0xff, tmp & 0xffff); else util::stream_format(stream, "%%%04x", tmp); @@ -307,7 +834,8 @@ CPU_DISASSEMBLE(z8000) } } else stream << *src++; } - break; + } + break; } - return (new_pc - pc) | flags | DASMFLAG_SUPPORTED; + return (new_pc - pc) | flags | SUPPORTED; } diff --git a/src/devices/cpu/z8000/8000dasm.h b/src/devices/cpu/z8000/8000dasm.h new file mode 100644 index 00000000000..16a2f0974e1 --- /dev/null +++ b/src/devices/cpu/z8000/8000dasm.h @@ -0,0 +1,50 @@ +// license:BSD-3-Clause +// copyright-holders:Juergen Buchmueller,Ernesto Corvi +/***************************************************************************** + * + * 8000dasm.c + * Portable Z8000(2) emulator + * + *****************************************************************************/ + +#ifndef MAME_CPU_Z8000_8000DASM_H +#define MAME_CPU_Z8000_8000DASM_H + +#pragma once + +class z8000_disassembler : public util::disasm_interface +{ +public: + struct config { + virtual ~config() = default; + virtual bool get_segmented_mode() const = 0; + }; + + z8000_disassembler(config *conf); + virtual ~z8000_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + struct opcode { + u16 beg, end, step; + u16 size; + const char *dasm; + offs_t dasmflags; + }; + + static const opcode table[]; + static const char *const cc[16]; + static const char *const flg[16]; + static const char *const ints[4]; + + config *m_config; + + u16 oplist[0x10000]; + + void get_op(const data_buffer &opcodes, int i, offs_t &new_pc, u16 *w, u8 *b, u8 *n); + +}; + +#endif diff --git a/src/devices/cpu/z8000/z8000.cpp b/src/devices/cpu/z8000/z8000.cpp index ab42e44539e..251dbfa9a99 100644 --- a/src/devices/cpu/z8000/z8000.cpp +++ b/src/devices/cpu/z8000/z8000.cpp @@ -22,10 +22,6 @@ //#define VERBOSE 1 #include "logmacro.h" - -extern int z8k_segm; -extern int z8k_segm_mode; - DEFINE_DEVICE_TYPE(Z8001, z8001_device, "z8001", "Zilog Z8001") DEFINE_DEVICE_TYPE(Z8002, z8002_device, "z8002", "Zilog Z8002") @@ -54,12 +50,6 @@ z8001_device::z8001_device(const machine_config &mconfig, const char *tag, devic } -offs_t z8002_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) -{ - extern CPU_DISASSEMBLE( z8000 ); - return CPU_DISASSEMBLE_NAME(z8000)(this, stream, pc, oprom, opram, options); -} - device_memory_interface::space_config_vector z8002_device::memory_space_config() const { return space_config_vector { @@ -77,21 +67,14 @@ device_memory_interface::space_config_vector z8001_device::memory_space_config() }; } -/* opcode execution table */ -std::unique_ptr z8002_device::z8000_exec; - -/* zero, sign and parity flags for logical byte operations */ -static uint8_t z8000_zsp[256]; - - -int z8002_device::segmented_mode() +bool z8002_device::get_segmented_mode() const { - return 0; + return false; } -int z8001_device::segmented_mode() +bool z8001_device::get_segmented_mode() const { - return (m_fcw & F_SEG) ? 1 : 0; + return (m_fcw & F_SEG) ? true : false; } uint32_t z8002_device::addr_add(uint32_t addr, uint32_t addend) @@ -145,7 +128,7 @@ uint32_t z8002_device::get_addr_operand(int opnum) { uint32_t seg = m_program->read_word(m_pc); m_pc += 2; - if (segmented_mode()) + if (get_segmented_mode()) { if (seg & 0x8000) { @@ -175,7 +158,7 @@ uint32_t z8002_device::get_raw_addr_operand(int opnum) { uint32_t seg = m_program->read_word(m_pc); m_pc += 2; - if (segmented_mode()) + if (get_segmented_mode()) { if (seg & 0x8000) { @@ -651,47 +634,22 @@ void z8002_device::state_string_export(const device_state_entry &entry, std::str } } -void z8001_device::z8k_disass_mode(int ref, const std::vector ¶ms) +void z8002_device::init_tables() { - size_t len; - if (params.size() == 1) - { - len = params[0].length(); - if (!core_strnicmp(params[0].c_str(), "segmented", len) || !core_stricmp(params[0].c_str(), "z8001")) { - z8k_segm = true; - z8k_segm_mode = Z8K_SEGM_MODE_SEG; - machine().debugger().console().printf("Disassembler mode set to Z8001/segmented\n"); - } - else if (!core_strnicmp(params[0].c_str(), "non-segmented", len) || !core_stricmp(params[0].c_str(), "z8002")) - { - z8k_segm = false; - z8k_segm_mode = Z8K_SEGM_MODE_NONSEG; - machine().debugger().console().printf("Disassembler mode set to Z8002/non-segmented\n"); - } - else if (!core_strnicmp(params[0].c_str(), "automatic", len)) - { - z8k_segm_mode = Z8K_SEGM_MODE_AUTO; - machine().debugger().console().printf("Disassembler mode set to automatic\n"); - } - else - goto usage; - } - else if (params.size() > 1) - { - usage: - machine().debugger().console().printf("Usage: z8k_disass_mode \n"); - machine().debugger().console().printf(" set disassembler mode\n"); - machine().debugger().console().printf(" mode: \"segmented\" or \"z8001\" - Z8001 mode\n"); - machine().debugger().console().printf(" \"non-segmented\" or \"z8002\" - Z8002 mode\n"); - machine().debugger().console().printf(" \"automatic\" - automatic mode\n"); - } - else - { - machine().debugger().console().printf("Current disassembler mode: "); - if (z8k_segm_mode == Z8K_SEGM_MODE_AUTO) - machine().debugger().console().printf("automatic, currently "); - machine().debugger().console().printf("%s\n", z8k_segm ? "Z8001/segmented" : "Z8002/non-segmented"); - } + /* set up the zero, sign, parity lookup table */ + for (int i = 0; i < 256; i++) + z8000_zsp[i] = ((i == 0) ? F_Z : 0) | + ((i & 128) ? F_S : 0) | + ((((i>>7)^(i>>6)^(i>>5)^(i>>4)^(i>>3)^(i>>2)^(i>>1)^i) & 1) ? 0 : F_PV); + + for (const Z8000_init *opc = table; opc->size; opc++) + for (u32 val = opc->beg; val <= opc->end; val += opc->step) + z8000_exec[val] = opc - table; +} + +util::disasm_interface *z8002_device::create_disassembler() +{ + return new z8000_disassembler(this); } void z8001_device::device_start() @@ -710,14 +668,6 @@ void z8001_device::device_start() init_tables(); - if (machine().debug_flags & DEBUG_FLAG_ENABLED) - { - using namespace std::placeholders; - machine().debugger().console().register_command("z8k_disass_mode", CMDFLAG_NONE, 0, 0, 1, std::bind(&z8001_device::z8k_disass_mode, this, _1, _2)); - } - - z8k_segm = true; - register_debug_state(); m_icountptr = &m_icount; @@ -741,8 +691,6 @@ void z8002_device::device_start() init_tables(); - z8k_segm = false; - register_debug_state(); m_icountptr = &m_icount; @@ -773,8 +721,6 @@ void z8002_device::device_reset() z8002_device::~z8002_device() { - // FIXME: assumes that these CPUs can't outlive each other - deinit_tables(); } void z8002_device::execute_run() @@ -785,9 +731,6 @@ void z8002_device::execute_run() if (m_irq_req) Interrupt(); - if (z8k_segm_mode == Z8K_SEGM_MODE_AUTO) - z8k_segm = (m_fcw & F_SEG_Z8001()) ? 1 : 0; - m_ppc = m_pc; debugger_instruction_hook(this, m_pc); @@ -799,10 +742,10 @@ void z8002_device::execute_run() { m_op[0] = RDOP(); m_op_valid = 1; - Z8000_exec const *const exec = &z8000_exec[m_op[0]]; + const Z8000_init &exec = table[z8000_exec[m_op[0]]]; - m_icount -= exec->cycles; - (this->*exec->opcode)(); + m_icount -= exec.cycles; + (this->*exec.opcode)(); m_op_valid = 0; } } while (m_icount > 0); diff --git a/src/devices/cpu/z8000/z8000.h b/src/devices/cpu/z8000/z8000.h index a782efbaf18..4f46eaf76e6 100644 --- a/src/devices/cpu/z8000/z8000.h +++ b/src/devices/cpu/z8000/z8000.h @@ -5,6 +5,7 @@ #pragma once +#include "8000dasm.h" enum { @@ -31,7 +32,7 @@ enum #define MCFG_Z8000_MO(_devcb) \ devcb = &z8002_device::set_mo_callback(*device, DEVCB_##_devcb); -class z8002_device : public cpu_device +class z8002_device : public cpu_device, public z8000_disassembler::config { public: // construction/destruction @@ -41,12 +42,6 @@ public: template static devcb_base &set_mo_callback(device_t &device, Object &&cb) { return downcast(device).m_mo_out.set_callback(std::forward(cb)); } DECLARE_WRITE_LINE_MEMBER(mi_w) { m_mi = state; } // XXX: this has to apply in the middle of an insn for now - struct Z8000_dasm { char const *dasm; uint32_t flags; int size; }; - - static void init_tables(); - static void deinit_tables(); - static Z8000_dasm dasm(unsigned w); - protected: z8002_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock, int addrbits, int iobits, int vecmult); @@ -69,9 +64,9 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 6; } - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; + + void init_tables(); address_space_config m_program_config; address_space_config m_io_config; @@ -108,7 +103,7 @@ protected: void clear_internal_state(); void register_debug_state(); - virtual int segmented_mode(); + virtual bool get_segmented_mode() const override; static inline uint32_t addr_add(uint32_t addr, uint32_t addend); static inline uint32_t addr_sub(uint32_t addr, uint32_t subtrahend); inline uint16_t RDOP(); @@ -628,22 +623,14 @@ private: int beg, end, step; int size, cycles; opcode_func opcode; - const char *dasm; - uint32_t dasmflags; - }; - - /* structure for the opcode execution table / disassembler */ - struct Z8000_exec { - opcode_func opcode; - int cycles; - int size; - const char *dasm; - uint32_t dasmflags; }; /* opcode execution table */ static const Z8000_init table[]; - static std::unique_ptr z8000_exec; + u16 z8000_exec[0x10000]; + + /* zero, sign and parity flags for logical byte operations */ + u8 z8000_zsp[256]; }; @@ -661,12 +648,9 @@ protected: // device_memory_interface overrides virtual space_config_vector memory_space_config() const override; - // device_disasm_interface overrides - virtual uint32_t disasm_max_opcode_bytes() const override { return 8; } - address_space_config m_data_config; - virtual int segmented_mode() override; + virtual bool get_segmented_mode() const override; virtual uint32_t adjust_addr_for_nonseg_mode(uint32_t addr) override; virtual uint16_t RDPORT_W(int mode, uint16_t addr) override; virtual void WRPORT_W(int mode, uint16_t addr, uint16_t value) override; @@ -677,9 +661,6 @@ protected: virtual uint32_t F_SEG_Z8001() override; virtual uint32_t PSA_ADDR() override; virtual uint32_t read_irq_vector() override; - -private: - void z8k_disass_mode(int ref, const std::vector ¶ms); }; diff --git a/src/devices/cpu/z8000/z8000cpu.h b/src/devices/cpu/z8000/z8000cpu.h index 102cac41f0e..dc65a8dc3df 100644 --- a/src/devices/cpu/z8000/z8000cpu.h +++ b/src/devices/cpu/z8000/z8000cpu.h @@ -42,7 +42,7 @@ #define RQ(n) m_regs.Q[(n) >> 2] /* the register used as stack pointer */ -#define SP (segmented_mode() ? 14 : 15) +#define SP (get_segmented_mode() ? 14 : 15) /* these vectors are based on m_psap */ #define RST (PSA_ADDR() + 0) /* start up m_fcw and m_pc */ diff --git a/src/devices/cpu/z8000/z8000ops.hxx b/src/devices/cpu/z8000/z8000ops.hxx index bde18d4d70b..4599538525f 100644 --- a/src/devices/cpu/z8000/z8000ops.hxx +++ b/src/devices/cpu/z8000/z8000ops.hxx @@ -96,7 +96,7 @@ uint32_t z8002_device::segmented_addr(uint32_t addr) uint32_t z8002_device::addr_from_reg(int regno) { - if (segmented_mode()) + if (get_segmented_mode()) return segmented_addr(RL(regno)); else return RW(regno); @@ -104,7 +104,7 @@ uint32_t z8002_device::addr_from_reg(int regno) void z8002_device::addr_to_reg(int regno, uint32_t addr) { - if (segmented_mode()) { + if (get_segmented_mode()) { uint32_t segaddr = make_segmented_addr(addr); RW(regno) = (RW(regno) & 0x80ff) | ((segaddr >> 16) & 0x7f00); RW(regno | 1) = segaddr & 0xffff; @@ -115,21 +115,21 @@ void z8002_device::addr_to_reg(int regno, uint32_t addr) void z8002_device::add_to_addr_reg(int regno, uint16_t addend) { - if (segmented_mode()) + if (get_segmented_mode()) regno |= 1; RW(regno) += addend; } void z8002_device::sub_from_addr_reg(int regno, uint16_t subtrahend) { - if (segmented_mode()) + if (get_segmented_mode()) regno |= 1; RW(regno) -= subtrahend; } void z8002_device::set_pc(uint32_t addr) { - if (segmented_mode()) + if (get_segmented_mode()) m_pc = addr; else m_pc = (m_pc & 0xffff0000) | (addr & 0xffff); @@ -137,7 +137,7 @@ void z8002_device::set_pc(uint32_t addr) void z8002_device::PUSHW(uint8_t dst, uint16_t value) { - if (segmented_mode()) + if (get_segmented_mode()) RW(dst | 1) -= 2; else RW(dst) -= 2; @@ -147,7 +147,7 @@ void z8002_device::PUSHW(uint8_t dst, uint16_t value) uint16_t z8002_device::POPW(uint8_t src) { uint16_t result = RDMEM_W(AS_DATA, addr_from_reg(src)); - if (segmented_mode()) + if (get_segmented_mode()) RW(src | 1) += 2; else RW(src) += 2; @@ -156,7 +156,7 @@ uint16_t z8002_device::POPW(uint8_t src) void z8002_device::PUSHL(uint8_t dst, uint32_t value) { - if (segmented_mode()) + if (get_segmented_mode()) RW(dst | 1) -= 4; else RW(dst) -= 4; @@ -166,7 +166,7 @@ void z8002_device::PUSHL(uint8_t dst, uint32_t value) uint32_t z8002_device::POPL(uint8_t src) { uint32_t result = RDMEM_L(AS_DATA, addr_from_reg(src)); - if (segmented_mode()) + if (get_segmented_mode()) RW(src | 1) += 4; else RW(src) += 4; @@ -1971,7 +1971,7 @@ void z8002_device::Z1E_ddN0_cccc() void z8002_device::Z1F_ddN0_0000() { GET_DST(OP0,NIB2); - if (segmented_mode()) + if (get_segmented_mode()) PUSHL(SP, make_segmented_addr(m_pc)); else PUSHW(SP, m_pc); @@ -2361,7 +2361,7 @@ void z8002_device::Z34_ssN0_dddd_imm16() GET_DST(OP0,NIB3); GET_SRC(OP0,NIB2); GET_IDX16(OP1); - if (segmented_mode()) { + if (get_segmented_mode()) { RL(dst) = RL(src); } else { @@ -2465,7 +2465,7 @@ void z8002_device::Z39_ssN0_0000() CHECK_PRIVILEGED_INSTR(); GET_SRC(OP0,NIB2); uint16_t fcw; - if (segmented_mode()) { + if (get_segmented_mode()) { uint32_t addr = addr_from_reg(src); fcw = RDMEM_W(AS_DATA, addr + 2); set_pc(segmented_addr(RDMEM_L(AS_DATA, addr + 4))); @@ -3995,7 +3995,7 @@ void z8002_device::Z5E_ddN0_cccc_addr() void z8002_device::Z5F_0000_0000_addr() { GET_ADDR(OP1); - if (segmented_mode()) + if (get_segmented_mode()) PUSHL(SP, make_segmented_addr(m_pc)); else PUSHW(SP, m_pc); @@ -4010,7 +4010,7 @@ void z8002_device::Z5F_ddN0_0000_addr() { GET_DST(OP0,NIB2); GET_ADDR(OP1); - if (segmented_mode()) + if (get_segmented_mode()) PUSHL(SP, make_segmented_addr(m_pc)); else PUSHW(SP, m_pc); @@ -4469,7 +4469,7 @@ void z8002_device::Z74_ssN0_dddd_0000_xxxx_0000_0000() GET_DST(OP0,NIB3); GET_SRC(OP0,NIB2); GET_IDX(OP1,NIB1); - if (segmented_mode()) { + if (get_segmented_mode()) { RL(dst) = RL(src); } else { @@ -4498,7 +4498,7 @@ void z8002_device::Z76_0000_dddd_addr() { GET_DST(OP0,NIB3); GET_ADDR_RAW(OP1); - if (segmented_mode()) { + if (get_segmented_mode()) { RL(dst) = addr; } else { @@ -4516,7 +4516,7 @@ void z8002_device::Z76_ssN0_dddd_addr() GET_SRC(OP0,NIB2); GET_ADDR_RAW(OP1); uint16_t temp = RW(src); // store src in case dst == src - if (segmented_mode()) { + if (get_segmented_mode()) { RL(dst) = addr; } else { @@ -4560,7 +4560,7 @@ void z8002_device::Z79_0000_0000_addr() CHECK_PRIVILEGED_INSTR(); GET_ADDR(OP1); uint16_t fcw; - if (segmented_mode()) { + if (get_segmented_mode()) { fcw = RDMEM_W(AS_DATA, addr + 2); set_pc(segmented_addr(RDMEM_L(AS_DATA, addr + 4))); } @@ -4582,7 +4582,7 @@ void z8002_device::Z79_ssN0_0000_addr() GET_ADDR(OP1); uint16_t fcw; addr = addr_add(addr, RW(src)); - if (segmented_mode()) { + if (get_segmented_mode()) { fcw = RDMEM_W(AS_DATA, addr + 2); set_pc(segmented_addr(RDMEM_L(AS_DATA, addr + 4))); } @@ -4615,7 +4615,7 @@ void z8002_device::Z7B_0000_0000() CHECK_PRIVILEGED_INSTR(); tag = POPW(SP); /* get type tag */ fcw = POPW(SP); /* get m_fcw */ - if (segmented_mode()) + if (get_segmented_mode()) set_pc(segmented_addr(POPL(SP))); else m_pc = POPW(SP); /* get m_pc */ @@ -5289,7 +5289,7 @@ void z8002_device::Z9D_imm8() void z8002_device::Z9E_0000_cccc() { GET_CCC(OP0,NIB3); - if (segmented_mode()) + if (get_segmented_mode()) switch (cc) { case 0: if (CC0) set_pc(segmented_addr(POPL(SP))); break; case 1: if (CC1) set_pc(segmented_addr(POPL(SP))); break; @@ -6746,7 +6746,7 @@ void z8002_device::ZC_dddd_imm8() void z8002_device::ZD_dsp12() { int16_t dsp12 = m_op[0] & 0xfff; - if (segmented_mode()) + if (get_segmented_mode()) PUSHL(SP, make_segmented_addr(m_pc)); else PUSHW(SP, m_pc); diff --git a/src/devices/cpu/z8000/z8000tbl.hxx b/src/devices/cpu/z8000/z8000tbl.hxx index 7ebbeb4d071..0d54009a7f4 100644 --- a/src/devices/cpu/z8000/z8000tbl.hxx +++ b/src/devices/cpu/z8000/z8000tbl.hxx @@ -9,583 +9,525 @@ *****************************************************************************/ const z8002_device::Z8000_init z8002_device::table[] = { -{0x0000,0x000f, 1,2, 7,&z8002_device::Z00_0000_dddd_imm8, "addb %rb3,%#b3", 0}, -{0x0010,0x00ff, 1,1, 7,&z8002_device::Z00_ssN0_dddd, "addb %rb3,@%rw2", 0}, -{0x0100,0x010f, 1,2, 7,&z8002_device::Z01_0000_dddd_imm16, "add %rw3,%#w1", 0}, -{0x0110,0x01ff, 1,1, 7,&z8002_device::Z01_ssN0_dddd, "add %rw3,@%rw2", 0}, -{0x0200,0x020f, 1,2, 7,&z8002_device::Z02_0000_dddd_imm8, "subb %rb3,%#b3", 0}, -{0x0210,0x02ff, 1,1, 7,&z8002_device::Z02_ssN0_dddd, "subb %rb3,@%rw2", 0}, -{0x0300,0x030f, 1,2, 7,&z8002_device::Z03_0000_dddd_imm16, "sub %rw3,%#w1", 0}, -{0x0310,0x03ff, 1,1, 7,&z8002_device::Z03_ssN0_dddd, "sub %rw3,@%rw2", 0}, -{0x0400,0x040f, 1,2, 7,&z8002_device::Z04_0000_dddd_imm8, "orb %rb3,%#b3", 0}, -{0x0410,0x04ff, 1,1, 7,&z8002_device::Z04_ssN0_dddd, "orb %rb3,@%rw2", 0}, -{0x0500,0x050f, 1,2, 7,&z8002_device::Z05_0000_dddd_imm16, "or %rw3,%#w1", 0}, -{0x0510,0x05ff, 1,1, 7,&z8002_device::Z05_ssN0_dddd, "or %rw3,@%rw2", 0}, -{0x0600,0x060f, 1,2, 7,&z8002_device::Z06_0000_dddd_imm8, "andb %rb3,%#b3", 0}, -{0x0610,0x06ff, 1,1, 7,&z8002_device::Z06_ssN0_dddd, "andb %rb3,@%rw2", 0}, -{0x0700,0x070f, 1,2, 7,&z8002_device::Z07_0000_dddd_imm16, "and %rw3,%#w1", 0}, -{0x0710,0x07ff, 1,1, 7,&z8002_device::Z07_ssN0_dddd, "and %rw3,@%rw2", 0}, -{0x0800,0x080f, 1,2, 7,&z8002_device::Z08_0000_dddd_imm8, "xorb %rb3,%#b3", 0}, -{0x0810,0x08ff, 1,1, 7,&z8002_device::Z08_ssN0_dddd, "xorb %rb3,@%rw2", 0}, -{0x0900,0x090f, 1,2, 7,&z8002_device::Z09_0000_dddd_imm16, "xor %rw3,%#w1", 0}, -{0x0910,0x09ff, 1,1, 7,&z8002_device::Z09_ssN0_dddd, "xor %rw3,@%rw2", 0}, -{0x0a00,0x0a0f, 1,2, 7,&z8002_device::Z0A_0000_dddd_imm8, "cpb %rb3,%#b3", 0}, -{0x0a10,0x0aff, 1,1, 7,&z8002_device::Z0A_ssN0_dddd, "cpb %rb3,@%rw2", 0}, -{0x0b00,0x0b0f, 1,2, 7,&z8002_device::Z0B_0000_dddd_imm16, "cp %rw3,%#w1", 0}, -{0x0b10,0x0bff, 1,1, 7,&z8002_device::Z0B_ssN0_dddd, "cp %rw3,@%rw2", 0}, -{0x0c10,0x0cf0,16,1, 12,&z8002_device::Z0C_ddN0_0000, "comb @%rw2", 0}, -{0x0c11,0x0cf1,16,2, 11,&z8002_device::Z0C_ddN0_0001_imm8, "cpb @%rw2,%#b3", 0}, -{0x0c12,0x0cf2,16,1, 12,&z8002_device::Z0C_ddN0_0010, "negb @%rw2", 0}, -{0x0c14,0x0cf4,16,1, 8,&z8002_device::Z0C_ddN0_0100, "testb @%rw2", 0}, -{0x0c15,0x0cf5,16,2, 7,&z8002_device::Z0C_ddN0_0101_imm8, "ldb @%rw2,%#b3", 0}, -{0x0c16,0x0cf6,16,1, 11,&z8002_device::Z0C_ddN0_0110, "tsetb @%rw2", 0}, -{0x0c18,0x0cf8,16,1, 8,&z8002_device::Z0C_ddN0_1000, "clrb @%rw2", 0}, -{0x0d10,0x0df0,16,1, 12,&z8002_device::Z0D_ddN0_0000, "com @%rw2", 0}, -{0x0d11,0x0df1,16,2, 11,&z8002_device::Z0D_ddN0_0001_imm16, "cp @%rw2,%#w1", 0}, -{0x0d12,0x0df2,16,1, 12,&z8002_device::Z0D_ddN0_0010, "neg @%rw2", 0}, -{0x0d14,0x0df4,16,1, 8,&z8002_device::Z0D_ddN0_0100, "test @%rw2", 0}, -{0x0d15,0x0df5,16,2, 11,&z8002_device::Z0D_ddN0_0101_imm16, "ld @%rw2,%#w1", 0}, /* fix cycles ld IR,IM */ -{0x0d16,0x0df6,16,1, 11,&z8002_device::Z0D_ddN0_0110, "tset @%rw2", 0}, -{0x0d18,0x0df8,16,1, 8,&z8002_device::Z0D_ddN0_1000, "clr @%rw2", 0}, -{0x0d19,0x0df9,16,2, 12,&z8002_device::Z0D_ddN0_1001_imm16, "push @%rw2,%#w1", 0}, -{0x0e00,0x0eff, 1,1, 10,&z8002_device::Z0E_imm8, "ext0e %#b1", 0}, -{0x0f00,0x0fff, 1,1, 10,&z8002_device::Z0F_imm8, "ext0f %#b1", 0}, -{0x1000,0x100f, 1,3, 14,&z8002_device::Z10_0000_dddd_imm32, "cpl %rl3,%#l1", 0}, -{0x1010,0x10ff, 1,1, 14,&z8002_device::Z10_ssN0_dddd, "cpl %rl3,@%rw2", 0}, -{0x1111,0x11ff, 1,1, 20,&z8002_device::Z11_ddN0_ssN0, "pushl @%rw2,@%rw3", 0}, -{0x1200,0x120f, 1,3, 14,&z8002_device::Z12_0000_dddd_imm32, "subl %rl3,%#l1", 0}, -{0x1210,0x12ff, 1,1, 14,&z8002_device::Z12_ssN0_dddd, "subl %rl3,@%rw2", 0}, -{0x1311,0x13ff, 1,1, 13,&z8002_device::Z13_ddN0_ssN0, "push @%rw2,@%rw3", 0}, -{0x1400,0x140f, 1,3, 11,&z8002_device::Z14_0000_dddd_imm32, "ldl %rl3,%#l1", 0}, -{0x1410,0x14ff, 1,1, 11,&z8002_device::Z14_ssN0_dddd, "ldl %rl3,@%rw2", 0}, -{0x1511,0x15ff, 1,1, 19,&z8002_device::Z15_ssN0_ddN0, "popl @%rw3,@%rw2", 0}, -{0x1600,0x160f, 1,3, 14,&z8002_device::Z16_0000_dddd_imm32, "addl %rl3,%#l1", 0}, -{0x1610,0x16ff, 1,1, 14,&z8002_device::Z16_ssN0_dddd, "addl %rl3,@%rw2", 0}, -{0x1711,0x17ff, 1,1, 12,&z8002_device::Z17_ssN0_ddN0, "pop @%rw3,@%rw2", 0}, -{0x1800,0x180f, 1,1,282,&z8002_device::Z18_00N0_dddd_imm32, "multl %rq3,@%l#1", 0}, -{0x1810,0x18ff, 1,1,282,&z8002_device::Z18_ssN0_dddd, "multl %rq3,@%rw2", 0}, -{0x1900,0x190f, 1,2, 70,&z8002_device::Z19_0000_dddd_imm16, "mult %rl3,%#w1", 0}, -{0x1910,0x19ff, 1,1, 70,&z8002_device::Z19_ssN0_dddd, "mult %rl3,@%rw2", 0}, -{0x1a00,0x1a0f, 1,3,744,&z8002_device::Z1A_0000_dddd_imm32, "divl %rq3,%#l1", 0}, -{0x1a10,0x1aff, 1,1,744,&z8002_device::Z1A_ssN0_dddd, "divl %rq3,@%rw2", 0}, -{0x1b00,0x1b0f, 1,2,107,&z8002_device::Z1B_0000_dddd_imm16, "div %rl3,%#w1", 0}, -{0x1b10,0x1bff, 1,1,107,&z8002_device::Z1B_ssN0_dddd, "div %rl3,@%rw2", 0}, -{0x1c11,0x1cf1,16,2, 11,&z8002_device::Z1C_ssN0_0001_0000_dddd_0000_nmin1, "ldm %rw5,@%rw2,#%n", 0}, -{0x1c18,0x1cf8,16,1, 13,&z8002_device::Z1C_ddN0_1000, "testl @%rw2", 0}, -{0x1c19,0x1cf9,16,2, 11,&z8002_device::Z1C_ddN0_1001_0000_ssss_0000_nmin1, "ldm @%rw2,%rw5,#%n", 0}, -{0x1d10,0x1dff, 1,1, 11,&z8002_device::Z1D_ddN0_ssss, "ldl @%rw2,%rl3", 0}, -{0x1e10,0x1eff, 1,1, 10,&z8002_device::Z1E_ddN0_cccc, "jp %c3,@%rl2", 0}, -{0x1f10,0x1ff0,16,1, 10,&z8002_device::Z1F_ddN0_0000, "call %rw2", DASMFLAG_STEP_OVER}, -{0x2000,0x200f, 1,2, 7,&z8002_device::Z20_0000_dddd_imm8, "ldb %rb3,%#b3", 0}, -{0x2010,0x20ff, 1,1, 7,&z8002_device::Z20_ssN0_dddd, "ldb %rb3,@%rw2", 0}, -{0x2100,0x210f, 1,2, 7,&z8002_device::Z21_0000_dddd_imm16, "ld %rw3,%#w1", 0}, -{0x2110,0x21ff, 1,1, 7,&z8002_device::Z21_ssN0_dddd, "ld %rw3,@%rw2", 0}, -{0x2200,0x220f, 1,2, 10,&z8002_device::Z22_0000_ssss_0000_dddd_0000_0000, "resb %rb5,%rw3", 0}, -{0x2210,0x22ff, 1,1, 11,&z8002_device::Z22_ddN0_imm4, "resb @%rw2,%3", 0}, -{0x2300,0x230f, 1,2, 10,&z8002_device::Z23_0000_ssss_0000_dddd_0000_0000, "res %rw5,%rw3", 0}, -{0x2310,0x23ff, 1,1, 11,&z8002_device::Z23_ddN0_imm4, "res @%rw2,%3", 0}, -{0x2400,0x240f, 1,2, 10,&z8002_device::Z24_0000_ssss_0000_dddd_0000_0000, "setb %rb5,%rw3", 0}, -{0x2410,0x24ff, 1,1, 11,&z8002_device::Z24_ddN0_imm4, "setb @%rw2,%3", 0}, -{0x2500,0x250f, 1,2, 10,&z8002_device::Z25_0000_ssss_0000_dddd_0000_0000, "set %rw5,%rw3", 0}, -{0x2510,0x25ff, 1,1, 11,&z8002_device::Z25_ddN0_imm4, "set @%rw2,%3", 0}, -{0x2600,0x260f, 1,2, 10,&z8002_device::Z26_0000_ssss_0000_dddd_0000_0000, "bitb %rb5,%rw3", 0}, -{0x2610,0x26ff, 1,1, 8,&z8002_device::Z26_ddN0_imm4, "bitb @%rw2,%3", 0}, -{0x2700,0x270f, 1,2, 10,&z8002_device::Z27_0000_ssss_0000_dddd_0000_0000, "bit %rw5,%rw3", 0}, -{0x2710,0x27ff, 1,1, 8,&z8002_device::Z27_ddN0_imm4, "bit @%rw2,%3", 0}, -{0x2810,0x28ff, 1,1, 11,&z8002_device::Z28_ddN0_imm4m1, "incb @%rw2,%+3", 0}, -{0x2910,0x29ff, 1,1, 11,&z8002_device::Z29_ddN0_imm4m1, "inc @%rw2,%+3", 0}, -{0x2a10,0x2aff, 1,1, 11,&z8002_device::Z2A_ddN0_imm4m1, "decb @%rw2,%+3", 0}, -{0x2b10,0x2bff, 1,1, 11,&z8002_device::Z2B_ddN0_imm4m1, "dec @%rw2,%+3", 0}, -{0x2c10,0x2cff, 1,1, 12,&z8002_device::Z2C_ssN0_dddd, "exb %rb3,@%rw2", 0}, -{0x2d10,0x2dff, 1,1, 12,&z8002_device::Z2D_ssN0_dddd, "ex %rw3,@%rw2", 0}, -{0x2e10,0x2eff, 1,1, 8,&z8002_device::Z2E_ddN0_ssss, "ldb @%rw2,%rb3", 0}, -{0x2f10,0x2fff, 1,1, 8,&z8002_device::Z2F_ddN0_ssss, "ld @%rw2,%rw3", 0}, -{0x3000,0x300f, 1,2, 14,&z8002_device::Z30_0000_dddd_dsp16, "ldrb %rb3,%p1", 0}, -{0x3010,0x30ff, 1,2, 14,&z8002_device::Z30_ssN0_dddd_imm16, "ldb %rb3,%rw2(%#w1)", 0}, -{0x3100,0x310f, 1,2, 14,&z8002_device::Z31_0000_dddd_dsp16, "ldr %rw3,%p1", 0}, -{0x3110,0x31ff, 1,2, 14,&z8002_device::Z31_ssN0_dddd_imm16, "ld %rw3,%rw2(%#w1)", 0}, -{0x3200,0x320f, 1,2, 14,&z8002_device::Z32_0000_ssss_dsp16, "ldrb %p1,%rb3", 0}, -{0x3210,0x32ff, 1,2, 14,&z8002_device::Z32_ddN0_ssss_imm16, "ldb %rw2(%#w1),%rb3", 0}, -{0x3300,0x330f, 1,2, 14,&z8002_device::Z33_0000_ssss_dsp16, "ldr %p1,%rw3", 0}, -{0x3310,0x33ff, 1,2, 14,&z8002_device::Z33_ddN0_ssss_imm16, "ld %rw2(%#w1),%rw3", 0}, -{0x3400,0x340f, 1,2, 15,&z8002_device::Z34_0000_dddd_dsp16, "ldar p%rw3,%p1", 0}, -{0x3410,0x34ff, 1,2, 15,&z8002_device::Z34_ssN0_dddd_imm16, "lda p%rw3,%rw2(%#w1)", 0}, -{0x3500,0x350f, 1,2, 17,&z8002_device::Z35_0000_dddd_dsp16, "ldrl %rl3,%p1", 0}, -{0x3510,0x35ff, 1,2, 17,&z8002_device::Z35_ssN0_dddd_imm16, "ldl %rl3,%rw2(%#w1)", 0}, -{0x3600,0x3600, 1,1, 2,&z8002_device::Z36_0000_0000, "bpt", 0}, -{0x3601,0x36ff, 1,1, 10,&z8002_device::Z36_imm8, "rsvd36", 0}, -{0x3700,0x370f, 1,2, 17,&z8002_device::Z37_0000_ssss_dsp16, "ldrl %p1,%rl3", 0}, -{0x3710,0x37ff, 1,2, 17,&z8002_device::Z37_ddN0_ssss_imm16, "ldl %rw2(%#w1),%rl3", 0}, -{0x3800,0x38ff, 1,1, 10,&z8002_device::Z38_imm8, "rsvd38", 0}, -{0x3910,0x39f0,16,1, 12,&z8002_device::Z39_ssN0_0000, "ldps @%rw2", 0}, -{0x3a00,0x3af0,16,2, 21,&z8002_device::Z3A_ssss_0000_0000_aaaa_dddd_x000, "%R @%rw6,@%rw2,%rw5", 0}, -{0x3a01,0x3af1,16,2, 21,&z8002_device::Z3A_ssss_0001_0000_aaaa_dddd_x000, "%R @%rw6,@%rw2,%rw5", 0}, -{0x3a02,0x3af2,16,2, 21,&z8002_device::Z3A_ssss_0010_0000_aaaa_dddd_x000, "%R @%rw6,@%rw2,%rw5", 0}, -{0x3a03,0x3af3,16,2, 21,&z8002_device::Z3A_ssss_0011_0000_aaaa_dddd_x000, "%R @%rw6,@%rw2,%rw5", 0}, -{0x3a04,0x3af4,16,2, 10,&z8002_device::Z3A_dddd_0100_imm16, "%R %rb2,%#w1", 0}, -{0x3a05,0x3af5,16,2, 10,&z8002_device::Z3A_dddd_0101_imm16, "%R %rb2,%#w1", 0}, -{0x3a06,0x3af6,16,2, 12,&z8002_device::Z3A_ssss_0110_imm16, "%R %#w1,%rb2", 0}, -{0x3a07,0x3af7,16,2, 12,&z8002_device::Z3A_ssss_0111_imm16, "%R %#w1,%rb2", 0}, -{0x3a08,0x3af8,16,2, 21,&z8002_device::Z3A_ssss_1000_0000_aaaa_dddd_x000, "%R @%rw6,@%rw2,%rw5", 0}, -{0x3a09,0x3af9,16,2, 21,&z8002_device::Z3A_ssss_1001_0000_aaaa_dddd_x000, "%R @%rw6,@%rw2,%rw5", 0}, -{0x3a0a,0x3afa,16,2, 21,&z8002_device::Z3A_ssss_1010_0000_aaaa_dddd_x000, "%R @%rw6,@%rw2,%rw5", 0}, -{0x3a0b,0x3afb,16,2, 21,&z8002_device::Z3A_ssss_1011_0000_aaaa_dddd_x000, "%R @%rw6,@%rw2,%rw5", 0}, -{0x3b00,0x3bf0,16,2, 21,&z8002_device::Z3B_ssss_0000_0000_aaaa_dddd_x000, "%R @%rw6,@%rw2,%rw5", 0}, -{0x3b01,0x3bf1,16,2, 21,&z8002_device::Z3B_ssss_0001_0000_aaaa_dddd_x000, "%R @%rw6,@%rw2,%rw5", 0}, -{0x3b02,0x3bf2,16,2, 21,&z8002_device::Z3B_ssss_0010_0000_aaaa_dddd_x000, "%R @%rw6,@%rw2,%rw5", 0}, -{0x3b03,0x3bf3,16,2, 21,&z8002_device::Z3B_ssss_0011_0000_aaaa_dddd_x000, "%R @%rw6,@%rw2,%rw5", 0}, -{0x3b04,0x3bf4,16,2, 12,&z8002_device::Z3B_dddd_0100_imm16, "%R %rw2,%#w1", 0}, -{0x3b05,0x3bf5,16,2, 12,&z8002_device::Z3B_dddd_0101_imm16, "%R %rw2,%#w1", 0}, -{0x3b06,0x3bf6,16,2, 12,&z8002_device::Z3B_ssss_0110_imm16, "%R %#w1,%rw2", 0}, -{0x3b07,0x3bf7,16,2, 12,&z8002_device::Z3B_ssss_0111_imm16, "%R %#w1,%rw2", 0}, -{0x3b08,0x3bf8,16,2, 21,&z8002_device::Z3B_ssss_1000_0000_aaaa_dddd_x000, "%R @%rw6,@%rw2,%rw5", 0}, -{0x3b09,0x3bf9,16,2, 21,&z8002_device::Z3B_ssss_1001_0000_aaaa_dddd_x000, "%R @%rw6,@%rw2,%rw5", 0}, -{0x3b0a,0x3bfa,16,2, 21,&z8002_device::Z3B_ssss_1010_0000_aaaa_dddd_x000, "%R @%rw6,@%rw2,%rb5", 0}, -{0x3b0b,0x3bfb,16,2, 21,&z8002_device::Z3B_ssss_1011_0000_aaaa_dddd_x000, "%R @%rw6,@%rw2,%rb5", 0}, -{0x3c00,0x3cff, 1,1, 10,&z8002_device::Z3C_ssss_dddd, "inb %rb3,@%rw2", 0}, -{0x3d00,0x3dff, 1,1, 10,&z8002_device::Z3D_ssss_dddd, "in %rw3,@%rw2", 0}, -{0x3e00,0x3eff, 1,1, 12,&z8002_device::Z3E_dddd_ssss, "outb @%rw2,%rb3", 0}, -{0x3f00,0x3fff, 1,1, 12,&z8002_device::Z3F_dddd_ssss, "out @%rw2,%rw3", 0}, -{0x4000,0x400f, 1,2, 9,&z8002_device::Z40_0000_dddd_addr, "addb %rb3,%a1", 0}, -{0x4010,0x40ff, 1,2, 10,&z8002_device::Z40_ssN0_dddd_addr, "addb %rb3,%a1(%rw2)", 0}, -{0x4100,0x410f, 1,2, 9,&z8002_device::Z41_0000_dddd_addr, "add %rw3,%a1", 0}, -{0x4110,0x41ff, 1,2, 10,&z8002_device::Z41_ssN0_dddd_addr, "add %rw3,%a1(%rw2)", 0}, -{0x4200,0x420f, 1,2, 9,&z8002_device::Z42_0000_dddd_addr, "subb %rb3,%a1", 0}, -{0x4210,0x42ff, 1,2, 10,&z8002_device::Z42_ssN0_dddd_addr, "subb %rb3,%a1(%rw2)", 0}, -{0x4300,0x430f, 1,2, 9,&z8002_device::Z43_0000_dddd_addr, "sub %rw3,%a1", 0}, -{0x4310,0x43ff, 1,2, 10,&z8002_device::Z43_ssN0_dddd_addr, "sub %rw3,%a1(%rw2)", 0}, -{0x4400,0x440f, 1,2, 9,&z8002_device::Z44_0000_dddd_addr, "orb %rb3,%a1", 0}, -{0x4410,0x44ff, 1,2, 10,&z8002_device::Z44_ssN0_dddd_addr, "orb %rb3,%a1(%rw2)", 0}, -{0x4500,0x450f, 1,2, 9,&z8002_device::Z45_0000_dddd_addr, "or %rw3,%a1", 0}, -{0x4510,0x45ff, 1,2, 10,&z8002_device::Z45_ssN0_dddd_addr, "or %rw3,%a1(%rw2)", 0}, -{0x4600,0x460f, 1,2, 9,&z8002_device::Z46_0000_dddd_addr, "andb %rb3,%a1", 0}, -{0x4610,0x46ff, 1,2, 10,&z8002_device::Z46_ssN0_dddd_addr, "andb %rb3,%a1(%rw2)", 0}, -{0x4700,0x470f, 1,2, 9,&z8002_device::Z47_0000_dddd_addr, "and %rw3,%a1", 0}, -{0x4710,0x47ff, 1,2, 10,&z8002_device::Z47_ssN0_dddd_addr, "and %rw3,%a1(%rw2)", 0}, -{0x4800,0x480f, 1,2, 9,&z8002_device::Z48_0000_dddd_addr, "xorb %rb3,%a1", 0}, -{0x4810,0x48ff, 1,2, 10,&z8002_device::Z48_ssN0_dddd_addr, "xorb %rb3,%a1(%rw2)", 0}, -{0x4900,0x490f, 1,2, 9,&z8002_device::Z49_0000_dddd_addr, "xor %rw3,%a1", 0}, -{0x4910,0x49ff, 1,2, 10,&z8002_device::Z49_ssN0_dddd_addr, "xor %rw3,%a1(%rw2)", 0}, -{0x4a00,0x4a0f, 1,2, 9,&z8002_device::Z4A_0000_dddd_addr, "cpb %rb3,%a1", 0}, -{0x4a10,0x4aff, 1,2, 10,&z8002_device::Z4A_ssN0_dddd_addr, "cpb %rb3,%a1(%rw2)", 0}, -{0x4b00,0x4b0f, 1,2, 9,&z8002_device::Z4B_0000_dddd_addr, "cp %rw3,%a1", 0}, -{0x4b10,0x4bff, 1,2, 10,&z8002_device::Z4B_ssN0_dddd_addr, "cp %rw3,%a1(%rw2)", 0}, -{0x4c00,0x4c00, 1,2, 15,&z8002_device::Z4C_0000_0000_addr, "comb %a1", 0}, -{0x4c01,0x4c01, 1,3, 14,&z8002_device::Z4C_0000_0001_addr_imm8, "cpb %a1,%#b3", 0}, -{0x4c02,0x4c02, 1,2, 15,&z8002_device::Z4C_0000_0010_addr, "negb %a1", 0}, -{0x4c04,0x4c04, 1,2, 11,&z8002_device::Z4C_0000_0100_addr, "testb %a1", 0}, -{0x4c05,0x4c05, 1,3, 14,&z8002_device::Z4C_0000_0101_addr_imm8, "ldb %a1,%#b3", 0}, -{0x4c06,0x4c06, 1,2, 14,&z8002_device::Z4C_0000_0110_addr, "tsetb %a1", 0}, -{0x4c08,0x4c08, 1,2, 11,&z8002_device::Z4C_0000_1000_addr, "clrb %a1", 0}, -{0x4c10,0x4cf0,16,2, 16,&z8002_device::Z4C_ddN0_0000_addr, "comb %a1(%rw2)", 0}, -{0x4c11,0x4cf1,16,3, 15,&z8002_device::Z4C_ddN0_0001_addr_imm8, "cpb %a1(%rw2),%#b3", 0}, -{0x4c12,0x4cf2,16,2, 16,&z8002_device::Z4C_ddN0_0010_addr, "negb %a1(%rw2)", 0}, -{0x4c14,0x4cf4,16,2, 12,&z8002_device::Z4C_ddN0_0100_addr, "testb %a1(%rw2)", 0}, -{0x4c15,0x4cf5,16,3, 15,&z8002_device::Z4C_ddN0_0101_addr_imm8, "ldb %a1(%rw2),%#b3", 0}, -{0x4c16,0x4cf6,16,2, 15,&z8002_device::Z4C_ddN0_0110_addr, "tsetb %a1(%rw2)", 0}, -{0x4c18,0x4cf8,16,2, 12,&z8002_device::Z4C_ddN0_1000_addr, "clrb %a1(%rw2)", 0}, -{0x4d00,0x4d00, 1,2, 15,&z8002_device::Z4D_0000_0000_addr, "com %a1", 0}, -{0x4d01,0x4d01, 1,3, 14,&z8002_device::Z4D_0000_0001_addr_imm16, "cp %a1,%#w2", 0}, -{0x4d02,0x4d02, 1,2, 15,&z8002_device::Z4D_0000_0010_addr, "neg %a1", 0}, -{0x4d04,0x4d04, 1,2, 11,&z8002_device::Z4D_0000_0100_addr, "test %a1", 0}, -{0x4d05,0x4d05, 1,3, 14,&z8002_device::Z4D_0000_0101_addr_imm16, "ld %a1,%#w2", 0}, -{0x4d06,0x4d06, 1,2, 14,&z8002_device::Z4D_0000_0110_addr, "tset %a1", 0}, -{0x4d08,0x4d08, 1,2, 11,&z8002_device::Z4D_0000_1000_addr, "clr %a1", 0}, -{0x4d10,0x4df0,16,2, 16,&z8002_device::Z4D_ddN0_0000_addr, "com %a1(%rw2)", 0}, -{0x4d11,0x4df1,16,3, 15,&z8002_device::Z4D_ddN0_0001_addr_imm16, "cp %a1(%rw2),%#w2", 0}, -{0x4d12,0x4df2,16,2, 16,&z8002_device::Z4D_ddN0_0010_addr, "neg %a1(%rw2)", 0}, -{0x4d14,0x4df4,16,2, 12,&z8002_device::Z4D_ddN0_0100_addr, "test %a1(%rw2)", 0}, -{0x4d15,0x4df5,16,3, 15,&z8002_device::Z4D_ddN0_0101_addr_imm16, "ld %a1(%rw2),%#w2", 0}, -{0x4d16,0x4df6,16,2, 15,&z8002_device::Z4D_ddN0_0110_addr, "tset %a1(%rw2)", 0}, -{0x4d18,0x4df8,16,2, 12,&z8002_device::Z4D_ddN0_1000_addr, "clr %a1(%rw2)", 0}, -{0x4e11,0x4ef0,16,2, 12,&z8002_device::Z4E_ddN0_ssN0_addr, "ldb %a1(%rw2),%rb3", 0}, -{0x5000,0x500f, 1,2, 15,&z8002_device::Z50_0000_dddd_addr, "cpl %rl3,%a1", 0}, -{0x5010,0x50ff, 1,2, 16,&z8002_device::Z50_ssN0_dddd_addr, "cpl %rl3,%a1(%rw2)", 0}, -{0x5110,0x51f0,16,2, 21,&z8002_device::Z51_ddN0_0000_addr, "pushl @%rw2,%a1", 0}, -{0x5111,0x51f1,16,2, 21,&z8002_device::Z51_ddN0_ssN0_addr, "pushl @%rw2,%a1(%rw3)", 0}, -{0x5112,0x51f2,16,2, 21,&z8002_device::Z51_ddN0_ssN0_addr, "pushl @%rw2,%a1(%rw3)", 0}, -{0x5113,0x51f3,16,2, 21,&z8002_device::Z51_ddN0_ssN0_addr, "pushl @%rw2,%a1(%rw3)", 0}, -{0x5114,0x51f4,16,2, 21,&z8002_device::Z51_ddN0_ssN0_addr, "pushl @%rw2,%a1(%rw3)", 0}, -{0x5115,0x51f5,16,2, 21,&z8002_device::Z51_ddN0_ssN0_addr, "pushl @%rw2,%a1(%rw3)", 0}, -{0x5116,0x51f6,16,2, 21,&z8002_device::Z51_ddN0_ssN0_addr, "pushl @%rw2,%a1(%rw3)", 0}, -{0x5117,0x51f7,16,2, 21,&z8002_device::Z51_ddN0_ssN0_addr, "pushl @%rw2,%a1(%rw3)", 0}, -{0x5118,0x51f8,16,2, 21,&z8002_device::Z51_ddN0_ssN0_addr, "pushl @%rw2,%a1(%rw3)", 0}, -{0x5119,0x51f9,16,2, 21,&z8002_device::Z51_ddN0_ssN0_addr, "pushl @%rw2,%a1(%rw3)", 0}, -{0x511a,0x51fa,16,2, 21,&z8002_device::Z51_ddN0_ssN0_addr, "pushl @%rw2,%a1(%rw3)", 0}, -{0x511b,0x51fb,16,2, 21,&z8002_device::Z51_ddN0_ssN0_addr, "pushl @%rw2,%a1(%rw3)", 0}, -{0x511c,0x51fc,16,2, 21,&z8002_device::Z51_ddN0_ssN0_addr, "pushl @%rw2,%a1(%rw3)", 0}, -{0x511d,0x51fd,16,2, 21,&z8002_device::Z51_ddN0_ssN0_addr, "pushl @%rw2,%a1(%rw3)", 0}, -{0x511e,0x51fe,16,2, 21,&z8002_device::Z51_ddN0_ssN0_addr, "pushl @%rw2,%a1(%rw3)", 0}, -{0x511f,0x51ff,16,2, 21,&z8002_device::Z51_ddN0_ssN0_addr, "pushl @%rw2,%a1(%rw3)", 0}, -{0x5200,0x520f, 1,2, 15,&z8002_device::Z52_0000_dddd_addr, "subl %rl3,%a1", 0}, -{0x5210,0x52ff, 1,2, 16,&z8002_device::Z52_ssN0_dddd_addr, "subl %rl3,%a1(%rw2)", 0}, -{0x5310,0x53f0,16,2, 14,&z8002_device::Z53_ddN0_0000_addr, "push @%rw2,%a1", 0}, -{0x5311,0x53f1,16,2, 14,&z8002_device::Z53_ddN0_ssN0_addr, "push @%rw2,%a1(%rw3)", 0}, -{0x5312,0x53f2,16,2, 14,&z8002_device::Z53_ddN0_ssN0_addr, "push @%rw2,%a1(%rw3)", 0}, -{0x5313,0x53f3,16,2, 14,&z8002_device::Z53_ddN0_ssN0_addr, "push @%rw2,%a1(%rw3)", 0}, -{0x5314,0x53f4,16,2, 14,&z8002_device::Z53_ddN0_ssN0_addr, "push @%rw2,%a1(%rw3)", 0}, -{0x5315,0x53f5,16,2, 14,&z8002_device::Z53_ddN0_ssN0_addr, "push @%rw2,%a1(%rw3)", 0}, -{0x5316,0x53f6,16,2, 14,&z8002_device::Z53_ddN0_ssN0_addr, "push @%rw2,%a1(%rw3)", 0}, -{0x5317,0x53f7,16,2, 14,&z8002_device::Z53_ddN0_ssN0_addr, "push @%rw2,%a1(%rw3)", 0}, -{0x5318,0x53f8,16,2, 14,&z8002_device::Z53_ddN0_ssN0_addr, "push @%rw2,%a1(%rw3)", 0}, -{0x5319,0x53f9,16,2, 14,&z8002_device::Z53_ddN0_ssN0_addr, "push @%rw2,%a1(%rw3)", 0}, -{0x531a,0x53fa,16,2, 14,&z8002_device::Z53_ddN0_ssN0_addr, "push @%rw2,%a1(%rw3)", 0}, -{0x531b,0x53fb,16,2, 14,&z8002_device::Z53_ddN0_ssN0_addr, "push @%rw2,%a1(%rw3)", 0}, -{0x531c,0x53fc,16,2, 14,&z8002_device::Z53_ddN0_ssN0_addr, "push @%rw2,%a1(%rw3)", 0}, -{0x531d,0x53fd,16,2, 14,&z8002_device::Z53_ddN0_ssN0_addr, "push @%rw2,%a1(%rw3)", 0}, -{0x531e,0x53fe,16,2, 14,&z8002_device::Z53_ddN0_ssN0_addr, "push @%rw2,%a1(%rw3)", 0}, -{0x531f,0x53ff,16,2, 14,&z8002_device::Z53_ddN0_ssN0_addr, "push @%rw2,%a1(%rw3)", 0}, -{0x5400,0x540f, 1,2, 12,&z8002_device::Z54_0000_dddd_addr, "ldl %rl3,%a1", 0}, -{0x5410,0x54ff, 1,2, 13,&z8002_device::Z54_ssN0_dddd_addr, "ldl %rl3,%a1(%rw2)", 0}, -{0x5510,0x55f0,16,2, 23,&z8002_device::Z55_ssN0_0000_addr, "popl %a1,@%rw2", 0}, -{0x5511,0x55f1,16,2, 23,&z8002_device::Z55_ssN0_ddN0_addr, "popl %a1(%rw3),@%rw2", 0}, -{0x5512,0x55f2,16,2, 23,&z8002_device::Z55_ssN0_ddN0_addr, "popl %a1(%rw3),@%rw2", 0}, -{0x5513,0x55f3,16,2, 23,&z8002_device::Z55_ssN0_ddN0_addr, "popl %a1(%rw3),@%rw2", 0}, -{0x5514,0x55f4,16,2, 23,&z8002_device::Z55_ssN0_ddN0_addr, "popl %a1(%rw3),@%rw2", 0}, -{0x5515,0x55f5,16,2, 23,&z8002_device::Z55_ssN0_ddN0_addr, "popl %a1(%rw3),@%rw2", 0}, -{0x5516,0x55f6,16,2, 23,&z8002_device::Z55_ssN0_ddN0_addr, "popl %a1(%rw3),@%rw2", 0}, -{0x5517,0x55f7,16,2, 23,&z8002_device::Z55_ssN0_ddN0_addr, "popl %a1(%rw3),@%rw2", 0}, -{0x5518,0x55f8,16,2, 23,&z8002_device::Z55_ssN0_ddN0_addr, "popl %a1(%rw3),@%rw2", 0}, -{0x5519,0x55f9,16,2, 23,&z8002_device::Z55_ssN0_ddN0_addr, "popl %a1(%rw3),@%rw2", 0}, -{0x551a,0x55fa,16,2, 23,&z8002_device::Z55_ssN0_ddN0_addr, "popl %a1(%rw3),@%rw2", 0}, -{0x551b,0x55fb,16,2, 23,&z8002_device::Z55_ssN0_ddN0_addr, "popl %a1(%rw3),@%rw2", 0}, -{0x551c,0x55fc,16,2, 23,&z8002_device::Z55_ssN0_ddN0_addr, "popl %a1(%rw3),@%rw2", 0}, -{0x551d,0x55fd,16,2, 23,&z8002_device::Z55_ssN0_ddN0_addr, "popl %a1(%rw3),@%rw2", 0}, -{0x551e,0x55fe,16,2, 23,&z8002_device::Z55_ssN0_ddN0_addr, "popl %a1(%rw3),@%rw2", 0}, -{0x551f,0x55ff,16,2, 23,&z8002_device::Z55_ssN0_ddN0_addr, "popl %a1(%rw3),@%rw2", 0}, -{0x5600,0x560f, 1,2, 15,&z8002_device::Z56_0000_dddd_addr, "addl %rl3,%a1", 0}, -{0x5610,0x56ff, 1,2, 16,&z8002_device::Z56_ssN0_dddd_addr, "addl %rl3,%a1(%rw2)", 0}, -{0x5710,0x57f0,16,2, 16,&z8002_device::Z57_ssN0_0000_addr, "pop %a1,@%rw2", 0}, -{0x5711,0x57f1,16,2, 16,&z8002_device::Z57_ssN0_ddN0_addr, "pop %a1(%rw3),@%rw2", 0}, -{0x5712,0x57f2,16,2, 16,&z8002_device::Z57_ssN0_ddN0_addr, "pop %a1(%rw3),@%rw2", 0}, -{0x5713,0x57f3,16,2, 16,&z8002_device::Z57_ssN0_ddN0_addr, "pop %a1(%rw3),@%rw2", 0}, -{0x5714,0x57f4,16,2, 16,&z8002_device::Z57_ssN0_ddN0_addr, "pop %a1(%rw3),@%rw2", 0}, -{0x5715,0x57f5,16,2, 16,&z8002_device::Z57_ssN0_ddN0_addr, "pop %a1(%rw3),@%rw2", 0}, -{0x5716,0x57f6,16,2, 16,&z8002_device::Z57_ssN0_ddN0_addr, "pop %a1(%rw3),@%rw2", 0}, -{0x5717,0x57f7,16,2, 16,&z8002_device::Z57_ssN0_ddN0_addr, "pop %a1(%rw3),@%rw2", 0}, -{0x5718,0x57f8,16,2, 16,&z8002_device::Z57_ssN0_ddN0_addr, "pop %a1(%rw3),@%rw2", 0}, -{0x5719,0x57f9,16,2, 16,&z8002_device::Z57_ssN0_ddN0_addr, "pop %a1(%rw3),@%rw2", 0}, -{0x571a,0x57fa,16,2, 16,&z8002_device::Z57_ssN0_ddN0_addr, "pop %a1(%rw3),@%rw2", 0}, -{0x571b,0x57fb,16,2, 16,&z8002_device::Z57_ssN0_ddN0_addr, "pop %a1(%rw3),@%rw2", 0}, -{0x571c,0x57fc,16,2, 16,&z8002_device::Z57_ssN0_ddN0_addr, "pop %a1(%rw3),@%rw2", 0}, -{0x571d,0x57fd,16,2, 16,&z8002_device::Z57_ssN0_ddN0_addr, "pop %a1(%rw3),@%rw2", 0}, -{0x571e,0x57fe,16,2, 16,&z8002_device::Z57_ssN0_ddN0_addr, "pop %a1(%rw3),@%rw2", 0}, -{0x571f,0x57ff,16,2, 16,&z8002_device::Z57_ssN0_ddN0_addr, "pop %a1(%rw3),@%rw2", 0}, -{0x5800,0x580f, 1,2,283,&z8002_device::Z58_0000_dddd_addr, "multl %rq3,%a1", 0}, -{0x5810,0x58ff, 1,2,284,&z8002_device::Z58_ssN0_dddd_addr, "multl %rq3,%a1(%rw2)", 0}, -{0x5900,0x590f, 1,2, 71,&z8002_device::Z59_0000_dddd_addr, "mult %rl3,%a1", 0}, -{0x5910,0x59ff, 1,2, 72,&z8002_device::Z59_ssN0_dddd_addr, "mult %rl3,%a1(%rw2)", 0}, -{0x5a00,0x5a0f, 1,2,745,&z8002_device::Z5A_0000_dddd_addr, "divl %rq3,%a1", 0}, -{0x5a10,0x5aff, 1,2,746,&z8002_device::Z5A_ssN0_dddd_addr, "divl %rq3,%a1(%rw2)", 0}, -{0x5b00,0x5b0f, 1,2,108,&z8002_device::Z5B_0000_dddd_addr, "div %rl3,%a1", 0}, -{0x5b10,0x5bff, 1,2,109,&z8002_device::Z5B_ssN0_dddd_addr, "div %rl3,%a1(%rw2)", 0}, -{0x5c01,0x5c01, 1,3, 14,&z8002_device::Z5C_0000_0001_0000_dddd_0000_nmin1_addr, "ldm %rw5,%a2,#%n", 0}, -{0x5c08,0x5c08, 1,2, 16,&z8002_device::Z5C_0000_1000_addr, "testl %a1", 0}, -{0x5c09,0x5c09, 1,3, 14,&z8002_device::Z5C_0000_1001_0000_ssss_0000_nmin1_addr, "ldm %a2,%rw5,#%n", 0}, -{0x5c11,0x5cf1,16,3, 15,&z8002_device::Z5C_ssN0_0001_0000_dddd_0000_nmin1_addr, "ldm %rw5,%a2(%rw2),#%n", 0}, -{0x5c18,0x5cf8,16,2, 17,&z8002_device::Z5C_ddN0_1000_addr, "testl %a1(%rw2)", 0}, -{0x5c19,0x5cf9,16,3, 15,&z8002_device::Z5C_ddN0_1001_0000_ssN0_0000_nmin1_addr, "ldm %a2(%rw2),%rw5,#%n", 0}, -{0x5d00,0x5d0f, 1,2, 15,&z8002_device::Z5D_0000_ssss_addr, "ldl %a1,%rl3", 0}, -{0x5d10,0x5dff, 1,2, 14,&z8002_device::Z5D_ddN0_ssss_addr, "ldl %a1(%rw2),%rl3", 0}, -{0x5e00,0x5e0f, 1,2, 7,&z8002_device::Z5E_0000_cccc_addr, "jp %c3,%a1", 0}, -{0x5e10,0x5eff, 1,2, 8,&z8002_device::Z5E_ddN0_cccc_addr, "jp %c3,%a1(%rw2)", 0}, -{0x5f00,0x5f00, 1,2, 12,&z8002_device::Z5F_0000_0000_addr, "call %a1", DASMFLAG_STEP_OVER}, -{0x5f10,0x5ff0,16,2, 13,&z8002_device::Z5F_ddN0_0000_addr, "call %a1(%rw2)", DASMFLAG_STEP_OVER}, -{0x6000,0x600f, 1,2, 9,&z8002_device::Z60_0000_dddd_addr, "ldb %rb3,%a1", 0}, -{0x6010,0x60ff, 1,2, 10,&z8002_device::Z60_ssN0_dddd_addr, "ldb %rb3,%a1(%rw2)", 0}, -{0x6100,0x610f, 1,2, 9,&z8002_device::Z61_0000_dddd_addr, "ld %rw3,%a1", 0}, -{0x6110,0x61ff, 1,2, 10,&z8002_device::Z61_ssN0_dddd_addr, "ld %rw3,%a1(%rw2)", 0}, -{0x6200,0x620f, 1,2, 13,&z8002_device::Z62_0000_imm4_addr, "resb %a1,%3", 0}, -{0x6210,0x62ff, 1,2, 14,&z8002_device::Z62_ddN0_imm4_addr, "resb %a1(%rw2),%3", 0}, -{0x6300,0x630f, 1,2, 13,&z8002_device::Z63_0000_imm4_addr, "res %a1,%3", 0}, -{0x6310,0x63ff, 1,2, 14,&z8002_device::Z63_ddN0_imm4_addr, "res %a1(%rw2),%3", 0}, -{0x6400,0x640f, 1,2, 13,&z8002_device::Z64_0000_imm4_addr, "setb %a1,%3", 0}, -{0x6410,0x64ff, 1,2, 14,&z8002_device::Z64_ddN0_imm4_addr, "setb %a1(%rw2),%3", 0}, -{0x6500,0x650f, 1,2, 13,&z8002_device::Z65_0000_imm4_addr, "set %a1,%3", 0}, -{0x6510,0x65ff, 1,2, 14,&z8002_device::Z65_ddN0_imm4_addr, "set %a1(%rw2),%3", 0}, -{0x6600,0x660f, 1,2, 10,&z8002_device::Z66_0000_imm4_addr, "bitb %a1,%3", 0}, -{0x6610,0x66ff, 1,2, 11,&z8002_device::Z66_ddN0_imm4_addr, "bitb %a1(%rw2),%3", 0}, -{0x6700,0x670f, 1,2, 10,&z8002_device::Z67_0000_imm4_addr, "bit %a1,%3", 0}, -{0x6710,0x67ff, 1,2, 11,&z8002_device::Z67_ddN0_imm4_addr, "bit %a1(%rw2),%3", 0}, -{0x6800,0x680f, 1,2, 13,&z8002_device::Z68_0000_imm4m1_addr, "incb %a1,%+3", 0}, -{0x6810,0x68ff, 1,2, 14,&z8002_device::Z68_ddN0_imm4m1_addr, "incb %a1(%rw2),%+3", 0}, -{0x6900,0x690f, 1,2, 13,&z8002_device::Z69_0000_imm4m1_addr, "inc %a1,%+3", 0}, -{0x6910,0x69ff, 1,2, 14,&z8002_device::Z69_ddN0_imm4m1_addr, "inc %a1(%rw2),%+3", 0}, -{0x6a00,0x6a0f, 1,2, 13,&z8002_device::Z6A_0000_imm4m1_addr, "decb %a1,%+3", 0}, -{0x6a10,0x6aff, 1,2, 14,&z8002_device::Z6A_ddN0_imm4m1_addr, "decb %a1(%rw2),%+3", 0}, -{0x6b00,0x6b0f, 1,2, 13,&z8002_device::Z6B_0000_imm4m1_addr, "dec %a1,%+3", 0}, -{0x6b10,0x6bff, 1,2, 14,&z8002_device::Z6B_ddN0_imm4m1_addr, "dec %a1(%rw2),%+3", 0}, -{0x6c00,0x6c0f, 1,2, 15,&z8002_device::Z6C_0000_dddd_addr, "exb %rb3,%a1", 0}, -{0x6c10,0x6cff, 1,2, 16,&z8002_device::Z6C_ssN0_dddd_addr, "exb %rb3,%a1(%rw2)", 0}, -{0x6d00,0x6d0f, 1,2, 15,&z8002_device::Z6D_0000_dddd_addr, "ex %rw3,%a1", 0}, -{0x6d10,0x6dff, 1,2, 16,&z8002_device::Z6D_ssN0_dddd_addr, "ex %rw3,%a1(%rw2)", 0}, -{0x6e00,0x6e0f, 1,2, 11,&z8002_device::Z6E_0000_ssss_addr, "ldb %a1,%rb3", 0}, -{0x6e10,0x6eff, 1,2, 11,&z8002_device::Z6E_ddN0_ssss_addr, "ldb %a1(%rw2),%rb3", 0}, -{0x6f00,0x6f0f, 1,2, 11,&z8002_device::Z6F_0000_ssss_addr, "ld %a1,%rw3", 0}, -{0x6f10,0x6fff, 1,2, 12,&z8002_device::Z6F_ddN0_ssss_addr, "ld %a1(%rw2),%rw3", 0}, -{0x7010,0x70ff, 1,2, 14,&z8002_device::Z70_ssN0_dddd_0000_xxxx_0000_0000, "ldb %rb3,%rw2(%rw5)", 0}, -{0x7110,0x71ff, 1,2, 14,&z8002_device::Z71_ssN0_dddd_0000_xxxx_0000_0000, "ld %rw3,%rw2(%rw5)", 0}, -{0x7210,0x72ff, 1,2, 14,&z8002_device::Z72_ddN0_ssss_0000_xxxx_0000_0000, "ldb %rw2(%rw5),%rb3", 0}, -{0x7310,0x73ff, 1,2, 14,&z8002_device::Z73_ddN0_ssss_0000_xxxx_0000_0000, "ld %rw2(%rw5),%rw3", 0}, -{0x7410,0x74ff, 1,2, 15,&z8002_device::Z74_ssN0_dddd_0000_xxxx_0000_0000, "lda p%rw3,%rw2(%rw5)", 0}, -{0x7510,0x75ff, 1,2, 17,&z8002_device::Z75_ssN0_dddd_0000_xxxx_0000_0000, "ldl %rl3,%rw2(%rw5)", 0}, -{0x7600,0x760f, 1,2, 12,&z8002_device::Z76_0000_dddd_addr, "lda p%rw3,%a1", 0}, -{0x7610,0x76ff, 1,2, 13,&z8002_device::Z76_ssN0_dddd_addr, "lda p%rw3,%a1(%rw2)", 0}, -{0x7710,0x77ff, 1,2, 17,&z8002_device::Z77_ddN0_ssss_0000_xxxx_0000_0000, "ldl %rw2(%rw5),%rl3", 0}, -{0x7800,0x78ff, 1,1, 10,&z8002_device::Z78_imm8, "rsvd78", 0}, -{0x7900,0x7900, 1,2, 16,&z8002_device::Z79_0000_0000_addr, "ldps %a1", 0}, -{0x7910,0x79f0,16,2, 17,&z8002_device::Z79_ssN0_0000_addr, "ldps %a1(%rw2)", 0}, -{0x7a00,0x7a00, 1,1, 8,&z8002_device::Z7A_0000_0000, "halt", DASMFLAG_STEP_OVER}, -{0x7b00,0x7b00, 1,1, 13,&z8002_device::Z7B_0000_0000, "iret", DASMFLAG_STEP_OUT}, -{0x7b08,0x7b08, 1,1, 5,&z8002_device::Z7B_0000_1000, "mset", 0}, -{0x7b09,0x7b09, 1,1, 5,&z8002_device::Z7B_0000_1001, "mres", 0}, -{0x7b0a,0x7b0a, 1,1, 7,&z8002_device::Z7B_0000_1010, "mbit", 0}, -{0x7b0d,0x7bfd,16,1, 12,&z8002_device::Z7B_dddd_1101, "mreq %rw2", 0}, -{0x7c00,0x7c03, 1,1, 7,&z8002_device::Z7C_0000_00ii, "di %i3", 0}, -{0x7c04,0x7c07, 1,1, 7,&z8002_device::Z7C_0000_01ii, "ei %i3", 0}, -{0x7d00,0x7df0,16,1, 7,&z8002_device::Z7D_dddd_0ccc, "ldctl %rw2,ctrl0", 0}, -{0x7d01,0x7df1,16,1, 7,&z8002_device::Z7D_dddd_0ccc, "ldctl %rw2,ctrl1", 0}, -{0x7d02,0x7df2,16,1, 7,&z8002_device::Z7D_dddd_0ccc, "ldctl %rw2,fcw", 0}, -{0x7d03,0x7df3,16,1, 7,&z8002_device::Z7D_dddd_0ccc, "ldctl %rw2,refresh", 0}, -{0x7d04,0x7df4,16,1, 7,&z8002_device::Z7D_dddd_0ccc, "ldctl %rw2,psapseg", 0}, -{0x7d05,0x7df5,16,1, 7,&z8002_device::Z7D_dddd_0ccc, "ldctl %rw2,psapoff", 0}, -{0x7d06,0x7df6,16,1, 7,&z8002_device::Z7D_dddd_0ccc, "ldctl %rw2,nspseg", 0}, -{0x7d07,0x7df7,16,1, 7,&z8002_device::Z7D_dddd_0ccc, "ldctl %rw2,nspoff", 0}, -{0x7d08,0x7df8,16,1, 7,&z8002_device::Z7D_ssss_1ccc, "ldctl ctrl0,%rw2", 0}, -{0x7d09,0x7df9,16,1, 7,&z8002_device::Z7D_ssss_1ccc, "ldctl ctrl1,%rw2", 0}, -{0x7d0a,0x7dfa,16,1, 7,&z8002_device::Z7D_ssss_1ccc, "ldctl fcw,%rw2", 0}, -{0x7d0b,0x7dfb,16,1, 7,&z8002_device::Z7D_ssss_1ccc, "ldctl refresh,%rw2", 0}, -{0x7d0c,0x7dfc,16,1, 7,&z8002_device::Z7D_ssss_1ccc, "ldctl psapseg,%rw2", 0}, -{0x7d0d,0x7dfd,16,1, 7,&z8002_device::Z7D_ssss_1ccc, "ldctl psapoff,%rw2", 0}, -{0x7d0e,0x7dfe,16,1, 7,&z8002_device::Z7D_ssss_1ccc, "ldctl nspseg,%rw2", 0}, -{0x7d0f,0x7dff,16,1, 7,&z8002_device::Z7D_ssss_1ccc, "ldctl nspoff,%rw2", 0}, -{0x7e00,0x7eff, 1,1, 10,&z8002_device::Z7E_imm8, "rsvd7e %#b1", 0}, -{0x7f00,0x7fff, 1,1, 33,&z8002_device::Z7F_imm8, "sc %#b1", DASMFLAG_STEP_OVER}, -{0x8000,0x80ff, 1,1, 4,&z8002_device::Z80_ssss_dddd, "addb %rb3,%rb2", 0}, -{0x8100,0x81ff, 1,1, 4,&z8002_device::Z81_ssss_dddd, "add %rw3,%rw2", 0}, -{0x8200,0x82ff, 1,1, 4,&z8002_device::Z82_ssss_dddd, "subb %rb3,%rb2", 0}, -{0x8300,0x83ff, 1,1, 4,&z8002_device::Z83_ssss_dddd, "sub %rw3,%rw2", 0}, -{0x8400,0x84ff, 1,1, 4,&z8002_device::Z84_ssss_dddd, "orb %rb3,%rb2", 0}, -{0x8500,0x85ff, 1,1, 4,&z8002_device::Z85_ssss_dddd, "or %rw3,%rw2", 0}, -{0x8600,0x86ff, 1,1, 4,&z8002_device::Z86_ssss_dddd, "andb %rb3,%rb2", 0}, -{0x8700,0x87ff, 1,1, 4,&z8002_device::Z87_ssss_dddd, "and %rw3,%rw2", 0}, -{0x8800,0x88ff, 1,1, 4,&z8002_device::Z88_ssss_dddd, "xorb %rb3,%rb2", 0}, -{0x8900,0x89ff, 1,1, 4,&z8002_device::Z89_ssss_dddd, "xor %rw3,%rw2", 0}, -{0x8a00,0x8aff, 1,1, 4,&z8002_device::Z8A_ssss_dddd, "cpb %rb3,%rb2", 0}, -{0x8b00,0x8bff, 1,1, 4,&z8002_device::Z8B_ssss_dddd, "cp %rw3,%rw2", 0}, -{0x8c00,0x8cf0,16,1, 7,&z8002_device::Z8C_dddd_0000, "comb %rb2", 0}, -{0x8c02,0x8cf2,16,1, 7,&z8002_device::Z8C_dddd_0010, "negb %rb2", 0}, -{0x8c04,0x8cf4,16,1, 7,&z8002_device::Z8C_dddd_0100, "testb %rb2", 0}, -{0x8c06,0x8cf6,16,1, 7,&z8002_device::Z8C_dddd_0110, "tsetb %rb2", 0}, -{0x8c01,0x8cf1,16,1, 7,&z8002_device::Z8C_dddd_0001, "ldctlb %rb2,flags", 0}, -{0x8c08,0x8cf8,16,1, 7,&z8002_device::Z8C_dddd_1000, "clrb %rb2", 0}, -{0x8c09,0x8cf9,16,1, 7,&z8002_device::Z8C_dddd_1001, "ldctlb flags,%rb2", 0}, -{0x8d00,0x8df0,16,1, 7,&z8002_device::Z8D_dddd_0000, "com %rw2", 0}, -{0x8d01,0x8df1,16,1, 7,&z8002_device::Z8D_imm4_0001, "setflg %f2", 0}, -{0x8d02,0x8df2,16,1, 7,&z8002_device::Z8D_dddd_0010, "neg %rw2", 0}, -{0x8d03,0x8df3,16,1, 7,&z8002_device::Z8D_imm4_0011, "resflg %f2", 0}, -{0x8d04,0x8df4,16,1, 7,&z8002_device::Z8D_dddd_0100, "test %rw2", 0}, -{0x8d05,0x8df5,16,1, 7,&z8002_device::Z8D_imm4_0101, "comflg %f2", 0}, -{0x8d06,0x8df6,16,1, 7,&z8002_device::Z8D_dddd_0110, "tset %rw2", 0}, -{0x8d07,0x8d07, 1,1, 7,&z8002_device::Z8D_0000_0111, "nop", 0}, -{0x8d08,0x8df8,16,1, 7,&z8002_device::Z8D_dddd_1000, "clr %rw2", 0}, -{0x8e00,0x8eff, 1,1, 10,&z8002_device::Z8E_imm8, "ext8e %#b1", 0}, -{0x8f00,0x8fff, 1,1, 10,&z8002_device::Z8F_imm8, "ext8f %#b1", 0}, -{0x9000,0x90ff, 1,1, 8,&z8002_device::Z90_ssss_dddd, "cpl %rl3,%rl2", 0}, -{0x9110,0x91ff, 1,1, 12,&z8002_device::Z91_ddN0_ssss, "pushl @%rw2,%rl3", 0}, -{0x9200,0x92ff, 1,1, 8,&z8002_device::Z92_ssss_dddd, "subl %rl3,%rl2", 0}, -{0x9310,0x93ff, 1,1, 9,&z8002_device::Z93_ddN0_ssss, "push @%rw2,%rw3", 0}, -{0x9400,0x94ff, 1,1, 5,&z8002_device::Z94_ssss_dddd, "ldl %rl3,%rl2", 0}, -{0x9510,0x95ff, 1,1, 12,&z8002_device::Z95_ssN0_dddd, "popl %rl3,@%rw2", 0}, -{0x9600,0x96ff, 1,1, 8,&z8002_device::Z96_ssss_dddd, "addl %rl3,%rl2", 0}, -{0x9710,0x97ff, 1,1, 8,&z8002_device::Z97_ssN0_dddd, "pop %rw3,@%rw2", 0}, -{0x9800,0x98ff, 1,1,282,&z8002_device::Z98_ssss_dddd, "multl %rq3,%rl2", 0}, -{0x9900,0x99ff, 1,1, 70,&z8002_device::Z99_ssss_dddd, "mult %rl3,%rw2", 0}, -{0x9a00,0x9aff, 1,1,744,&z8002_device::Z9A_ssss_dddd, "divl %rq3,%rl2", 0}, -{0x9b00,0x9bff, 1,1,107,&z8002_device::Z9B_ssss_dddd, "div %rl3,%rw2", 0}, -{0x9c00,0x9cf8, 8,1, 13,&z8002_device::Z9C_dddd_1000, "testl %rl2", 0}, -{0x9d00,0x9dff, 1,1, 10,&z8002_device::Z9D_imm8, "rsvd9d", 0}, -{0x9e00,0x9e0f, 1,1, 10,&z8002_device::Z9E_0000_cccc, "ret %c3", DASMFLAG_STEP_OUT}, -{0x9f00,0x9fff, 1,1, 10,&z8002_device::Z9F_imm8, "rsvd9f", 0}, -{0xa000,0xa0ff, 1,1, 3,&z8002_device::ZA0_ssss_dddd, "ldb %rb3,%rb2", 0}, -{0xa100,0xa1ff, 1,1, 3,&z8002_device::ZA1_ssss_dddd, "ld %rw3,%rw2", 0}, -{0xa200,0xa2ff, 1,1, 4,&z8002_device::ZA2_dddd_imm4, "resb %rb2,%3", 0}, -{0xa300,0xa3ff, 1,1, 4,&z8002_device::ZA3_dddd_imm4, "res %rw2,%3", 0}, -{0xa400,0xa4ff, 1,1, 4,&z8002_device::ZA4_dddd_imm4, "setb %rb2,%3", 0}, -{0xa500,0xa5ff, 1,1, 4,&z8002_device::ZA5_dddd_imm4, "set %rw2,%3", 0}, -{0xa600,0xa6ff, 1,1, 4,&z8002_device::ZA6_dddd_imm4, "bitb %rb2,%3", 0}, -{0xa700,0xa7ff, 1,1, 4,&z8002_device::ZA7_dddd_imm4, "bit %rw2,%3", 0}, -{0xa800,0xa8ff, 1,1, 4,&z8002_device::ZA8_dddd_imm4m1, "incb %rb2,%+3", 0}, -{0xa900,0xa9ff, 1,1, 4,&z8002_device::ZA9_dddd_imm4m1, "inc %rw2,%+3", 0}, -{0xaa00,0xaaff, 1,1, 4,&z8002_device::ZAA_dddd_imm4m1, "decb %rb2,%+3", 0}, -{0xab00,0xabff, 1,1, 4,&z8002_device::ZAB_dddd_imm4m1, "dec %rw2,%+3", 0}, -{0xac00,0xacff, 1,1, 6,&z8002_device::ZAC_ssss_dddd, "exb %rb3,%rb2", 0}, -{0xad00,0xadff, 1,1, 6,&z8002_device::ZAD_ssss_dddd, "ex %rw3,%rw2", 0}, -{0xae00,0xaeff, 1,1, 5,&z8002_device::ZAE_dddd_cccc, "tccb %c3,%rb2", 0}, -{0xaf00,0xafff, 1,1, 5,&z8002_device::ZAF_dddd_cccc, "tcc %c3,%rw2", 0}, -{0xb000,0xb0f0,16,1, 5,&z8002_device::ZB0_dddd_0000, "dab %rb2", 0}, -{0xb100,0xb1f0,16,1, 11,&z8002_device::ZB1_dddd_0000, "extsb %rw2", 0}, -{0xb107,0xb1f7,16,1, 11,&z8002_device::ZB1_dddd_0111, "extsl %rq2", 0}, -{0xb10a,0xb1fa,16,1, 11,&z8002_device::ZB1_dddd_1010, "exts %rl2", 0}, -{0xb200,0xb2f0,16,1, 6,&z8002_device::ZB2_dddd_00I0, "rlb %rb2,%?3", 0}, -{0xb201,0xb2f1,16,2, 13,&z8002_device::ZB2_dddd_0001_imm8, "s%*lb %rb2,%$3", 0}, -{0xb202,0xb2f2,16,1, 6,&z8002_device::ZB2_dddd_00I0, "rlb %rb2,%?3", 0}, -{0xb203,0xb2f3,16,2, 15,&z8002_device::ZB2_dddd_0011_0000_ssss_0000_0000, "sdlb %rb2,%rw5", 0}, -{0xb204,0xb2f4,16,1, 6,&z8002_device::ZB2_dddd_01I0, "rrb %rb2,%?3", 0}, -{0xb206,0xb2f6,16,1, 6,&z8002_device::ZB2_dddd_01I0, "rrb %rb2,%?3", 0}, -{0xb208,0xb2f8,16,1, 9,&z8002_device::ZB2_dddd_10I0, "rlcb %rb2,%?3", 0}, -{0xb209,0xb2f9,16,2, 13,&z8002_device::ZB2_dddd_1001_imm8, "s%*ab %rb2,%$3", 0}, -{0xb20a,0xb2fa,16,1, 9,&z8002_device::ZB2_dddd_10I0, "rlcb %rb2,%?3", 0}, -{0xb20b,0xb2fb,16,2, 15,&z8002_device::ZB2_dddd_1011_0000_ssss_0000_0000, "sdab %rb2,%rw5", 0}, -{0xb20c,0xb2fc,16,1, 9,&z8002_device::ZB2_dddd_11I0, "rrcb %rb2,%?3", 0}, -{0xb20e,0xb2fe,16,1, 9,&z8002_device::ZB2_dddd_11I0, "rrcb %rb2,%?3", 0}, -{0xb300,0xb3f0,16,1, 6,&z8002_device::ZB3_dddd_00I0, "rl %rw2,%?3", 0}, -{0xb301,0xb3f1,16,2, 13,&z8002_device::ZB3_dddd_0001_imm8, "s%*l %rw2,%$3", 0}, -{0xb302,0xb3f2,16,1, 6,&z8002_device::ZB3_dddd_00I0, "rl %rw2,%?3", 0}, -{0xb303,0xb3f3,16,2, 15,&z8002_device::ZB3_dddd_0011_0000_ssss_0000_0000, "sdl %rw2,%rw5", 0}, -{0xb304,0xb3f4,16,1, 6,&z8002_device::ZB3_dddd_01I0, "rr %rw2,%?3", 0}, -{0xb305,0xb3f5,16,2, 13,&z8002_device::ZB3_dddd_0101_imm8, "s%*ll %rl2,%$3", 0}, -{0xb306,0xb3f6,16,1, 6,&z8002_device::ZB3_dddd_01I0, "rr %rw2,%?3", 0}, -{0xb307,0xb3f7,16,2, 15,&z8002_device::ZB3_dddd_0111_0000_ssss_0000_0000, "sdll %rl2,%rw5", 0}, -{0xb308,0xb3f8,16,1, 6,&z8002_device::ZB3_dddd_10I0, "rlc %rw2,%?3", 0}, -{0xb309,0xb3f9,16,2, 13,&z8002_device::ZB3_dddd_1001_imm8, "s%*a %rw2,%$3", 0}, -{0xb30a,0xb3fa,16,1, 6,&z8002_device::ZB3_dddd_10I0, "rlc %rw2,%?3", 0}, -{0xb30b,0xb3fb,16,2, 15,&z8002_device::ZB3_dddd_1011_0000_ssss_0000_0000, "sda %rw2,%rw5", 0}, -{0xb30c,0xb3fc,16,1, 6,&z8002_device::ZB3_dddd_11I0, "rrc %rw2,%?3", 0}, -{0xb30d,0xb3fd,16,2, 13,&z8002_device::ZB3_dddd_1101_imm8, "s%*al %rl2,%$3", 0}, -{0xb30e,0xb3fe,16,1, 6,&z8002_device::ZB3_dddd_11I0, "rrc %rw2,%?3", 0}, -{0xb30f,0xb3ff,16,2, 15,&z8002_device::ZB3_dddd_1111_0000_ssss_0000_0000, "sdal %rl2,%rw5", 0}, -{0xb400,0xb4ff, 1,1, 5,&z8002_device::ZB4_ssss_dddd, "adcb %rb3,%rb2", 0}, -{0xb500,0xb5ff, 1,1, 5,&z8002_device::ZB5_ssss_dddd, "adc %rw3,%rw2", 0}, -{0xb600,0xb6ff, 1,1, 5,&z8002_device::ZB6_ssss_dddd, "sbcb %rb3,%rb2", 0}, -{0xb700,0xb7ff, 1,1, 5,&z8002_device::ZB7_ssss_dddd, "sbc %rw3,%rw2", 0}, -{0xb810,0xb8f0,16,2, 25,&z8002_device::ZB8_ddN0_0000_0000_rrrr_ssN0_0000, "trib @%rw2,@%rw6,%rb5", 0}, -{0xb812,0xb8f2,16,2, 25,&z8002_device::ZB8_ddN0_0010_0000_rrrr_ssN0_0000, "trtib @%rw2,@%rw6,%rb5", 0}, -{0xb814,0xb8f4,16,2, 25,&z8002_device::ZB8_ddN0_0100_0000_rrrr_ssN0_0000, "trirb @%rw2,@%rw6,%rb5", 0}, -{0xb816,0xb8f6,16,2, 25,&z8002_device::ZB8_ddN0_0110_0000_rrrr_ssN0_1110, "trtirb @%rw2,@%rw6,%rb5", 0}, -{0xb818,0xb8f8,16,2, 25,&z8002_device::ZB8_ddN0_1000_0000_rrrr_ssN0_0000, "trdb @%rw2,@%rw6,%rb5", 0}, -{0xb81a,0xb8fa,16,2, 25,&z8002_device::ZB8_ddN0_1010_0000_rrrr_ssN0_0000, "trtrb @%rw2,@%rw6,%rb5", 0}, -{0xb81c,0xb8fc,16,2, 25,&z8002_device::ZB8_ddN0_1100_0000_rrrr_ssN0_0000, "trdrb @%rw2,@%rw6,%rb5", 0}, -{0xb81e,0xb8fe,16,2, 25,&z8002_device::ZB8_ddN0_1110_0000_rrrr_ssN0_1110, "trtdrb @%rw2,@%rw6,%rb5", 0}, -{0xb900,0xb9ff,16,1, 10,&z8002_device::ZB9_imm8, "rsvdb9", 0}, -{0xba10,0xbaf0,16,2, 11,&z8002_device::ZBA_ssN0_0000_0000_rrrr_dddd_cccc, "cpib %rb6,@%rw2,%rw5,%c7", 0}, -{0xba11,0xbaf1,16,2, 11,&z8002_device::ZBA_ssN0_0001_0000_rrrr_ddN0_x000, "ldirb @%rw6,@%rw2,%rw5", DASMFLAG_STEP_OVER}, -{0xba12,0xbaf2,16,2, 11,&z8002_device::ZBA_ssN0_0010_0000_rrrr_ddN0_cccc, "cpsib @%rw6,@%rw2,%rw5,%c7", 0}, -{0xba14,0xbaf4,16,2, 11,&z8002_device::ZBA_ssN0_0100_0000_rrrr_dddd_cccc, "cpirb %rb6,@%rw2,%rw5,%c7", DASMFLAG_STEP_OVER}, -{0xba16,0xbaf6,16,2, 11,&z8002_device::ZBA_ssN0_0110_0000_rrrr_ddN0_cccc, "cpsirb @%rw6,@%rw2,%rw5,%c7", DASMFLAG_STEP_OVER}, -{0xba18,0xbaf8,16,2, 11,&z8002_device::ZBA_ssN0_1000_0000_rrrr_dddd_cccc, "cpdb %rb6,@%rw2,%rw5,%c7", 0}, -{0xba19,0xbaf9,16,2, 11,&z8002_device::ZBA_ssN0_1001_0000_rrrr_ddN0_x000, "lddrb @%rw2,@%rw6,%rw5", DASMFLAG_STEP_OVER}, -{0xba1a,0xbafa,16,2, 11,&z8002_device::ZBA_ssN0_1010_0000_rrrr_ddN0_cccc, "cpsdb @%rw6,@%rw2,%rw5,%c7", 0}, -{0xba1c,0xbafc,16,2, 11,&z8002_device::ZBA_ssN0_1100_0000_rrrr_dddd_cccc, "cpdrb %rb6,@%rw2,%rw5,%c7", DASMFLAG_STEP_OVER}, -{0xba1e,0xbafe,16,2, 11,&z8002_device::ZBA_ssN0_1110_0000_rrrr_ddN0_cccc, "cpsdrb @%rw6,@%rw2,%rw5,%c7", DASMFLAG_STEP_OVER}, -{0xbb10,0xbbf0,16,2, 11,&z8002_device::ZBB_ssN0_0000_0000_rrrr_dddd_cccc, "cpi %rw6,@%rw2,%rw5,%c7", 0}, -{0xbb11,0xbbf1,16,2, 11,&z8002_device::ZBB_ssN0_0001_0000_rrrr_ddN0_x000, "ldir @%rw6,@%rw2,%rw5", DASMFLAG_STEP_OVER}, -{0xbb12,0xbbf2,16,2, 11,&z8002_device::ZBB_ssN0_0010_0000_rrrr_ddN0_cccc, "cpsi @%rw6,@%rw2,%rw5,%c7", 0}, -{0xbb14,0xbbf4,16,2, 11,&z8002_device::ZBB_ssN0_0100_0000_rrrr_dddd_cccc, "cpir %rw6,@%rw2,%rw5,%c7", DASMFLAG_STEP_OVER}, -{0xbb16,0xbbf6,16,2, 11,&z8002_device::ZBB_ssN0_0110_0000_rrrr_ddN0_cccc, "cpsir @%rw6,@%rw2,%rw5,%c7", DASMFLAG_STEP_OVER}, -{0xbb18,0xbbf8,16,2, 11,&z8002_device::ZBB_ssN0_1000_0000_rrrr_dddd_cccc, "cpd %rw6,@%rw2,%rw5,%c7", 0}, -{0xbb19,0xbbf9,16,2, 11,&z8002_device::ZBB_ssN0_1001_0000_rrrr_ddN0_x000, "lddr @%rw2,@%rw6,%rw5", DASMFLAG_STEP_OVER}, -{0xbb1a,0xbbfa,16,2, 11,&z8002_device::ZBB_ssN0_1010_0000_rrrr_ddN0_cccc, "cpsd @%rw6,@%rw2,%rw5,%c7", 0}, -{0xbb1c,0xbbfc,16,2, 11,&z8002_device::ZBB_ssN0_1100_0000_rrrr_dddd_cccc, "cpdr %rw6,@%rw2,%rw5,%c7", DASMFLAG_STEP_OVER}, -{0xbb1e,0xbbfe,16,2, 11,&z8002_device::ZBB_ssN0_1110_0000_rrrr_ddN0_cccc, "cpsdr @%rw6,@%rw2,%rw5,%c7", DASMFLAG_STEP_OVER}, -{0xbc00,0xbcff, 1,1, 9,&z8002_device::ZBC_aaaa_bbbb, "rrdb %rb3,%rb2", 0}, -{0xbd00,0xbdff, 1,1, 5,&z8002_device::ZBD_dddd_imm4, "ldk %rw2,%3", 0}, -{0xbe00,0xbeff, 1,1, 9,&z8002_device::ZBE_aaaa_bbbb, "rldb %rb3,%rb2", 0}, -{0xbf00,0xbfff, 1,1, 10,&z8002_device::ZBF_imm8, "rsvdbf", 0}, -{0xc000,0xcfff, 1,1, 5,&z8002_device::ZC_dddd_imm8, "ldb %rb1,%#b1", 0}, -{0xd000,0xdfff, 1,1, 10,&z8002_device::ZD_dsp12, "calr %d2", DASMFLAG_STEP_OVER}, -{0xe000,0xefff, 1,1, 6,&z8002_device::ZE_cccc_dsp8, "jr %c1,%d1", 0}, -{0xf000,0xf07f, 1,1, 11,&z8002_device::ZF_dddd_0dsp7, "dbjnz %rb1,%d0", DASMFLAG_STEP_OVER}, -{0xf100,0xf17f, 1,1, 11,&z8002_device::ZF_dddd_0dsp7, "dbjnz %rb1,%d0", DASMFLAG_STEP_OVER}, -{0xf200,0xf27f, 1,1, 11,&z8002_device::ZF_dddd_0dsp7, "dbjnz %rb1,%d0", DASMFLAG_STEP_OVER}, -{0xf300,0xf37f, 1,1, 11,&z8002_device::ZF_dddd_0dsp7, "dbjnz %rb1,%d0", DASMFLAG_STEP_OVER}, -{0xf400,0xf47f, 1,1, 11,&z8002_device::ZF_dddd_0dsp7, "dbjnz %rb1,%d0", DASMFLAG_STEP_OVER}, -{0xf500,0xf57f, 1,1, 11,&z8002_device::ZF_dddd_0dsp7, "dbjnz %rb1,%d0", DASMFLAG_STEP_OVER}, -{0xf600,0xf67f, 1,1, 11,&z8002_device::ZF_dddd_0dsp7, "dbjnz %rb1,%d0", DASMFLAG_STEP_OVER}, -{0xf700,0xf77f, 1,1, 11,&z8002_device::ZF_dddd_0dsp7, "dbjnz %rb1,%d0", DASMFLAG_STEP_OVER}, -{0xf800,0xf87f, 1,1, 11,&z8002_device::ZF_dddd_0dsp7, "dbjnz %rb1,%d0", DASMFLAG_STEP_OVER}, -{0xf900,0xf97f, 1,1, 11,&z8002_device::ZF_dddd_0dsp7, "dbjnz %rb1,%d0", DASMFLAG_STEP_OVER}, -{0xfa00,0xfa7f, 1,1, 11,&z8002_device::ZF_dddd_0dsp7, "dbjnz %rb1,%d0", DASMFLAG_STEP_OVER}, -{0xfb00,0xfb7f, 1,1, 11,&z8002_device::ZF_dddd_0dsp7, "dbjnz %rb1,%d0", DASMFLAG_STEP_OVER}, -{0xfc00,0xfc7f, 1,1, 11,&z8002_device::ZF_dddd_0dsp7, "dbjnz %rb1,%d0", DASMFLAG_STEP_OVER}, -{0xfd00,0xfd7f, 1,1, 11,&z8002_device::ZF_dddd_0dsp7, "dbjnz %rb1,%d0", DASMFLAG_STEP_OVER}, -{0xfe00,0xfe7f, 1,1, 11,&z8002_device::ZF_dddd_0dsp7, "dbjnz %rb1,%d0", DASMFLAG_STEP_OVER}, -{0xff00,0xff7f, 1,1, 11,&z8002_device::ZF_dddd_0dsp7, "dbjnz %rb1,%d0", DASMFLAG_STEP_OVER}, -{0xf080,0xf0ff, 1,1, 11,&z8002_device::ZF_dddd_1dsp7, "djnz %rw1,%d0", DASMFLAG_STEP_OVER}, -{0xf180,0xf1ff, 1,1, 11,&z8002_device::ZF_dddd_1dsp7, "djnz %rw1,%d0", DASMFLAG_STEP_OVER}, -{0xf280,0xf2ff, 1,1, 11,&z8002_device::ZF_dddd_1dsp7, "djnz %rw1,%d0", DASMFLAG_STEP_OVER}, -{0xf380,0xf3ff, 1,1, 11,&z8002_device::ZF_dddd_1dsp7, "djnz %rw1,%d0", DASMFLAG_STEP_OVER}, -{0xf480,0xf4ff, 1,1, 11,&z8002_device::ZF_dddd_1dsp7, "djnz %rw1,%d0", DASMFLAG_STEP_OVER}, -{0xf580,0xf5ff, 1,1, 11,&z8002_device::ZF_dddd_1dsp7, "djnz %rw1,%d0", DASMFLAG_STEP_OVER}, -{0xf680,0xf6ff, 1,1, 11,&z8002_device::ZF_dddd_1dsp7, "djnz %rw1,%d0", DASMFLAG_STEP_OVER}, -{0xf780,0xf7ff, 1,1, 11,&z8002_device::ZF_dddd_1dsp7, "djnz %rw1,%d0", DASMFLAG_STEP_OVER}, -{0xf880,0xf8ff, 1,1, 11,&z8002_device::ZF_dddd_1dsp7, "djnz %rw1,%d0", DASMFLAG_STEP_OVER}, -{0xf980,0xf9ff, 1,1, 11,&z8002_device::ZF_dddd_1dsp7, "djnz %rw1,%d0", DASMFLAG_STEP_OVER}, -{0xfa80,0xfaff, 1,1, 11,&z8002_device::ZF_dddd_1dsp7, "djnz %rw1,%d0", DASMFLAG_STEP_OVER}, -{0xfb80,0xfbff, 1,1, 11,&z8002_device::ZF_dddd_1dsp7, "djnz %rw1,%d0", DASMFLAG_STEP_OVER}, -{0xfc80,0xfcff, 1,1, 11,&z8002_device::ZF_dddd_1dsp7, "djnz %rw1,%d0", DASMFLAG_STEP_OVER}, -{0xfd80,0xfdff, 1,1, 11,&z8002_device::ZF_dddd_1dsp7, "djnz %rw1,%d0", DASMFLAG_STEP_OVER}, -{0xfe80,0xfeff, 1,1, 11,&z8002_device::ZF_dddd_1dsp7, "djnz %rw1,%d0", DASMFLAG_STEP_OVER}, -{0xff80,0xffff, 1,1, 11,&z8002_device::ZF_dddd_1dsp7, "djnz %rw1,%d0", DASMFLAG_STEP_OVER}, -{0, 0, 0,0, 0,nullptr, nullptr, 0} -}; - - -void z8002_device::init_tables() -{ - /* already initialized? */ - if (z8000_exec) - return; - - const Z8000_init *init; - int i; - - /* allocate the opcode execution and disassembler array */ - std::unique_ptr exec(new Z8000_exec[0x10000]); - - /* set up the zero, sign, parity lookup table */ - for (i = 0; i < 256; i++) - z8000_zsp[i] = ((i == 0) ? F_Z : 0) | - ((i & 128) ? F_S : 0) | - ((((i>>7)^(i>>6)^(i>>5)^(i>>4)^(i>>3)^(i>>2)^(i>>1)^i) & 1) ? 0 : F_PV); + { 0x0000, 0xffff, 1, 1, 4, &z8002_device::zinvalid }, - /* first set all 64K opcodes to invalid */ - for (i = 0; i < 0x10000; i++) - { - exec[i].opcode = &z8002_device::zinvalid; - exec[i].cycles = 4; - exec[i].size = 1; - exec[i].dasm = ".word %#w0"; - exec[i].dasmflags = 0; - } - - /* now decompose the initialization table */ - for (init = table; init->size; init++) - { - for (i = init->beg; i <= init->end; i += init->step) - { - if (exec[i].opcode != &z8002_device::zinvalid) - osd_printf_error("Z8000 opcode %04x clash '%s'\n", i, exec[i].dasm); - - exec[i].opcode = init->opcode; - exec[i].cycles = init->cycles; - exec[i].size = init->size; - exec[i].dasm = init->dasm; - exec[i].dasmflags = init->dasmflags; - } - } - - z8000_exec = std::move(exec); -} - -void z8002_device::deinit_tables() -{ - z8000_exec = nullptr; -} - -z8002_device::Z8000_dasm z8002_device::dasm(unsigned w) -{ - init_tables(); - Z8000_exec const &exec(z8000_exec[w]); - return Z8000_dasm{ exec.dasm, exec.dasmflags, exec.size }; -} + { 0x0000, 0x000f, 1, 2, 7, &z8002_device::Z00_0000_dddd_imm8 }, + { 0x0010, 0x00ff, 1, 1, 7, &z8002_device::Z00_ssN0_dddd }, + { 0x0100, 0x010f, 1, 2, 7, &z8002_device::Z01_0000_dddd_imm16 }, + { 0x0110, 0x01ff, 1, 1, 7, &z8002_device::Z01_ssN0_dddd }, + { 0x0200, 0x020f, 1, 2, 7, &z8002_device::Z02_0000_dddd_imm8 }, + { 0x0210, 0x02ff, 1, 1, 7, &z8002_device::Z02_ssN0_dddd }, + { 0x0300, 0x030f, 1, 2, 7, &z8002_device::Z03_0000_dddd_imm16 }, + { 0x0310, 0x03ff, 1, 1, 7, &z8002_device::Z03_ssN0_dddd }, + { 0x0400, 0x040f, 1, 2, 7, &z8002_device::Z04_0000_dddd_imm8 }, + { 0x0410, 0x04ff, 1, 1, 7, &z8002_device::Z04_ssN0_dddd }, + { 0x0500, 0x050f, 1, 2, 7, &z8002_device::Z05_0000_dddd_imm16 }, + { 0x0510, 0x05ff, 1, 1, 7, &z8002_device::Z05_ssN0_dddd }, + { 0x0600, 0x060f, 1, 2, 7, &z8002_device::Z06_0000_dddd_imm8 }, + { 0x0610, 0x06ff, 1, 1, 7, &z8002_device::Z06_ssN0_dddd }, + { 0x0700, 0x070f, 1, 2, 7, &z8002_device::Z07_0000_dddd_imm16 }, + { 0x0710, 0x07ff, 1, 1, 7, &z8002_device::Z07_ssN0_dddd }, + { 0x0800, 0x080f, 1, 2, 7, &z8002_device::Z08_0000_dddd_imm8 }, + { 0x0810, 0x08ff, 1, 1, 7, &z8002_device::Z08_ssN0_dddd }, + { 0x0900, 0x090f, 1, 2, 7, &z8002_device::Z09_0000_dddd_imm16 }, + { 0x0910, 0x09ff, 1, 1, 7, &z8002_device::Z09_ssN0_dddd }, + { 0x0a00, 0x0a0f, 1, 2, 7, &z8002_device::Z0A_0000_dddd_imm8 }, + { 0x0a10, 0x0aff, 1, 1, 7, &z8002_device::Z0A_ssN0_dddd }, + { 0x0b00, 0x0b0f, 1, 2, 7, &z8002_device::Z0B_0000_dddd_imm16 }, + { 0x0b10, 0x0bff, 1, 1, 7, &z8002_device::Z0B_ssN0_dddd }, + { 0x0c10, 0x0cf0, 16, 1, 12, &z8002_device::Z0C_ddN0_0000 }, + { 0x0c11, 0x0cf1, 16, 2, 11, &z8002_device::Z0C_ddN0_0001_imm8 }, + { 0x0c12, 0x0cf2, 16, 1, 12, &z8002_device::Z0C_ddN0_0010 }, + { 0x0c14, 0x0cf4, 16, 1, 8, &z8002_device::Z0C_ddN0_0100 }, + { 0x0c15, 0x0cf5, 16, 2, 7, &z8002_device::Z0C_ddN0_0101_imm8 }, + { 0x0c16, 0x0cf6, 16, 1, 11, &z8002_device::Z0C_ddN0_0110 }, + { 0x0c18, 0x0cf8, 16, 1, 8, &z8002_device::Z0C_ddN0_1000 }, + { 0x0d10, 0x0df0, 16, 1, 12, &z8002_device::Z0D_ddN0_0000 }, + { 0x0d11, 0x0df1, 16, 2, 11, &z8002_device::Z0D_ddN0_0001_imm16 }, + { 0x0d12, 0x0df2, 16, 1, 12, &z8002_device::Z0D_ddN0_0010 }, + { 0x0d14, 0x0df4, 16, 1, 8, &z8002_device::Z0D_ddN0_0100 }, + { 0x0d15, 0x0df5, 16, 2, 11, &z8002_device::Z0D_ddN0_0101_imm16 }, /* fix cycles ld IR,IM */ + { 0x0d16, 0x0df6, 16, 1, 11, &z8002_device::Z0D_ddN0_0110 }, + { 0x0d18, 0x0df8, 16, 1, 8, &z8002_device::Z0D_ddN0_1000 }, + { 0x0d19, 0x0df9, 16, 2, 12, &z8002_device::Z0D_ddN0_1001_imm16 }, + { 0x0e00, 0x0eff, 1, 1, 10, &z8002_device::Z0E_imm8 }, + { 0x0f00, 0x0fff, 1, 1, 10, &z8002_device::Z0F_imm8 }, + { 0x1000, 0x100f, 1, 3, 14, &z8002_device::Z10_0000_dddd_imm32 }, + { 0x1010, 0x10ff, 1, 1, 14, &z8002_device::Z10_ssN0_dddd }, + { 0x1111, 0x11ff, 1, 1, 20, &z8002_device::Z11_ddN0_ssN0 }, + { 0x1200, 0x120f, 1, 3, 14, &z8002_device::Z12_0000_dddd_imm32 }, + { 0x1210, 0x12ff, 1, 1, 14, &z8002_device::Z12_ssN0_dddd }, + { 0x1311, 0x13ff, 1, 1, 13, &z8002_device::Z13_ddN0_ssN0 }, + { 0x1400, 0x140f, 1, 3, 11, &z8002_device::Z14_0000_dddd_imm32 }, + { 0x1410, 0x14ff, 1, 1, 11, &z8002_device::Z14_ssN0_dddd }, + { 0x1511, 0x15ff, 1, 1, 19, &z8002_device::Z15_ssN0_ddN0 }, + { 0x1600, 0x160f, 1, 3, 14, &z8002_device::Z16_0000_dddd_imm32 }, + { 0x1610, 0x16ff, 1, 1, 14, &z8002_device::Z16_ssN0_dddd }, + { 0x1711, 0x17ff, 1, 1, 12, &z8002_device::Z17_ssN0_ddN0 }, + { 0x1800, 0x180f, 1, 1, 282, &z8002_device::Z18_00N0_dddd_imm32 }, + { 0x1810, 0x18ff, 1, 1, 282, &z8002_device::Z18_ssN0_dddd }, + { 0x1900, 0x190f, 1, 2, 70, &z8002_device::Z19_0000_dddd_imm16 }, + { 0x1910, 0x19ff, 1, 1, 70, &z8002_device::Z19_ssN0_dddd }, + { 0x1a00, 0x1a0f, 1, 3, 744, &z8002_device::Z1A_0000_dddd_imm32 }, + { 0x1a10, 0x1aff, 1, 1, 744, &z8002_device::Z1A_ssN0_dddd }, + { 0x1b00, 0x1b0f, 1, 2, 107, &z8002_device::Z1B_0000_dddd_imm16 }, + { 0x1b10, 0x1bff, 1, 1, 107, &z8002_device::Z1B_ssN0_dddd }, + { 0x1c11, 0x1cf1, 16, 2, 11, &z8002_device::Z1C_ssN0_0001_0000_dddd_0000_nmin1 }, + { 0x1c18, 0x1cf8, 16, 1, 13, &z8002_device::Z1C_ddN0_1000 }, + { 0x1c19, 0x1cf9, 16, 2, 11, &z8002_device::Z1C_ddN0_1001_0000_ssss_0000_nmin1 }, + { 0x1d10, 0x1dff, 1, 1, 11, &z8002_device::Z1D_ddN0_ssss }, + { 0x1e10, 0x1eff, 1, 1, 10, &z8002_device::Z1E_ddN0_cccc }, + { 0x1f10, 0x1ff0, 16, 1, 10, &z8002_device::Z1F_ddN0_0000 }, + { 0x2000, 0x200f, 1, 2, 7, &z8002_device::Z20_0000_dddd_imm8 }, + { 0x2010, 0x20ff, 1, 1, 7, &z8002_device::Z20_ssN0_dddd }, + { 0x2100, 0x210f, 1, 2, 7, &z8002_device::Z21_0000_dddd_imm16 }, + { 0x2110, 0x21ff, 1, 1, 7, &z8002_device::Z21_ssN0_dddd }, + { 0x2200, 0x220f, 1, 2, 10, &z8002_device::Z22_0000_ssss_0000_dddd_0000_0000 }, + { 0x2210, 0x22ff, 1, 1, 11, &z8002_device::Z22_ddN0_imm4 }, + { 0x2300, 0x230f, 1, 2, 10, &z8002_device::Z23_0000_ssss_0000_dddd_0000_0000 }, + { 0x2310, 0x23ff, 1, 1, 11, &z8002_device::Z23_ddN0_imm4 }, + { 0x2400, 0x240f, 1, 2, 10, &z8002_device::Z24_0000_ssss_0000_dddd_0000_0000 }, + { 0x2410, 0x24ff, 1, 1, 11, &z8002_device::Z24_ddN0_imm4 }, + { 0x2500, 0x250f, 1, 2, 10, &z8002_device::Z25_0000_ssss_0000_dddd_0000_0000 }, + { 0x2510, 0x25ff, 1, 1, 11, &z8002_device::Z25_ddN0_imm4 }, + { 0x2600, 0x260f, 1, 2, 10, &z8002_device::Z26_0000_ssss_0000_dddd_0000_0000 }, + { 0x2610, 0x26ff, 1, 1, 8, &z8002_device::Z26_ddN0_imm4 }, + { 0x2700, 0x270f, 1, 2, 10, &z8002_device::Z27_0000_ssss_0000_dddd_0000_0000 }, + { 0x2710, 0x27ff, 1, 1, 8, &z8002_device::Z27_ddN0_imm4 }, + { 0x2810, 0x28ff, 1, 1, 11, &z8002_device::Z28_ddN0_imm4m1 }, + { 0x2910, 0x29ff, 1, 1, 11, &z8002_device::Z29_ddN0_imm4m1 }, + { 0x2a10, 0x2aff, 1, 1, 11, &z8002_device::Z2A_ddN0_imm4m1 }, + { 0x2b10, 0x2bff, 1, 1, 11, &z8002_device::Z2B_ddN0_imm4m1 }, + { 0x2c10, 0x2cff, 1, 1, 12, &z8002_device::Z2C_ssN0_dddd }, + { 0x2d10, 0x2dff, 1, 1, 12, &z8002_device::Z2D_ssN0_dddd }, + { 0x2e10, 0x2eff, 1, 1, 8, &z8002_device::Z2E_ddN0_ssss }, + { 0x2f10, 0x2fff, 1, 1, 8, &z8002_device::Z2F_ddN0_ssss }, + { 0x3000, 0x300f, 1, 2, 14, &z8002_device::Z30_0000_dddd_dsp16 }, + { 0x3010, 0x30ff, 1, 2, 14, &z8002_device::Z30_ssN0_dddd_imm16 }, + { 0x3100, 0x310f, 1, 2, 14, &z8002_device::Z31_0000_dddd_dsp16 }, + { 0x3110, 0x31ff, 1, 2, 14, &z8002_device::Z31_ssN0_dddd_imm16 }, + { 0x3200, 0x320f, 1, 2, 14, &z8002_device::Z32_0000_ssss_dsp16 }, + { 0x3210, 0x32ff, 1, 2, 14, &z8002_device::Z32_ddN0_ssss_imm16 }, + { 0x3300, 0x330f, 1, 2, 14, &z8002_device::Z33_0000_ssss_dsp16 }, + { 0x3310, 0x33ff, 1, 2, 14, &z8002_device::Z33_ddN0_ssss_imm16 }, + { 0x3400, 0x340f, 1, 2, 15, &z8002_device::Z34_0000_dddd_dsp16 }, + { 0x3410, 0x34ff, 1, 2, 15, &z8002_device::Z34_ssN0_dddd_imm16 }, + { 0x3500, 0x350f, 1, 2, 17, &z8002_device::Z35_0000_dddd_dsp16 }, + { 0x3510, 0x35ff, 1, 2, 17, &z8002_device::Z35_ssN0_dddd_imm16 }, + { 0x3600, 0x3600, 1, 1, 2, &z8002_device::Z36_0000_0000 }, + { 0x3601, 0x36ff, 1, 1, 10, &z8002_device::Z36_imm8 }, + { 0x3700, 0x370f, 1, 2, 17, &z8002_device::Z37_0000_ssss_dsp16 }, + { 0x3710, 0x37ff, 1, 2, 17, &z8002_device::Z37_ddN0_ssss_imm16 }, + { 0x3800, 0x38ff, 1, 1, 10, &z8002_device::Z38_imm8 }, + { 0x3910, 0x39f0, 16, 1, 12, &z8002_device::Z39_ssN0_0000 }, + { 0x3a00, 0x3af0, 16, 2, 21, &z8002_device::Z3A_ssss_0000_0000_aaaa_dddd_x000 }, + { 0x3a01, 0x3af1, 16, 2, 21, &z8002_device::Z3A_ssss_0001_0000_aaaa_dddd_x000 }, + { 0x3a02, 0x3af2, 16, 2, 21, &z8002_device::Z3A_ssss_0010_0000_aaaa_dddd_x000 }, + { 0x3a03, 0x3af3, 16, 2, 21, &z8002_device::Z3A_ssss_0011_0000_aaaa_dddd_x000 }, + { 0x3a04, 0x3af4, 16, 2, 10, &z8002_device::Z3A_dddd_0100_imm16 }, + { 0x3a05, 0x3af5, 16, 2, 10, &z8002_device::Z3A_dddd_0101_imm16 }, + { 0x3a06, 0x3af6, 16, 2, 12, &z8002_device::Z3A_ssss_0110_imm16 }, + { 0x3a07, 0x3af7, 16, 2, 12, &z8002_device::Z3A_ssss_0111_imm16 }, + { 0x3a08, 0x3af8, 16, 2, 21, &z8002_device::Z3A_ssss_1000_0000_aaaa_dddd_x000 }, + { 0x3a09, 0x3af9, 16, 2, 21, &z8002_device::Z3A_ssss_1001_0000_aaaa_dddd_x000 }, + { 0x3a0a, 0x3afa, 16, 2, 21, &z8002_device::Z3A_ssss_1010_0000_aaaa_dddd_x000 }, + { 0x3a0b, 0x3afb, 16, 2, 21, &z8002_device::Z3A_ssss_1011_0000_aaaa_dddd_x000 }, + { 0x3b00, 0x3bf0, 16, 2, 21, &z8002_device::Z3B_ssss_0000_0000_aaaa_dddd_x000 }, + { 0x3b01, 0x3bf1, 16, 2, 21, &z8002_device::Z3B_ssss_0001_0000_aaaa_dddd_x000 }, + { 0x3b02, 0x3bf2, 16, 2, 21, &z8002_device::Z3B_ssss_0010_0000_aaaa_dddd_x000 }, + { 0x3b03, 0x3bf3, 16, 2, 21, &z8002_device::Z3B_ssss_0011_0000_aaaa_dddd_x000 }, + { 0x3b04, 0x3bf4, 16, 2, 12, &z8002_device::Z3B_dddd_0100_imm16 }, + { 0x3b05, 0x3bf5, 16, 2, 12, &z8002_device::Z3B_dddd_0101_imm16 }, + { 0x3b06, 0x3bf6, 16, 2, 12, &z8002_device::Z3B_ssss_0110_imm16 }, + { 0x3b07, 0x3bf7, 16, 2, 12, &z8002_device::Z3B_ssss_0111_imm16 }, + { 0x3b08, 0x3bf8, 16, 2, 21, &z8002_device::Z3B_ssss_1000_0000_aaaa_dddd_x000 }, + { 0x3b09, 0x3bf9, 16, 2, 21, &z8002_device::Z3B_ssss_1001_0000_aaaa_dddd_x000 }, + { 0x3b0a, 0x3bfa, 16, 2, 21, &z8002_device::Z3B_ssss_1010_0000_aaaa_dddd_x000 }, + { 0x3b0b, 0x3bfb, 16, 2, 21, &z8002_device::Z3B_ssss_1011_0000_aaaa_dddd_x000 }, + { 0x3c00, 0x3cff, 1, 1, 10, &z8002_device::Z3C_ssss_dddd }, + { 0x3d00, 0x3dff, 1, 1, 10, &z8002_device::Z3D_ssss_dddd }, + { 0x3e00, 0x3eff, 1, 1, 12, &z8002_device::Z3E_dddd_ssss }, + { 0x3f00, 0x3fff, 1, 1, 12, &z8002_device::Z3F_dddd_ssss }, + { 0x4000, 0x400f, 1, 2, 9, &z8002_device::Z40_0000_dddd_addr }, + { 0x4010, 0x40ff, 1, 2, 10, &z8002_device::Z40_ssN0_dddd_addr }, + { 0x4100, 0x410f, 1, 2, 9, &z8002_device::Z41_0000_dddd_addr }, + { 0x4110, 0x41ff, 1, 2, 10, &z8002_device::Z41_ssN0_dddd_addr }, + { 0x4200, 0x420f, 1, 2, 9, &z8002_device::Z42_0000_dddd_addr }, + { 0x4210, 0x42ff, 1, 2, 10, &z8002_device::Z42_ssN0_dddd_addr }, + { 0x4300, 0x430f, 1, 2, 9, &z8002_device::Z43_0000_dddd_addr }, + { 0x4310, 0x43ff, 1, 2, 10, &z8002_device::Z43_ssN0_dddd_addr }, + { 0x4400, 0x440f, 1, 2, 9, &z8002_device::Z44_0000_dddd_addr }, + { 0x4410, 0x44ff, 1, 2, 10, &z8002_device::Z44_ssN0_dddd_addr }, + { 0x4500, 0x450f, 1, 2, 9, &z8002_device::Z45_0000_dddd_addr }, + { 0x4510, 0x45ff, 1, 2, 10, &z8002_device::Z45_ssN0_dddd_addr }, + { 0x4600, 0x460f, 1, 2, 9, &z8002_device::Z46_0000_dddd_addr }, + { 0x4610, 0x46ff, 1, 2, 10, &z8002_device::Z46_ssN0_dddd_addr }, + { 0x4700, 0x470f, 1, 2, 9, &z8002_device::Z47_0000_dddd_addr }, + { 0x4710, 0x47ff, 1, 2, 10, &z8002_device::Z47_ssN0_dddd_addr }, + { 0x4800, 0x480f, 1, 2, 9, &z8002_device::Z48_0000_dddd_addr }, + { 0x4810, 0x48ff, 1, 2, 10, &z8002_device::Z48_ssN0_dddd_addr }, + { 0x4900, 0x490f, 1, 2, 9, &z8002_device::Z49_0000_dddd_addr }, + { 0x4910, 0x49ff, 1, 2, 10, &z8002_device::Z49_ssN0_dddd_addr }, + { 0x4a00, 0x4a0f, 1, 2, 9, &z8002_device::Z4A_0000_dddd_addr }, + { 0x4a10, 0x4aff, 1, 2, 10, &z8002_device::Z4A_ssN0_dddd_addr }, + { 0x4b00, 0x4b0f, 1, 2, 9, &z8002_device::Z4B_0000_dddd_addr }, + { 0x4b10, 0x4bff, 1, 2, 10, &z8002_device::Z4B_ssN0_dddd_addr }, + { 0x4c00, 0x4c00, 1, 2, 15, &z8002_device::Z4C_0000_0000_addr }, + { 0x4c01, 0x4c01, 1, 3, 14, &z8002_device::Z4C_0000_0001_addr_imm8 }, + { 0x4c02, 0x4c02, 1, 2, 15, &z8002_device::Z4C_0000_0010_addr }, + { 0x4c04, 0x4c04, 1, 2, 11, &z8002_device::Z4C_0000_0100_addr }, + { 0x4c05, 0x4c05, 1, 3, 14, &z8002_device::Z4C_0000_0101_addr_imm8 }, + { 0x4c06, 0x4c06, 1, 2, 14, &z8002_device::Z4C_0000_0110_addr }, + { 0x4c08, 0x4c08, 1, 2, 11, &z8002_device::Z4C_0000_1000_addr }, + { 0x4c10, 0x4cf0, 16, 2, 16, &z8002_device::Z4C_ddN0_0000_addr }, + { 0x4c11, 0x4cf1, 16, 3, 15, &z8002_device::Z4C_ddN0_0001_addr_imm8 }, + { 0x4c12, 0x4cf2, 16, 2, 16, &z8002_device::Z4C_ddN0_0010_addr }, + { 0x4c14, 0x4cf4, 16, 2, 12, &z8002_device::Z4C_ddN0_0100_addr }, + { 0x4c15, 0x4cf5, 16, 3, 15, &z8002_device::Z4C_ddN0_0101_addr_imm8 }, + { 0x4c16, 0x4cf6, 16, 2, 15, &z8002_device::Z4C_ddN0_0110_addr }, + { 0x4c18, 0x4cf8, 16, 2, 12, &z8002_device::Z4C_ddN0_1000_addr }, + { 0x4d00, 0x4d00, 1, 2, 15, &z8002_device::Z4D_0000_0000_addr }, + { 0x4d01, 0x4d01, 1, 3, 14, &z8002_device::Z4D_0000_0001_addr_imm16 }, + { 0x4d02, 0x4d02, 1, 2, 15, &z8002_device::Z4D_0000_0010_addr }, + { 0x4d04, 0x4d04, 1, 2, 11, &z8002_device::Z4D_0000_0100_addr }, + { 0x4d05, 0x4d05, 1, 3, 14, &z8002_device::Z4D_0000_0101_addr_imm16 }, + { 0x4d06, 0x4d06, 1, 2, 14, &z8002_device::Z4D_0000_0110_addr }, + { 0x4d08, 0x4d08, 1, 2, 11, &z8002_device::Z4D_0000_1000_addr }, + { 0x4d10, 0x4df0, 16, 2, 16, &z8002_device::Z4D_ddN0_0000_addr }, + { 0x4d11, 0x4df1, 16, 3, 15, &z8002_device::Z4D_ddN0_0001_addr_imm16 }, + { 0x4d12, 0x4df2, 16, 2, 16, &z8002_device::Z4D_ddN0_0010_addr }, + { 0x4d14, 0x4df4, 16, 2, 12, &z8002_device::Z4D_ddN0_0100_addr }, + { 0x4d15, 0x4df5, 16, 3, 15, &z8002_device::Z4D_ddN0_0101_addr_imm16 }, + { 0x4d16, 0x4df6, 16, 2, 15, &z8002_device::Z4D_ddN0_0110_addr }, + { 0x4d18, 0x4df8, 16, 2, 12, &z8002_device::Z4D_ddN0_1000_addr }, + { 0x4e11, 0x4ef0, 16, 2, 12, &z8002_device::Z4E_ddN0_ssN0_addr }, + { 0x5000, 0x500f, 1, 2, 15, &z8002_device::Z50_0000_dddd_addr }, + { 0x5010, 0x50ff, 1, 2, 16, &z8002_device::Z50_ssN0_dddd_addr }, + { 0x5110, 0x51f0, 16, 2, 21, &z8002_device::Z51_ddN0_0000_addr }, + { 0x5111, 0x51f1, 16, 2, 21, &z8002_device::Z51_ddN0_ssN0_addr }, + { 0x5112, 0x51f2, 16, 2, 21, &z8002_device::Z51_ddN0_ssN0_addr }, + { 0x5113, 0x51f3, 16, 2, 21, &z8002_device::Z51_ddN0_ssN0_addr }, + { 0x5114, 0x51f4, 16, 2, 21, &z8002_device::Z51_ddN0_ssN0_addr }, + { 0x5115, 0x51f5, 16, 2, 21, &z8002_device::Z51_ddN0_ssN0_addr }, + { 0x5116, 0x51f6, 16, 2, 21, &z8002_device::Z51_ddN0_ssN0_addr }, + { 0x5117, 0x51f7, 16, 2, 21, &z8002_device::Z51_ddN0_ssN0_addr }, + { 0x5118, 0x51f8, 16, 2, 21, &z8002_device::Z51_ddN0_ssN0_addr }, + { 0x5119, 0x51f9, 16, 2, 21, &z8002_device::Z51_ddN0_ssN0_addr }, + { 0x511a, 0x51fa, 16, 2, 21, &z8002_device::Z51_ddN0_ssN0_addr }, + { 0x511b, 0x51fb, 16, 2, 21, &z8002_device::Z51_ddN0_ssN0_addr }, + { 0x511c, 0x51fc, 16, 2, 21, &z8002_device::Z51_ddN0_ssN0_addr }, + { 0x511d, 0x51fd, 16, 2, 21, &z8002_device::Z51_ddN0_ssN0_addr }, + { 0x511e, 0x51fe, 16, 2, 21, &z8002_device::Z51_ddN0_ssN0_addr }, + { 0x511f, 0x51ff, 16, 2, 21, &z8002_device::Z51_ddN0_ssN0_addr }, + { 0x5200, 0x520f, 1, 2, 15, &z8002_device::Z52_0000_dddd_addr }, + { 0x5210, 0x52ff, 1, 2, 16, &z8002_device::Z52_ssN0_dddd_addr }, + { 0x5310, 0x53f0, 16, 2, 14, &z8002_device::Z53_ddN0_0000_addr }, + { 0x5311, 0x53f1, 16, 2, 14, &z8002_device::Z53_ddN0_ssN0_addr }, + { 0x5312, 0x53f2, 16, 2, 14, &z8002_device::Z53_ddN0_ssN0_addr }, + { 0x5313, 0x53f3, 16, 2, 14, &z8002_device::Z53_ddN0_ssN0_addr }, + { 0x5314, 0x53f4, 16, 2, 14, &z8002_device::Z53_ddN0_ssN0_addr }, + { 0x5315, 0x53f5, 16, 2, 14, &z8002_device::Z53_ddN0_ssN0_addr }, + { 0x5316, 0x53f6, 16, 2, 14, &z8002_device::Z53_ddN0_ssN0_addr }, + { 0x5317, 0x53f7, 16, 2, 14, &z8002_device::Z53_ddN0_ssN0_addr }, + { 0x5318, 0x53f8, 16, 2, 14, &z8002_device::Z53_ddN0_ssN0_addr }, + { 0x5319, 0x53f9, 16, 2, 14, &z8002_device::Z53_ddN0_ssN0_addr }, + { 0x531a, 0x53fa, 16, 2, 14, &z8002_device::Z53_ddN0_ssN0_addr }, + { 0x531b, 0x53fb, 16, 2, 14, &z8002_device::Z53_ddN0_ssN0_addr }, + { 0x531c, 0x53fc, 16, 2, 14, &z8002_device::Z53_ddN0_ssN0_addr }, + { 0x531d, 0x53fd, 16, 2, 14, &z8002_device::Z53_ddN0_ssN0_addr }, + { 0x531e, 0x53fe, 16, 2, 14, &z8002_device::Z53_ddN0_ssN0_addr }, + { 0x531f, 0x53ff, 16, 2, 14, &z8002_device::Z53_ddN0_ssN0_addr }, + { 0x5400, 0x540f, 1, 2, 12, &z8002_device::Z54_0000_dddd_addr }, + { 0x5410, 0x54ff, 1, 2, 13, &z8002_device::Z54_ssN0_dddd_addr }, + { 0x5510, 0x55f0, 16, 2, 23, &z8002_device::Z55_ssN0_0000_addr }, + { 0x5511, 0x55f1, 16, 2, 23, &z8002_device::Z55_ssN0_ddN0_addr }, + { 0x5512, 0x55f2, 16, 2, 23, &z8002_device::Z55_ssN0_ddN0_addr }, + { 0x5513, 0x55f3, 16, 2, 23, &z8002_device::Z55_ssN0_ddN0_addr }, + { 0x5514, 0x55f4, 16, 2, 23, &z8002_device::Z55_ssN0_ddN0_addr }, + { 0x5515, 0x55f5, 16, 2, 23, &z8002_device::Z55_ssN0_ddN0_addr }, + { 0x5516, 0x55f6, 16, 2, 23, &z8002_device::Z55_ssN0_ddN0_addr }, + { 0x5517, 0x55f7, 16, 2, 23, &z8002_device::Z55_ssN0_ddN0_addr }, + { 0x5518, 0x55f8, 16, 2, 23, &z8002_device::Z55_ssN0_ddN0_addr }, + { 0x5519, 0x55f9, 16, 2, 23, &z8002_device::Z55_ssN0_ddN0_addr }, + { 0x551a, 0x55fa, 16, 2, 23, &z8002_device::Z55_ssN0_ddN0_addr }, + { 0x551b, 0x55fb, 16, 2, 23, &z8002_device::Z55_ssN0_ddN0_addr }, + { 0x551c, 0x55fc, 16, 2, 23, &z8002_device::Z55_ssN0_ddN0_addr }, + { 0x551d, 0x55fd, 16, 2, 23, &z8002_device::Z55_ssN0_ddN0_addr }, + { 0x551e, 0x55fe, 16, 2, 23, &z8002_device::Z55_ssN0_ddN0_addr }, + { 0x551f, 0x55ff, 16, 2, 23, &z8002_device::Z55_ssN0_ddN0_addr }, + { 0x5600, 0x560f, 1, 2, 15, &z8002_device::Z56_0000_dddd_addr }, + { 0x5610, 0x56ff, 1, 2, 16, &z8002_device::Z56_ssN0_dddd_addr }, + { 0x5710, 0x57f0, 16, 2, 16, &z8002_device::Z57_ssN0_0000_addr }, + { 0x5711, 0x57f1, 16, 2, 16, &z8002_device::Z57_ssN0_ddN0_addr }, + { 0x5712, 0x57f2, 16, 2, 16, &z8002_device::Z57_ssN0_ddN0_addr }, + { 0x5713, 0x57f3, 16, 2, 16, &z8002_device::Z57_ssN0_ddN0_addr }, + { 0x5714, 0x57f4, 16, 2, 16, &z8002_device::Z57_ssN0_ddN0_addr }, + { 0x5715, 0x57f5, 16, 2, 16, &z8002_device::Z57_ssN0_ddN0_addr }, + { 0x5716, 0x57f6, 16, 2, 16, &z8002_device::Z57_ssN0_ddN0_addr }, + { 0x5717, 0x57f7, 16, 2, 16, &z8002_device::Z57_ssN0_ddN0_addr }, + { 0x5718, 0x57f8, 16, 2, 16, &z8002_device::Z57_ssN0_ddN0_addr }, + { 0x5719, 0x57f9, 16, 2, 16, &z8002_device::Z57_ssN0_ddN0_addr }, + { 0x571a, 0x57fa, 16, 2, 16, &z8002_device::Z57_ssN0_ddN0_addr }, + { 0x571b, 0x57fb, 16, 2, 16, &z8002_device::Z57_ssN0_ddN0_addr }, + { 0x571c, 0x57fc, 16, 2, 16, &z8002_device::Z57_ssN0_ddN0_addr }, + { 0x571d, 0x57fd, 16, 2, 16, &z8002_device::Z57_ssN0_ddN0_addr }, + { 0x571e, 0x57fe, 16, 2, 16, &z8002_device::Z57_ssN0_ddN0_addr }, + { 0x571f, 0x57ff, 16, 2, 16, &z8002_device::Z57_ssN0_ddN0_addr }, + { 0x5800, 0x580f, 1, 2, 283, &z8002_device::Z58_0000_dddd_addr }, + { 0x5810, 0x58ff, 1, 2, 284, &z8002_device::Z58_ssN0_dddd_addr }, + { 0x5900, 0x590f, 1, 2, 71, &z8002_device::Z59_0000_dddd_addr }, + { 0x5910, 0x59ff, 1, 2, 72, &z8002_device::Z59_ssN0_dddd_addr }, + { 0x5a00, 0x5a0f, 1, 2, 745, &z8002_device::Z5A_0000_dddd_addr }, + { 0x5a10, 0x5aff, 1, 2, 746, &z8002_device::Z5A_ssN0_dddd_addr }, + { 0x5b00, 0x5b0f, 1, 2, 108, &z8002_device::Z5B_0000_dddd_addr }, + { 0x5b10, 0x5bff, 1, 2, 109, &z8002_device::Z5B_ssN0_dddd_addr }, + { 0x5c01, 0x5c01, 1, 3, 14, &z8002_device::Z5C_0000_0001_0000_dddd_0000_nmin1_addr }, + { 0x5c08, 0x5c08, 1, 2, 16, &z8002_device::Z5C_0000_1000_addr }, + { 0x5c09, 0x5c09, 1, 3, 14, &z8002_device::Z5C_0000_1001_0000_ssss_0000_nmin1_addr }, + { 0x5c11, 0x5cf1, 16, 3, 15, &z8002_device::Z5C_ssN0_0001_0000_dddd_0000_nmin1_addr }, + { 0x5c18, 0x5cf8, 16, 2, 17, &z8002_device::Z5C_ddN0_1000_addr }, + { 0x5c19, 0x5cf9, 16, 3, 15, &z8002_device::Z5C_ddN0_1001_0000_ssN0_0000_nmin1_addr }, + { 0x5d00, 0x5d0f, 1, 2, 15, &z8002_device::Z5D_0000_ssss_addr }, + { 0x5d10, 0x5dff, 1, 2, 14, &z8002_device::Z5D_ddN0_ssss_addr }, + { 0x5e00, 0x5e0f, 1, 2, 7, &z8002_device::Z5E_0000_cccc_addr }, + { 0x5e10, 0x5eff, 1, 2, 8, &z8002_device::Z5E_ddN0_cccc_addr }, + { 0x5f00, 0x5f00, 1, 2, 12, &z8002_device::Z5F_0000_0000_addr }, + { 0x5f10, 0x5ff0, 16, 2, 13, &z8002_device::Z5F_ddN0_0000_addr }, + { 0x6000, 0x600f, 1, 2, 9, &z8002_device::Z60_0000_dddd_addr }, + { 0x6010, 0x60ff, 1, 2, 10, &z8002_device::Z60_ssN0_dddd_addr }, + { 0x6100, 0x610f, 1, 2, 9, &z8002_device::Z61_0000_dddd_addr }, + { 0x6110, 0x61ff, 1, 2, 10, &z8002_device::Z61_ssN0_dddd_addr }, + { 0x6200, 0x620f, 1, 2, 13, &z8002_device::Z62_0000_imm4_addr }, + { 0x6210, 0x62ff, 1, 2, 14, &z8002_device::Z62_ddN0_imm4_addr }, + { 0x6300, 0x630f, 1, 2, 13, &z8002_device::Z63_0000_imm4_addr }, + { 0x6310, 0x63ff, 1, 2, 14, &z8002_device::Z63_ddN0_imm4_addr }, + { 0x6400, 0x640f, 1, 2, 13, &z8002_device::Z64_0000_imm4_addr }, + { 0x6410, 0x64ff, 1, 2, 14, &z8002_device::Z64_ddN0_imm4_addr }, + { 0x6500, 0x650f, 1, 2, 13, &z8002_device::Z65_0000_imm4_addr }, + { 0x6510, 0x65ff, 1, 2, 14, &z8002_device::Z65_ddN0_imm4_addr }, + { 0x6600, 0x660f, 1, 2, 10, &z8002_device::Z66_0000_imm4_addr }, + { 0x6610, 0x66ff, 1, 2, 11, &z8002_device::Z66_ddN0_imm4_addr }, + { 0x6700, 0x670f, 1, 2, 10, &z8002_device::Z67_0000_imm4_addr }, + { 0x6710, 0x67ff, 1, 2, 11, &z8002_device::Z67_ddN0_imm4_addr }, + { 0x6800, 0x680f, 1, 2, 13, &z8002_device::Z68_0000_imm4m1_addr }, + { 0x6810, 0x68ff, 1, 2, 14, &z8002_device::Z68_ddN0_imm4m1_addr }, + { 0x6900, 0x690f, 1, 2, 13, &z8002_device::Z69_0000_imm4m1_addr }, + { 0x6910, 0x69ff, 1, 2, 14, &z8002_device::Z69_ddN0_imm4m1_addr }, + { 0x6a00, 0x6a0f, 1, 2, 13, &z8002_device::Z6A_0000_imm4m1_addr }, + { 0x6a10, 0x6aff, 1, 2, 14, &z8002_device::Z6A_ddN0_imm4m1_addr }, + { 0x6b00, 0x6b0f, 1, 2, 13, &z8002_device::Z6B_0000_imm4m1_addr }, + { 0x6b10, 0x6bff, 1, 2, 14, &z8002_device::Z6B_ddN0_imm4m1_addr }, + { 0x6c00, 0x6c0f, 1, 2, 15, &z8002_device::Z6C_0000_dddd_addr }, + { 0x6c10, 0x6cff, 1, 2, 16, &z8002_device::Z6C_ssN0_dddd_addr }, + { 0x6d00, 0x6d0f, 1, 2, 15, &z8002_device::Z6D_0000_dddd_addr }, + { 0x6d10, 0x6dff, 1, 2, 16, &z8002_device::Z6D_ssN0_dddd_addr }, + { 0x6e00, 0x6e0f, 1, 2, 11, &z8002_device::Z6E_0000_ssss_addr }, + { 0x6e10, 0x6eff, 1, 2, 11, &z8002_device::Z6E_ddN0_ssss_addr }, + { 0x6f00, 0x6f0f, 1, 2, 11, &z8002_device::Z6F_0000_ssss_addr }, + { 0x6f10, 0x6fff, 1, 2, 12, &z8002_device::Z6F_ddN0_ssss_addr }, + { 0x7010, 0x70ff, 1, 2, 14, &z8002_device::Z70_ssN0_dddd_0000_xxxx_0000_0000 }, + { 0x7110, 0x71ff, 1, 2, 14, &z8002_device::Z71_ssN0_dddd_0000_xxxx_0000_0000 }, + { 0x7210, 0x72ff, 1, 2, 14, &z8002_device::Z72_ddN0_ssss_0000_xxxx_0000_0000 }, + { 0x7310, 0x73ff, 1, 2, 14, &z8002_device::Z73_ddN0_ssss_0000_xxxx_0000_0000 }, + { 0x7410, 0x74ff, 1, 2, 15, &z8002_device::Z74_ssN0_dddd_0000_xxxx_0000_0000 }, + { 0x7510, 0x75ff, 1, 2, 17, &z8002_device::Z75_ssN0_dddd_0000_xxxx_0000_0000 }, + { 0x7600, 0x760f, 1, 2, 12, &z8002_device::Z76_0000_dddd_addr }, + { 0x7610, 0x76ff, 1, 2, 13, &z8002_device::Z76_ssN0_dddd_addr }, + { 0x7710, 0x77ff, 1, 2, 17, &z8002_device::Z77_ddN0_ssss_0000_xxxx_0000_0000 }, + { 0x7800, 0x78ff, 1, 1, 10, &z8002_device::Z78_imm8 }, + { 0x7900, 0x7900, 1, 2, 16, &z8002_device::Z79_0000_0000_addr }, + { 0x7910, 0x79f0, 16, 2, 17, &z8002_device::Z79_ssN0_0000_addr }, + { 0x7a00, 0x7a00, 1, 1, 8, &z8002_device::Z7A_0000_0000 }, + { 0x7b00, 0x7b00, 1, 1, 13, &z8002_device::Z7B_0000_0000 }, + { 0x7b08, 0x7b08, 1, 1, 5, &z8002_device::Z7B_0000_1000 }, + { 0x7b09, 0x7b09, 1, 1, 5, &z8002_device::Z7B_0000_1001 }, + { 0x7b0a, 0x7b0a, 1, 1, 7, &z8002_device::Z7B_0000_1010 }, + { 0x7b0d, 0x7bfd, 16, 1, 12, &z8002_device::Z7B_dddd_1101 }, + { 0x7c00, 0x7c03, 1, 1, 7, &z8002_device::Z7C_0000_00ii }, + { 0x7c04, 0x7c07, 1, 1, 7, &z8002_device::Z7C_0000_01ii }, + { 0x7d00, 0x7df0, 16, 1, 7, &z8002_device::Z7D_dddd_0ccc }, + { 0x7d01, 0x7df1, 16, 1, 7, &z8002_device::Z7D_dddd_0ccc }, + { 0x7d02, 0x7df2, 16, 1, 7, &z8002_device::Z7D_dddd_0ccc }, + { 0x7d03, 0x7df3, 16, 1, 7, &z8002_device::Z7D_dddd_0ccc }, + { 0x7d04, 0x7df4, 16, 1, 7, &z8002_device::Z7D_dddd_0ccc }, + { 0x7d05, 0x7df5, 16, 1, 7, &z8002_device::Z7D_dddd_0ccc }, + { 0x7d06, 0x7df6, 16, 1, 7, &z8002_device::Z7D_dddd_0ccc }, + { 0x7d07, 0x7df7, 16, 1, 7, &z8002_device::Z7D_dddd_0ccc }, + { 0x7d08, 0x7df8, 16, 1, 7, &z8002_device::Z7D_ssss_1ccc }, + { 0x7d09, 0x7df9, 16, 1, 7, &z8002_device::Z7D_ssss_1ccc }, + { 0x7d0a, 0x7dfa, 16, 1, 7, &z8002_device::Z7D_ssss_1ccc }, + { 0x7d0b, 0x7dfb, 16, 1, 7, &z8002_device::Z7D_ssss_1ccc }, + { 0x7d0c, 0x7dfc, 16, 1, 7, &z8002_device::Z7D_ssss_1ccc }, + { 0x7d0d, 0x7dfd, 16, 1, 7, &z8002_device::Z7D_ssss_1ccc }, + { 0x7d0e, 0x7dfe, 16, 1, 7, &z8002_device::Z7D_ssss_1ccc }, + { 0x7d0f, 0x7dff, 16, 1, 7, &z8002_device::Z7D_ssss_1ccc }, + { 0x7e00, 0x7eff, 1, 1, 10, &z8002_device::Z7E_imm8 }, + { 0x7f00, 0x7fff, 1, 1, 33, &z8002_device::Z7F_imm8 }, + { 0x8000, 0x80ff, 1, 1, 4, &z8002_device::Z80_ssss_dddd }, + { 0x8100, 0x81ff, 1, 1, 4, &z8002_device::Z81_ssss_dddd }, + { 0x8200, 0x82ff, 1, 1, 4, &z8002_device::Z82_ssss_dddd }, + { 0x8300, 0x83ff, 1, 1, 4, &z8002_device::Z83_ssss_dddd }, + { 0x8400, 0x84ff, 1, 1, 4, &z8002_device::Z84_ssss_dddd }, + { 0x8500, 0x85ff, 1, 1, 4, &z8002_device::Z85_ssss_dddd }, + { 0x8600, 0x86ff, 1, 1, 4, &z8002_device::Z86_ssss_dddd }, + { 0x8700, 0x87ff, 1, 1, 4, &z8002_device::Z87_ssss_dddd }, + { 0x8800, 0x88ff, 1, 1, 4, &z8002_device::Z88_ssss_dddd }, + { 0x8900, 0x89ff, 1, 1, 4, &z8002_device::Z89_ssss_dddd }, + { 0x8a00, 0x8aff, 1, 1, 4, &z8002_device::Z8A_ssss_dddd }, + { 0x8b00, 0x8bff, 1, 1, 4, &z8002_device::Z8B_ssss_dddd }, + { 0x8c00, 0x8cf0, 16, 1, 7, &z8002_device::Z8C_dddd_0000 }, + { 0x8c02, 0x8cf2, 16, 1, 7, &z8002_device::Z8C_dddd_0010 }, + { 0x8c04, 0x8cf4, 16, 1, 7, &z8002_device::Z8C_dddd_0100 }, + { 0x8c06, 0x8cf6, 16, 1, 7, &z8002_device::Z8C_dddd_0110 }, + { 0x8c01, 0x8cf1, 16, 1, 7, &z8002_device::Z8C_dddd_0001 }, + { 0x8c08, 0x8cf8, 16, 1, 7, &z8002_device::Z8C_dddd_1000 }, + { 0x8c09, 0x8cf9, 16, 1, 7, &z8002_device::Z8C_dddd_1001 }, + { 0x8d00, 0x8df0, 16, 1, 7, &z8002_device::Z8D_dddd_0000 }, + { 0x8d01, 0x8df1, 16, 1, 7, &z8002_device::Z8D_imm4_0001 }, + { 0x8d02, 0x8df2, 16, 1, 7, &z8002_device::Z8D_dddd_0010 }, + { 0x8d03, 0x8df3, 16, 1, 7, &z8002_device::Z8D_imm4_0011 }, + { 0x8d04, 0x8df4, 16, 1, 7, &z8002_device::Z8D_dddd_0100 }, + { 0x8d05, 0x8df5, 16, 1, 7, &z8002_device::Z8D_imm4_0101 }, + { 0x8d06, 0x8df6, 16, 1, 7, &z8002_device::Z8D_dddd_0110 }, + { 0x8d07, 0x8d07, 1, 1, 7, &z8002_device::Z8D_0000_0111 }, + { 0x8d08, 0x8df8, 16, 1, 7, &z8002_device::Z8D_dddd_1000 }, + { 0x8e00, 0x8eff, 1, 1, 10, &z8002_device::Z8E_imm8 }, + { 0x8f00, 0x8fff, 1, 1, 10, &z8002_device::Z8F_imm8 }, + { 0x9000, 0x90ff, 1, 1, 8, &z8002_device::Z90_ssss_dddd }, + { 0x9110, 0x91ff, 1, 1, 12, &z8002_device::Z91_ddN0_ssss }, + { 0x9200, 0x92ff, 1, 1, 8, &z8002_device::Z92_ssss_dddd }, + { 0x9310, 0x93ff, 1, 1, 9, &z8002_device::Z93_ddN0_ssss }, + { 0x9400, 0x94ff, 1, 1, 5, &z8002_device::Z94_ssss_dddd }, + { 0x9510, 0x95ff, 1, 1, 12, &z8002_device::Z95_ssN0_dddd }, + { 0x9600, 0x96ff, 1, 1, 8, &z8002_device::Z96_ssss_dddd }, + { 0x9710, 0x97ff, 1, 1, 8, &z8002_device::Z97_ssN0_dddd }, + { 0x9800, 0x98ff, 1, 1, 282, &z8002_device::Z98_ssss_dddd }, + { 0x9900, 0x99ff, 1, 1, 70, &z8002_device::Z99_ssss_dddd }, + { 0x9a00, 0x9aff, 1, 1, 744, &z8002_device::Z9A_ssss_dddd }, + { 0x9b00, 0x9bff, 1, 1, 107, &z8002_device::Z9B_ssss_dddd }, + { 0x9c00, 0x9cf8, 8, 1, 13, &z8002_device::Z9C_dddd_1000 }, + { 0x9d00, 0x9dff, 1, 1, 10, &z8002_device::Z9D_imm8 }, + { 0x9e00, 0x9e0f, 1, 1, 10, &z8002_device::Z9E_0000_cccc }, + { 0x9f00, 0x9fff, 1, 1, 10, &z8002_device::Z9F_imm8 }, + { 0xa000, 0xa0ff, 1, 1, 3, &z8002_device::ZA0_ssss_dddd }, + { 0xa100, 0xa1ff, 1, 1, 3, &z8002_device::ZA1_ssss_dddd }, + { 0xa200, 0xa2ff, 1, 1, 4, &z8002_device::ZA2_dddd_imm4 }, + { 0xa300, 0xa3ff, 1, 1, 4, &z8002_device::ZA3_dddd_imm4 }, + { 0xa400, 0xa4ff, 1, 1, 4, &z8002_device::ZA4_dddd_imm4 }, + { 0xa500, 0xa5ff, 1, 1, 4, &z8002_device::ZA5_dddd_imm4 }, + { 0xa600, 0xa6ff, 1, 1, 4, &z8002_device::ZA6_dddd_imm4 }, + { 0xa700, 0xa7ff, 1, 1, 4, &z8002_device::ZA7_dddd_imm4 }, + { 0xa800, 0xa8ff, 1, 1, 4, &z8002_device::ZA8_dddd_imm4m1 }, + { 0xa900, 0xa9ff, 1, 1, 4, &z8002_device::ZA9_dddd_imm4m1 }, + { 0xaa00, 0xaaff, 1, 1, 4, &z8002_device::ZAA_dddd_imm4m1 }, + { 0xab00, 0xabff, 1, 1, 4, &z8002_device::ZAB_dddd_imm4m1 }, + { 0xac00, 0xacff, 1, 1, 6, &z8002_device::ZAC_ssss_dddd }, + { 0xad00, 0xadff, 1, 1, 6, &z8002_device::ZAD_ssss_dddd }, + { 0xae00, 0xaeff, 1, 1, 5, &z8002_device::ZAE_dddd_cccc }, + { 0xaf00, 0xafff, 1, 1, 5, &z8002_device::ZAF_dddd_cccc }, + { 0xb000, 0xb0f0, 16, 1, 5, &z8002_device::ZB0_dddd_0000 }, + { 0xb100, 0xb1f0, 16, 1, 11, &z8002_device::ZB1_dddd_0000 }, + { 0xb107, 0xb1f7, 16, 1, 11, &z8002_device::ZB1_dddd_0111 }, + { 0xb10a, 0xb1fa, 16, 1, 11, &z8002_device::ZB1_dddd_1010 }, + { 0xb200, 0xb2f0, 16, 1, 6, &z8002_device::ZB2_dddd_00I0 }, + { 0xb201, 0xb2f1, 16, 2, 13, &z8002_device::ZB2_dddd_0001_imm8 }, + { 0xb202, 0xb2f2, 16, 1, 6, &z8002_device::ZB2_dddd_00I0 }, + { 0xb203, 0xb2f3, 16, 2, 15, &z8002_device::ZB2_dddd_0011_0000_ssss_0000_0000 }, + { 0xb204, 0xb2f4, 16, 1, 6, &z8002_device::ZB2_dddd_01I0 }, + { 0xb206, 0xb2f6, 16, 1, 6, &z8002_device::ZB2_dddd_01I0 }, + { 0xb208, 0xb2f8, 16, 1, 9, &z8002_device::ZB2_dddd_10I0 }, + { 0xb209, 0xb2f9, 16, 2, 13, &z8002_device::ZB2_dddd_1001_imm8 }, + { 0xb20a, 0xb2fa, 16, 1, 9, &z8002_device::ZB2_dddd_10I0 }, + { 0xb20b, 0xb2fb, 16, 2, 15, &z8002_device::ZB2_dddd_1011_0000_ssss_0000_0000 }, + { 0xb20c, 0xb2fc, 16, 1, 9, &z8002_device::ZB2_dddd_11I0 }, + { 0xb20e, 0xb2fe, 16, 1, 9, &z8002_device::ZB2_dddd_11I0 }, + { 0xb300, 0xb3f0, 16, 1, 6, &z8002_device::ZB3_dddd_00I0 }, + { 0xb301, 0xb3f1, 16, 2, 13, &z8002_device::ZB3_dddd_0001_imm8 }, + { 0xb302, 0xb3f2, 16, 1, 6, &z8002_device::ZB3_dddd_00I0 }, + { 0xb303, 0xb3f3, 16, 2, 15, &z8002_device::ZB3_dddd_0011_0000_ssss_0000_0000 }, + { 0xb304, 0xb3f4, 16, 1, 6, &z8002_device::ZB3_dddd_01I0 }, + { 0xb305, 0xb3f5, 16, 2, 13, &z8002_device::ZB3_dddd_0101_imm8 }, + { 0xb306, 0xb3f6, 16, 1, 6, &z8002_device::ZB3_dddd_01I0 }, + { 0xb307, 0xb3f7, 16, 2, 15, &z8002_device::ZB3_dddd_0111_0000_ssss_0000_0000 }, + { 0xb308, 0xb3f8, 16, 1, 6, &z8002_device::ZB3_dddd_10I0 }, + { 0xb309, 0xb3f9, 16, 2, 13, &z8002_device::ZB3_dddd_1001_imm8 }, + { 0xb30a, 0xb3fa, 16, 1, 6, &z8002_device::ZB3_dddd_10I0 }, + { 0xb30b, 0xb3fb, 16, 2, 15, &z8002_device::ZB3_dddd_1011_0000_ssss_0000_0000 }, + { 0xb30c, 0xb3fc, 16, 1, 6, &z8002_device::ZB3_dddd_11I0 }, + { 0xb30d, 0xb3fd, 16, 2, 13, &z8002_device::ZB3_dddd_1101_imm8 }, + { 0xb30e, 0xb3fe, 16, 1, 6, &z8002_device::ZB3_dddd_11I0 }, + { 0xb30f, 0xb3ff, 16, 2, 15, &z8002_device::ZB3_dddd_1111_0000_ssss_0000_0000 }, + { 0xb400, 0xb4ff, 1, 1, 5, &z8002_device::ZB4_ssss_dddd }, + { 0xb500, 0xb5ff, 1, 1, 5, &z8002_device::ZB5_ssss_dddd }, + { 0xb600, 0xb6ff, 1, 1, 5, &z8002_device::ZB6_ssss_dddd }, + { 0xb700, 0xb7ff, 1, 1, 5, &z8002_device::ZB7_ssss_dddd }, + { 0xb810, 0xb8f0, 16, 2, 25, &z8002_device::ZB8_ddN0_0000_0000_rrrr_ssN0_0000 }, + { 0xb812, 0xb8f2, 16, 2, 25, &z8002_device::ZB8_ddN0_0010_0000_rrrr_ssN0_0000 }, + { 0xb814, 0xb8f4, 16, 2, 25, &z8002_device::ZB8_ddN0_0100_0000_rrrr_ssN0_0000 }, + { 0xb816, 0xb8f6, 16, 2, 25, &z8002_device::ZB8_ddN0_0110_0000_rrrr_ssN0_1110 }, + { 0xb818, 0xb8f8, 16, 2, 25, &z8002_device::ZB8_ddN0_1000_0000_rrrr_ssN0_0000 }, + { 0xb81a, 0xb8fa, 16, 2, 25, &z8002_device::ZB8_ddN0_1010_0000_rrrr_ssN0_0000 }, + { 0xb81c, 0xb8fc, 16, 2, 25, &z8002_device::ZB8_ddN0_1100_0000_rrrr_ssN0_0000 }, + { 0xb81e, 0xb8fe, 16, 2, 25, &z8002_device::ZB8_ddN0_1110_0000_rrrr_ssN0_1110 }, + { 0xb900, 0xb9ff, 16, 1, 10, &z8002_device::ZB9_imm8 }, + { 0xba10, 0xbaf0, 16, 2, 11, &z8002_device::ZBA_ssN0_0000_0000_rrrr_dddd_cccc }, + { 0xba11, 0xbaf1, 16, 2, 11, &z8002_device::ZBA_ssN0_0001_0000_rrrr_ddN0_x000 }, + { 0xba12, 0xbaf2, 16, 2, 11, &z8002_device::ZBA_ssN0_0010_0000_rrrr_ddN0_cccc }, + { 0xba14, 0xbaf4, 16, 2, 11, &z8002_device::ZBA_ssN0_0100_0000_rrrr_dddd_cccc }, + { 0xba16, 0xbaf6, 16, 2, 11, &z8002_device::ZBA_ssN0_0110_0000_rrrr_ddN0_cccc }, + { 0xba18, 0xbaf8, 16, 2, 11, &z8002_device::ZBA_ssN0_1000_0000_rrrr_dddd_cccc }, + { 0xba19, 0xbaf9, 16, 2, 11, &z8002_device::ZBA_ssN0_1001_0000_rrrr_ddN0_x000 }, + { 0xba1a, 0xbafa, 16, 2, 11, &z8002_device::ZBA_ssN0_1010_0000_rrrr_ddN0_cccc }, + { 0xba1c, 0xbafc, 16, 2, 11, &z8002_device::ZBA_ssN0_1100_0000_rrrr_dddd_cccc }, + { 0xba1e, 0xbafe, 16, 2, 11, &z8002_device::ZBA_ssN0_1110_0000_rrrr_ddN0_cccc }, + { 0xbb10, 0xbbf0, 16, 2, 11, &z8002_device::ZBB_ssN0_0000_0000_rrrr_dddd_cccc }, + { 0xbb11, 0xbbf1, 16, 2, 11, &z8002_device::ZBB_ssN0_0001_0000_rrrr_ddN0_x000 }, + { 0xbb12, 0xbbf2, 16, 2, 11, &z8002_device::ZBB_ssN0_0010_0000_rrrr_ddN0_cccc }, + { 0xbb14, 0xbbf4, 16, 2, 11, &z8002_device::ZBB_ssN0_0100_0000_rrrr_dddd_cccc }, + { 0xbb16, 0xbbf6, 16, 2, 11, &z8002_device::ZBB_ssN0_0110_0000_rrrr_ddN0_cccc }, + { 0xbb18, 0xbbf8, 16, 2, 11, &z8002_device::ZBB_ssN0_1000_0000_rrrr_dddd_cccc }, + { 0xbb19, 0xbbf9, 16, 2, 11, &z8002_device::ZBB_ssN0_1001_0000_rrrr_ddN0_x000 }, + { 0xbb1a, 0xbbfa, 16, 2, 11, &z8002_device::ZBB_ssN0_1010_0000_rrrr_ddN0_cccc }, + { 0xbb1c, 0xbbfc, 16, 2, 11, &z8002_device::ZBB_ssN0_1100_0000_rrrr_dddd_cccc }, + { 0xbb1e, 0xbbfe, 16, 2, 11, &z8002_device::ZBB_ssN0_1110_0000_rrrr_ddN0_cccc }, + { 0xbc00, 0xbcff, 1, 1, 9, &z8002_device::ZBC_aaaa_bbbb }, + { 0xbd00, 0xbdff, 1, 1, 5, &z8002_device::ZBD_dddd_imm4 }, + { 0xbe00, 0xbeff, 1, 1, 9, &z8002_device::ZBE_aaaa_bbbb }, + { 0xbf00, 0xbfff, 1, 1, 10, &z8002_device::ZBF_imm8 }, + { 0xc000, 0xcfff, 1, 1, 5, &z8002_device::ZC_dddd_imm8 }, + { 0xd000, 0xdfff, 1, 1, 10, &z8002_device::ZD_dsp12 }, + { 0xe000, 0xefff, 1, 1, 6, &z8002_device::ZE_cccc_dsp8 }, + { 0xf000, 0xf07f, 1, 1, 11, &z8002_device::ZF_dddd_0dsp7 }, + { 0xf100, 0xf17f, 1, 1, 11, &z8002_device::ZF_dddd_0dsp7 }, + { 0xf200, 0xf27f, 1, 1, 11, &z8002_device::ZF_dddd_0dsp7 }, + { 0xf300, 0xf37f, 1, 1, 11, &z8002_device::ZF_dddd_0dsp7 }, + { 0xf400, 0xf47f, 1, 1, 11, &z8002_device::ZF_dddd_0dsp7 }, + { 0xf500, 0xf57f, 1, 1, 11, &z8002_device::ZF_dddd_0dsp7 }, + { 0xf600, 0xf67f, 1, 1, 11, &z8002_device::ZF_dddd_0dsp7 }, + { 0xf700, 0xf77f, 1, 1, 11, &z8002_device::ZF_dddd_0dsp7 }, + { 0xf800, 0xf87f, 1, 1, 11, &z8002_device::ZF_dddd_0dsp7 }, + { 0xf900, 0xf97f, 1, 1, 11, &z8002_device::ZF_dddd_0dsp7 }, + { 0xfa00, 0xfa7f, 1, 1, 11, &z8002_device::ZF_dddd_0dsp7 }, + { 0xfb00, 0xfb7f, 1, 1, 11, &z8002_device::ZF_dddd_0dsp7 }, + { 0xfc00, 0xfc7f, 1, 1, 11, &z8002_device::ZF_dddd_0dsp7 }, + { 0xfd00, 0xfd7f, 1, 1, 11, &z8002_device::ZF_dddd_0dsp7 }, + { 0xfe00, 0xfe7f, 1, 1, 11, &z8002_device::ZF_dddd_0dsp7 }, + { 0xff00, 0xff7f, 1, 1, 11, &z8002_device::ZF_dddd_0dsp7 }, + { 0xf080, 0xf0ff, 1, 1, 11, &z8002_device::ZF_dddd_1dsp7 }, + { 0xf180, 0xf1ff, 1, 1, 11, &z8002_device::ZF_dddd_1dsp7 }, + { 0xf280, 0xf2ff, 1, 1, 11, &z8002_device::ZF_dddd_1dsp7 }, + { 0xf380, 0xf3ff, 1, 1, 11, &z8002_device::ZF_dddd_1dsp7 }, + { 0xf480, 0xf4ff, 1, 1, 11, &z8002_device::ZF_dddd_1dsp7 }, + { 0xf580, 0xf5ff, 1, 1, 11, &z8002_device::ZF_dddd_1dsp7 }, + { 0xf680, 0xf6ff, 1, 1, 11, &z8002_device::ZF_dddd_1dsp7 }, + { 0xf780, 0xf7ff, 1, 1, 11, &z8002_device::ZF_dddd_1dsp7 }, + { 0xf880, 0xf8ff, 1, 1, 11, &z8002_device::ZF_dddd_1dsp7 }, + { 0xf980, 0xf9ff, 1, 1, 11, &z8002_device::ZF_dddd_1dsp7 }, + { 0xfa80, 0xfaff, 1, 1, 11, &z8002_device::ZF_dddd_1dsp7 }, + { 0xfb80, 0xfbff, 1, 1, 11, &z8002_device::ZF_dddd_1dsp7 }, + { 0xfc80, 0xfcff, 1, 1, 11, &z8002_device::ZF_dddd_1dsp7 }, + { 0xfd80, 0xfdff, 1, 1, 11, &z8002_device::ZF_dddd_1dsp7 }, + { 0xfe80, 0xfeff, 1, 1, 11, &z8002_device::ZF_dddd_1dsp7 }, + { 0xff80, 0xffff, 1, 1, 11, &z8002_device::ZF_dddd_1dsp7 }, + { 0, 0, 0, 0, 0, nullptr }, +}; diff --git a/src/devices/machine/68307.h b/src/devices/machine/68307.h index 3ed993ea3f7..a64c9985ce9 100644 --- a/src/devices/machine/68307.h +++ b/src/devices/machine/68307.h @@ -77,9 +77,6 @@ protected: virtual void device_reset() override; virtual void device_add_mconfig(machine_config &config) override; - virtual uint32_t disasm_min_opcode_bytes() const override { return 2; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 10; } - virtual uint32_t execute_min_cycles() const override { return 4; } virtual uint32_t execute_max_cycles() const override { return 158; } diff --git a/src/devices/machine/netlist.cpp b/src/devices/machine/netlist.cpp index 6674efee841..30ef04433f2 100644 --- a/src/devices/machine/netlist.cpp +++ b/src/devices/machine/netlist.cpp @@ -1045,23 +1045,6 @@ ATTR_COLD uint64_t netlist_mame_cpu_device::execute_cycles_to_clocks(uint64_t cy return cycles; } -ATTR_COLD offs_t netlist_mame_cpu_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) -{ - //char tmp[16]; - unsigned startpc = pc; - int relpc = pc - m_genPC; - if (relpc >= 0 && relpc < netlist().queue().size()) - { - int dpc = netlist().queue().size() - relpc - 1; - // FIXME: 50 below fixes crash in mame-debugger. It's based on try on error. - util::stream_format(stream, "%c %s @%10.7f", (relpc == 0) ? '*' : ' ', netlist().queue()[dpc].m_object->name().c_str(), - netlist().queue()[dpc].m_exec_time.as_double()); - } - - pc+=1; - return (pc - startpc); -} - ATTR_HOT void netlist_mame_cpu_device::execute_run() { bool check_debugger = ((device_t::machine().debug_flags & DEBUG_FLAG_ENABLED) != 0); @@ -1085,6 +1068,35 @@ ATTR_HOT void netlist_mame_cpu_device::execute_run() } } +util::disasm_interface *netlist_mame_cpu_device::create_disassembler() +{ + return new netlist_disassembler(this); +} + +netlist_disassembler::netlist_disassembler(netlist_mame_cpu_device *dev) : m_dev(dev) +{ +} + +u32 netlist_disassembler::opcode_alignment() const +{ + return 1; +} + +offs_t netlist_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + unsigned startpc = pc; + int relpc = pc - m_dev->genPC(); + if (relpc >= 0 && relpc < m_dev->netlist().queue().size()) + { + int dpc = m_dev->netlist().queue().size() - relpc - 1; + util::stream_format(stream, "%c %s @%10.7f", (relpc == 0) ? '*' : ' ', m_dev->netlist().queue()[dpc].m_object->name().c_str(), + m_dev->netlist().queue()[dpc].m_exec_time.as_double()); + } + + pc+=1; + return (pc - startpc); +} + // ---------------------------------------------------------------------------------------- // netlist_mame_sound_device // ---------------------------------------------------------------------------------------- diff --git a/src/devices/machine/netlist.h b/src/devices/machine/netlist.h index bf6fd084056..18a13d31f41 100644 --- a/src/devices/machine/netlist.h +++ b/src/devices/machine/netlist.h @@ -151,6 +151,21 @@ private: // netlist_mame_cpu_device // ---------------------------------------------------------------------------------------- +class netlist_mame_cpu_device; + +class netlist_disassembler : public util::disasm_interface +{ +public: + netlist_disassembler(netlist_mame_cpu_device *dev); + virtual ~netlist_disassembler() = default; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + netlist_mame_cpu_device *m_dev; +}; + class netlist_mame_cpu_device : public netlist_mame_device, public device_execute_interface, public device_state_interface, @@ -161,6 +176,8 @@ public: // construction/destruction netlist_mame_cpu_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); + offs_t genPC() const { return m_genPC; } + protected: // netlist_mame_device virtual void nl_register_devices() override; @@ -175,9 +192,7 @@ protected: ATTR_HOT virtual void execute_run() override; // device_disasm_interface overrides - ATTR_COLD virtual uint32_t disasm_min_opcode_bytes() const override { return 1; } - ATTR_COLD virtual uint32_t disasm_max_opcode_bytes() const override { return 1; } - ATTR_COLD virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; // device_memory_interface overrides virtual space_config_vector memory_space_config() const override; @@ -188,7 +203,7 @@ protected: address_space_config m_program_config; private: - int m_genPC; + offs_t m_genPC; }; // ---------------------------------------------------------------------------------------- diff --git a/src/emu/debug/debugbuf.cpp b/src/emu/debug/debugbuf.cpp new file mode 100644 index 00000000000..96392f60bf5 --- /dev/null +++ b/src/emu/debug/debugbuf.cpp @@ -0,0 +1,1381 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert + +// Buffering interface for the disassembly windows + +#include "emu.h" +#include "debugbuf.h" + +debug_disasm_buffer::debug_data_buffer::debug_data_buffer(util::disasm_interface *intf) : m_intf(intf) +{ + m_space = nullptr; + m_back = nullptr; + m_opcode = true; + m_lstart = m_lend = 0; + m_wrapped = false; +} + +bool debug_disasm_buffer::debug_data_buffer::active() const +{ + return m_space || m_back; +} + +void debug_disasm_buffer::debug_data_buffer::set_source(address_space &space) +{ + m_space = &space; + setup_methods(); +} + +void debug_disasm_buffer::debug_data_buffer::set_source(debug_data_buffer &back, bool opcode) +{ + m_back = &back; + m_opcode = opcode; + setup_methods(); +} + +u8 debug_disasm_buffer::debug_data_buffer::r8 (offs_t pc) const +{ + return m_do_r8(pc); +} + +u16 debug_disasm_buffer::debug_data_buffer::r16(offs_t pc) const +{ + return m_do_r16(pc); +} + +u32 debug_disasm_buffer::debug_data_buffer::r32(offs_t pc) const +{ + return m_do_r32(pc); +} + +u64 debug_disasm_buffer::debug_data_buffer::r64(offs_t pc) const +{ + return m_do_r64(pc); +} + +address_space *debug_disasm_buffer::debug_data_buffer::get_underlying_space() const +{ + return m_space; +} + +void debug_disasm_buffer::debug_data_buffer::fill(offs_t lstart, offs_t size) const +{ + offs_t lend = (lstart + size) & m_pc_mask; + if(m_page_mask) { + if((lstart ^ lend) & ~m_page_mask) { + lstart = lstart & ~m_page_mask; + lend = (((lend - 1) | m_page_mask) + 1) & m_pc_mask; + } + } + + if(!m_buffer.empty()) { + if(m_wrapped) { + if(lstart >= m_lstart && (lend > m_lstart || lend <= m_lend)) + return; + if(lstart < m_lend && lend <= m_lend) + return; + } else { + if(m_lend && lstart >= m_lstart && lend <= m_lend) + return; + if(!m_lend && lstart >= m_lstart) + return; + if(m_lstart == m_lend) + return; + } + } + + if(m_buffer.empty()) { + m_lstart = lstart; + m_lend = lend; + m_wrapped = lend < lstart; + offs_t size = m_pc_delta_to_bytes((lend - lstart) & m_pc_mask); + m_buffer.resize(size); + m_do_fill(lstart, lend); + + } else { + offs_t n_lstart, n_lend; + if(lstart > lend) { + if(m_wrapped) { + // Old is wrapped, new is wrapped, just extend + n_lstart = std::min(m_lstart, lstart); + n_lend = std::max(m_lend, lend); + } else { + // Old is unwrapped, new is wrapped. Reduce the amount of "useless" data. + offs_t gap_post = m_lend >= lstart ? 0 : lstart - m_lend; + offs_t gap_pre = m_lstart <= lend ? 0 : m_lstart - lend; + if(gap_post < gap_pre) { + // extend the old one end until it reaches the new one + n_lstart = std::min(m_lstart, lstart); + n_lend = lend; + } else { + // extend the old one start until it reaches the new one + n_lstart = lstart; + n_lend = std::max(m_lend, lend); + } + m_wrapped = true; + } + } else if(m_wrapped) { + // Old is wrapped, new is unwrapped. Reduce the amount of "useless" data. + offs_t gap_post = m_lend >= lstart ? 0 : lstart - m_lend; + offs_t gap_pre = m_lstart <= lend ? 0 : m_lstart - lend; + if(gap_post < gap_pre) { + // extend the old one end until it reaches the new one + n_lstart = m_lstart; + n_lend = lend; + } else { + // extend the old one start until it reaches the new one + n_lstart = lstart; + n_lend = m_lend; + } + } else { + // Both are unwrapped, decide whether to wrap. + // If there's overlap, don't wrap, just extend + if(lend >= m_lstart && lstart < m_lend) { + n_lstart = std::min(m_lstart, lstart); + n_lend = std::max(m_lend, lend); + } else { + // If there's no overlap, compute the gap with wrapping or without + offs_t gap_unwrapped = lstart > m_lstart ? lstart - m_lend : m_lstart - lend; + offs_t gap_wrapped = lstart > m_lstart ? (m_lstart - lend) & m_pc_mask : (lstart - m_lend) & m_pc_mask; + if(gap_unwrapped < gap_wrapped) { + n_lstart = std::min(m_lstart, lstart); + n_lend = std::max(m_lend, lend); + } else { + n_lstart = std::max(m_lstart, lstart); + n_lend = std::min(m_lend, lend); + m_wrapped = true; + } + } + } + + if(n_lstart != m_lstart) { + offs_t size = m_pc_delta_to_bytes((m_lstart - n_lstart) & m_pc_mask); + m_buffer.insert(m_buffer.begin(), size, 0); + offs_t old_lstart = m_lstart; + m_lstart = n_lstart; + m_do_fill(m_lstart, old_lstart); + } + if(n_lend != m_lend) { + offs_t size = m_pc_delta_to_bytes((n_lend - m_lstart) & m_pc_mask); + m_buffer.resize(size); + offs_t old_lend = m_lend; + m_lend = n_lend; + m_do_fill(old_lend, m_lend); + } + } +} + +std::string debug_disasm_buffer::debug_data_buffer::data_to_string(offs_t pc, offs_t size) const +{ + return m_data_to_string(pc, size); +} + +void debug_disasm_buffer::debug_data_buffer::data_get(offs_t pc, offs_t size, std::vector &data) const +{ + return m_data_get(pc, size, data); +} + +void debug_disasm_buffer::debug_data_buffer::setup_methods() +{ + address_space *space = m_space ? m_space : m_back->get_underlying_space(); + int shift = space->addrbus_shift(); + int alignment = m_intf->opcode_alignment(); + endianness_t endian = space->endianness(); + + m_pc_mask = space->logaddrmask(); + + if(m_intf->interface_flags() & util::disasm_interface::PAGED) + m_page_mask = (1 << m_intf->page_address_bits()) - 1; + else + m_page_mask = 0; + + // Define the byte counter + switch(shift) { + case -3: m_pc_delta_to_bytes = [](offs_t delta) { return delta << 3; }; break; + case -2: m_pc_delta_to_bytes = [](offs_t delta) { return delta << 2; }; break; + case -1: m_pc_delta_to_bytes = [](offs_t delta) { return delta << 1; }; break; + case 0: m_pc_delta_to_bytes = [](offs_t delta) { return delta; }; break; + case 3: m_pc_delta_to_bytes = [](offs_t delta) { return delta >> 3; }; break; + default: throw emu_fatalerror("debug_disasm_buffer::debug_data_buffer::setup_methods: Abnormal address buf shift\n"); + } + + // Define the filler + if(m_space) { + // get the data from given space + if(m_intf->interface_flags() & util::disasm_interface::NONLINEAR_PC) { + switch(shift) { + case -1: + m_do_fill = [this](offs_t lstart, offs_t lend) { + auto dis = m_space->machine().disable_side_effect(); + u16 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 1) & m_pc_mask) { + offs_t tpc = m_intf->pc_linear_to_real(lpc); + if (m_space->device().memory().translate(m_space->spacenum(), TRANSLATE_FETCH_DEBUG, tpc)) + *dest++ = m_space->read_word(tpc << 1); + else + *dest++ = 0; + } + }; + break; + case 0: + m_do_fill = [this](offs_t lstart, offs_t lend) { + auto dis = m_space->machine().disable_side_effect(); + u8 *dest = get_ptr(lstart); + u32 steps = 0; + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 1) & m_pc_mask) { + offs_t tpc = m_intf->pc_linear_to_real(lpc); + if (m_space->device().memory().translate(m_space->spacenum(), TRANSLATE_FETCH_DEBUG, tpc)) + *dest++ = m_space->read_byte(tpc); + else + *dest++ = 0; + steps++; + } + }; + break; + } + + } else { + switch(shift) { + case -3: // bus granularity 64 + m_do_fill = [this](offs_t lstart, offs_t lend) { + auto dis = m_space->machine().disable_side_effect(); + u64 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 1) & m_pc_mask) { + offs_t tpc = lpc; + if (m_space->device().memory().translate(m_space->spacenum(), TRANSLATE_FETCH_DEBUG, tpc)) + *dest++ = m_space->read_qword(tpc << 3); + else + *dest++ = 0; + } + }; + break; + + case -2: // bus granularity 32 + m_do_fill = [this](offs_t lstart, offs_t lend) { + auto dis = m_space->machine().disable_side_effect(); + u32 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 1) & m_pc_mask) { + offs_t tpc = lpc; + if (m_space->device().memory().translate(m_space->spacenum(), TRANSLATE_FETCH_DEBUG, tpc)) + *dest++ = m_space->read_dword(tpc << 2); + else + *dest++ = 0; + } + }; + break; + + case -1: // bus granularity 16 + m_do_fill = [this](offs_t lstart, offs_t lend) { + auto dis = m_space->machine().disable_side_effect(); + u16 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 1) & m_pc_mask) { + offs_t tpc = lpc; + if (m_space->device().memory().translate(m_space->spacenum(), TRANSLATE_FETCH_DEBUG, tpc)) + *dest++ = m_space->read_word(tpc << 1); + else + *dest++ = 0; + } + }; + break; + + case 0: // bus granularity 8 + m_do_fill = [this](offs_t lstart, offs_t lend) { + auto dis = m_space->machine().disable_side_effect(); + u8 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 1) & m_pc_mask) { + offs_t tpc = lpc; + if (m_space->device().memory().translate(m_space->spacenum(), TRANSLATE_FETCH_DEBUG, tpc)) + *dest++ = m_space->read_byte(tpc); + else + *dest++ = 0; + } + }; + break; + + case 3: // bus granularity 1, stored as u16 + m_do_fill = [this](offs_t lstart, offs_t lend) { + auto dis = m_space->machine().disable_side_effect(); + u16 *dest = reinterpret_cast(&m_buffer[0]) + ((lstart - m_lstart) >> 4); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 0x10) & m_pc_mask) { + offs_t tpc = lpc; + if (m_space->device().memory().translate(m_space->spacenum(), TRANSLATE_FETCH_DEBUG, tpc)) + *dest++ = m_space->read_word(tpc >> 3); + else + *dest++ = 0; + } + }; + break; + } + } + } else { + // get the data from a back buffer and decrypt it through the device + // size chosen is alignment * granularity + assert(!(m_intf->interface_flags() & util::disasm_interface::NONLINEAR_PC)); + + switch(shift) { + case -3: // bus granularity 64, endianness irrelevant + m_do_fill = [this](offs_t lstart, offs_t lend) { + u64 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 1) & m_pc_mask) + *dest++ = m_intf->decrypt64(m_back->r64(lpc), lpc, m_opcode); + }; + break; + + case -2: // bus granularity 32 + switch(alignment) { + case 1: // bus granularity 32, alignment 32, endianness irrelevant + m_do_fill = [this](offs_t lstart, offs_t lend) { + u32 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 1) & m_pc_mask) + *dest++ = m_intf->decrypt32(m_back->r32(lpc), lpc, m_opcode); + }; + break; + + case 2: // bus granularity 32, alignment 64 + switch(endian) { + case ENDIANNESS_LITTLE: // bus granularity 32, alignment 64, little endian + m_do_fill = [this](offs_t lstart, offs_t lend) { + u32 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 2) & m_pc_mask) { + u64 val = m_intf->decrypt64(m_back->r64(lpc), lpc, m_opcode); + *dest++ = val; + *dest++ = val >> 32; + } + }; + break; + + case ENDIANNESS_BIG: // bus granularity 32, bus width 64, big endian + m_do_fill = [this](offs_t lstart, offs_t lend) { + u32 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 2) & m_pc_mask) { + u64 val = m_intf->decrypt64(m_back->r64(lpc), lpc, m_opcode); + *dest++ = val >> 32; + *dest++ = val; + } + }; + break; + } + break; + } + break; + + case -1: // bus granularity 16 + switch(alignment) { + case 1: // bus granularity 16, alignment 16, endianness irrelevant + m_do_fill = [this](offs_t lstart, offs_t lend) { + u16 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 1) & m_pc_mask) + *dest++ = m_intf->decrypt16(m_back->r16(lpc), lpc, m_opcode); + }; + break; + + case 2: // bus granularity 16, alignment 32 + switch(endian) { + case ENDIANNESS_LITTLE: // bus granularity 16, alignment 32, little endian + m_do_fill = [this](offs_t lstart, offs_t lend) { + u16 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 2) & m_pc_mask) { + u32 val = m_intf->decrypt32(m_back->r32(lpc), lpc, m_opcode); + *dest++ = val; + *dest++ = val >> 16; + } + }; + break; + + case ENDIANNESS_BIG: // bus granularity 16, alignment 32, big endian + m_do_fill = [this](offs_t lstart, offs_t lend) { + u16 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 2) & m_pc_mask) { + u32 val = m_intf->decrypt32(m_back->r32(lpc), lpc, m_opcode); + *dest++ = val >> 16; + *dest++ = val; + } + }; + break; + } + break; + + case 4: // bus granularity 16, alignment 64 + switch(endian) { + case ENDIANNESS_LITTLE: // bus granularity 16, alignment 64, little endian + m_do_fill = [this](offs_t lstart, offs_t lend) { + u16 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 4) & m_pc_mask) { + u64 val = m_intf->decrypt64(m_back->r64(lpc), lpc, m_opcode); + *dest++ = val; + *dest++ = val >> 16; + *dest++ = val >> 32; + *dest++ = val >> 48; + } + }; + break; + + case ENDIANNESS_BIG: // bus granularity 16, alignment 64, big endian + m_do_fill = [this](offs_t lstart, offs_t lend) { + u16 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 4) & m_pc_mask) { + u64 val = m_intf->decrypt64(m_back->r64(lpc), lpc, m_opcode); + *dest++ = val >> 48; + *dest++ = val >> 32; + *dest++ = val >> 16; + *dest++ = val; + } + }; + break; + } + break; + } + break; + + case 0: // bus granularity 8 + switch(alignment) { + case 1: // bus granularity 8, alignment 8, endianness irrelevant + m_do_fill = [this](offs_t lstart, offs_t lend) { + u8 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 1) & m_pc_mask) + *dest++ = m_intf->decrypt8(m_back->r8(lpc), lpc, m_opcode); + }; + break; + + case 2: // bus granularity 8, alignment 16 + switch(endian) { + case ENDIANNESS_LITTLE: // bus granularity 8, alignment 16, little endian + m_do_fill = [this](offs_t lstart, offs_t lend) { + u8 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 2) & m_pc_mask) { + u16 val = m_intf->decrypt16(m_back->r16(lpc), lpc, m_opcode); + *dest++ = val; + *dest++ = val >> 8; + } + }; + break; + + case ENDIANNESS_BIG: // bus granularity 16, alignment 16, big endian + m_do_fill = [this](offs_t lstart, offs_t lend) { + u8 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 2) & m_pc_mask) { + u16 val = m_intf->decrypt16(m_back->r16(lpc), lpc, m_opcode); + *dest++ = val >> 8; + *dest++ = val; + } + }; + break; + } + break; + + case 4: // bus granularity 8, alignment 32 + switch(endian) { + case ENDIANNESS_LITTLE: // bus granularity 8, alignment 16, little endian + m_do_fill = [this](offs_t lstart, offs_t lend) { + u8 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 4) & m_pc_mask) { + u32 val = m_intf->decrypt32(m_back->r32(lpc), lpc, m_opcode); + *dest++ = val; + *dest++ = val >> 8; + *dest++ = val >> 16; + *dest++ = val >> 24; + } + }; + break; + + case ENDIANNESS_BIG: // bus granularity 16, alignment 32, big endian + m_do_fill = [this](offs_t lstart, offs_t lend) { + u8 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 4) & m_pc_mask) { + u32 val = m_intf->decrypt32(m_back->r32(lpc), lpc, m_opcode); + *dest++ = val >> 24; + *dest++ = val >> 16; + *dest++ = val >> 8; + *dest++ = val; + } + }; + break; + } + break; + + + case 8: // bus granularity 8, alignment 64 + switch(endian) { + case ENDIANNESS_LITTLE: // bus granularity 8, alignment 64, little endian + m_do_fill = [this](offs_t lstart, offs_t lend) { + u8 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 8) & m_pc_mask) { + u64 val = m_intf->decrypt64(m_back->r64(lpc), lpc, m_opcode); + *dest++ = val; + *dest++ = val >> 8; + *dest++ = val >> 16; + *dest++ = val >> 24; + *dest++ = val >> 32; + *dest++ = val >> 40; + *dest++ = val >> 48; + *dest++ = val >> 56; + } + }; + break; + + case ENDIANNESS_BIG: // bus granularity 8, alignment 64, big endian + m_do_fill = [this](offs_t lstart, offs_t lend) { + u8 *dest = get_ptr(lstart); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 2) & m_pc_mask) { + u64 val = m_intf->decrypt64(m_back->r64(lpc), lpc, m_opcode); + *dest++ = val >> 56; + *dest++ = val >> 48; + *dest++ = val >> 40; + *dest++ = val >> 32; + *dest++ = val >> 24; + *dest++ = val >> 16; + *dest++ = val >> 8; + *dest++ = val; + } + }; + break; + } + break; + } + break; + + case 3: // bus granularity 1, alignment 16, little endian (bit addressing, stored as u16, tms3401x) + assert(alignment == 16); + assert(endian == ENDIANNESS_LITTLE); + m_do_fill = [this](offs_t lstart, offs_t lend) { + u16 *dest = reinterpret_cast(&m_buffer[0]) + ((lstart - m_lstart) >> 4); + for(offs_t lpc = lstart; lpc != lend; lpc = (lpc + 0x10) & m_pc_mask) + *dest++ = m_intf->decrypt16(m_back->r16(lpc), lpc, m_opcode); + }; + break; + } + } + + // Define the accessors + if(m_intf->interface_flags() & util::disasm_interface::NONLINEAR_PC) { + switch(shift) { + case -1: + m_do_r8 = [](offs_t pc) -> u8 { throw emu_fatalerror("debug_disasm_buffer::debug_data_buffer: r8 access on 16-bits granularity bus\n"); }; + m_do_r16 = [this](offs_t pc) -> u16 { + offs_t lpc = m_intf->pc_real_to_linear(pc); + fill(lpc, 1); + const u16 *src = get_ptr(lpc); + return src[0]; + }; + + switch(endian) { + case ENDIANNESS_LITTLE: + m_do_r32 = [this](offs_t pc) -> u32 { + offs_t lpc = m_intf->pc_real_to_linear(pc); + fill(lpc, 2); + u32 r = 0; + for(int j=0; j != 2; j++) { + r |= get(lpc) << (j*16); + lpc = (lpc & ~m_page_mask) | ((lpc + 1) & m_page_mask); + } + return r; + }; + m_do_r64 = [this](offs_t pc) -> u64 { + offs_t lpc = m_intf->pc_real_to_linear(pc); + fill(lpc, 4); + u64 r = 0; + for(int j=0; j != 4; j++) { + r |= u64(get(lpc)) << (j*16); + lpc = (lpc & ~m_page_mask) | ((lpc + 1) & m_page_mask); + } + return r; + }; + break; + + case ENDIANNESS_BIG: + m_do_r32 = [this](offs_t pc) -> u32 { + offs_t lpc = m_intf->pc_real_to_linear(pc); + fill(lpc, 2); + u32 r = 0; + for(int j=0; j != 2; j++) { + r |= get(lpc) << ((1-j)*16); + lpc = (lpc & ~m_page_mask) | ((lpc + 1) & m_page_mask); + } + return r; + }; + m_do_r64 = [this](offs_t pc) -> u64 { + offs_t lpc = m_intf->pc_real_to_linear(pc); + fill(lpc, 4); + u64 r = 0; + for(int j=0; j != 4; j++) { + r |= u64(get(lpc)) << ((3-j)*16); + lpc = (lpc & ~m_page_mask) | ((lpc + 1) & m_page_mask); + } + return r; + }; + break; + } + break; + + case 0: + m_do_r8 = [this](offs_t pc) -> u8 { + offs_t lpc = m_intf->pc_real_to_linear(pc); + fill(lpc, 1); + const u8 *src = get_ptr(lpc); + return src[0]; + }; + + switch(endian) { + case ENDIANNESS_LITTLE: + m_do_r16 = [this](offs_t pc) -> u16 { + offs_t lpc = m_intf->pc_real_to_linear(pc); + fill(lpc, 2); + u16 r = 0; + for(int j=0; j != 2; j++) { + r |= get(lpc) << (j*8); + lpc = (lpc & ~m_page_mask) | ((lpc + 1) & m_page_mask); + } + return r; + }; + m_do_r32 = [this](offs_t pc) -> u32 { + offs_t lpc = m_intf->pc_real_to_linear(pc); + fill(lpc, 4); + u32 r = 0; + for(int j=0; j != 2; j++) { + r |= get(lpc) << (j*8); + lpc = (lpc & ~m_page_mask) | ((lpc + 1) & m_page_mask); + } + return r; + }; + m_do_r64 = [this](offs_t pc) -> u64 { + offs_t lpc = m_intf->pc_real_to_linear(pc); + fill(lpc, 8); + u64 r = 0; + for(int j=0; j != 8; j++) { + r |= u64(get(lpc)) << (j*8); + lpc = (lpc & ~m_page_mask) | ((lpc + 1) & m_page_mask); + } + return r; + }; + break; + + case ENDIANNESS_BIG: + m_do_r16 = [this](offs_t pc) -> u16 { + offs_t lpc = m_intf->pc_real_to_linear(pc); + fill(lpc, 2); + u16 r = 0; + for(int j=0; j != 2; j++) { + r |= get(lpc) << ((1-j)*8); + lpc = (lpc & ~m_page_mask) | ((lpc + 1) & m_page_mask); + } + return r; + }; + m_do_r32 = [this](offs_t pc) -> u32 { + offs_t lpc = m_intf->pc_real_to_linear(pc); + fill(lpc, 4); + u32 r = 0; + for(int j=0; j != 2; j++) { + r |= get(lpc) << ((3-j)*8); + lpc = (lpc & ~m_page_mask) | ((lpc + 1) & m_page_mask); + } + return r; + }; + m_do_r64 = [this](offs_t pc) -> u64 { + offs_t lpc = m_intf->pc_real_to_linear(pc); + fill(lpc, 8); + u64 r = 0; + for(int j=0; j != 8; j++) { + r |= u64(get(lpc)) << ((7-j)*8); + lpc = (lpc & ~m_page_mask) | ((lpc + 1) & m_page_mask); + } + return r; + }; + break; + } + break; + } + } else { + switch(shift) { + case -3: // bus granularity 64 + m_do_r8 = [](offs_t pc) -> u8 { throw emu_fatalerror("debug_disasm_buffer::debug_data_buffer: r8 access on 64-bits granularity bus\n"); }; + m_do_r16 = [](offs_t pc) -> u16 { throw emu_fatalerror("debug_disasm_buffer::debug_data_buffer: r16 access on 64-bits granularity bus\n"); }; + m_do_r32 = [](offs_t pc) -> u32 { throw emu_fatalerror("debug_disasm_buffer::debug_data_buffer: r32 access on 64-bits granularity bus\n"); }; + m_do_r64 = [this](offs_t pc) -> u64 { + fill(pc, 1); + const u64 *src = get_ptr(pc); + return src[0]; + }; + break; + + case -2: // bus granularity 32 + m_do_r8 = [](offs_t pc) -> u8 { throw emu_fatalerror("debug_disasm_buffer::debug_data_buffer: r8 access on 32-bits granularity bus\n"); }; + m_do_r16 = [](offs_t pc) -> u16 { throw emu_fatalerror("debug_disasm_buffer::debug_data_buffer: r16 access on 32-bits granularity bus\n"); }; + m_do_r32 = [this](offs_t pc) -> u32 { + fill(pc, 1); + const u32 *src = get_ptr(pc); + return src[0]; + }; + switch(endian) { + case ENDIANNESS_LITTLE: + if(m_page_mask) { + m_do_r64 = [this](offs_t pc) -> u64 { + fill(pc, 2); + u64 r = 0; + for(int j=0; j != 2; j++) { + r |= u64(get(pc)) << (j*32); + pc = (pc & ~m_page_mask) | ((pc + 1) & m_page_mask); + } + return r; + }; + } else { + m_do_r64 = [this](offs_t pc) -> u64 { + fill(pc, 2); + const u32 *src = get_ptr(pc); + return src[0] | (u64(src[1]) << 32); + }; + } + break; + case ENDIANNESS_BIG: + if(m_page_mask) { + m_do_r64 = [this](offs_t pc) -> u64 { + fill(pc, 2); + u64 r = 0; + for(int j=0; j != 2; j++) { + r |= u64(get(pc)) << ((1-j)*32); + pc = (pc & ~m_page_mask) | ((pc + 1) & m_page_mask); + } + return r; + }; + } else { + m_do_r64 = [this](offs_t pc) -> u64 { + fill(pc, 2); + const u32 *src = get_ptr(pc); + return (u64(src[0]) << 32) | u64(src[1]); + }; + } + break; + } + break; + + case -1: // bus granularity 16 + m_do_r8 = [](offs_t pc) -> u8 { throw emu_fatalerror("debug_disasm_buffer::debug_data_buffer: r8 access on 16-bits granularity bus\n"); }; + m_do_r16 = [this](offs_t pc) -> u16 { + fill(pc, 1); + const u16 *src = get_ptr(pc); + return src[0]; + }; + switch(endian) { + case ENDIANNESS_LITTLE: + if(m_page_mask) { + m_do_r32 = [this](offs_t pc) -> u32 { + fill(pc, 2); + u32 r = 0; + for(int j=0; j != 2; j++) { + r |= get(pc) << (j*16); + pc = (pc & ~m_page_mask) | ((pc + 1) & m_page_mask); + } + return r; + }; + m_do_r64 = [this](offs_t pc) -> u64 { + fill(pc, 4); + u64 r = 0; + for(int j=0; j != 4; j++) { + r |= u64(get(pc)) << (j*16); + pc = (pc & ~m_page_mask) | ((pc + 1) & m_page_mask); + } + return r; + }; + } else { + m_do_r32 = [this](offs_t pc) -> u32 { + fill(pc, 2); + const u16 *src = get_ptr(pc); + return src[0] | (src[1] << 16); + }; + m_do_r64 = [this](offs_t pc) -> u64 { + fill(pc, 4); + const u16 *src = get_ptr(pc); + return src[0] | (src[1] << 16) | (u64(src[2]) << 32) | (u64(src[3]) << 48); + }; + } + break; + case ENDIANNESS_BIG: + if(m_page_mask) { + m_do_r32 = [this](offs_t pc) -> u32 { + fill(pc, 2); + u32 r = 0; + for(int j=0; j != 2; j++) { + r |= get(pc) << ((1-j)*16); + pc = (pc & ~m_page_mask) | ((pc + 1) & m_page_mask); + } + return r; + }; + m_do_r64 = [this](offs_t pc) -> u64 { + fill(pc, 4); + u64 r = 0; + for(int j=0; j != 4; j++) { + r |= u64(get(pc)) << ((3-j)*16); + pc = (pc & ~m_page_mask) | ((pc + 1) & m_page_mask); + } + return r; + }; + } else { + m_do_r32 = [this](offs_t pc) -> u32 { + fill(pc, 2); + const u16 *src = get_ptr(pc); + return (src[0] << 16) | src[1]; + }; + m_do_r64 = [this](offs_t pc) -> u64 { + fill(pc, 4); + const u16 *src = get_ptr(pc); + return (u64(src[0]) << 48) | (u64(src[1]) << 32) | (src[2] << 16) | src[3]; + }; + } + break; + } + break; + + case 0: // bus granularity 8 + m_do_r8 = [this](offs_t pc) -> u8 { + fill(pc, 1); + const u8 *src = get_ptr(pc); + return src[0]; + }; + switch(endian) { + case ENDIANNESS_LITTLE: + if(m_page_mask) { + m_do_r16 = [this](offs_t pc) -> u16 { + fill(pc, 2); + u16 r = 0; + for(int j=0; j != 2; j++) { + r |= get(pc) << (j*8); + pc = (pc & ~m_page_mask) | ((pc + 1) & m_page_mask); + } + return r; + }; + m_do_r32 = [this](offs_t pc) -> u32 { + fill(pc, 4); + u32 r = 0; + for(int j=0; j != 4; j++) { + r |= get(pc) << (j*8); + pc = (pc & ~m_page_mask) | ((pc + 1) & m_page_mask); + } + return r; + }; + m_do_r64 = [this](offs_t pc) -> u64 { + fill(pc, 8); + u64 r = 0; + for(int j=0; j != 8; j++) { + r |= u64(get(pc)) << (j*8); + pc = (pc & ~m_page_mask) | ((pc + 1) & m_page_mask); + } + return r; + }; + } else { + m_do_r16 = [this](offs_t pc) -> u16 { + fill(pc, 2); + const u8 *src = get_ptr(pc); + return src[0] | (src[1] << 8); + }; + m_do_r32 = [this](offs_t pc) -> u32 { + fill(pc, 4); + const u8 *src = get_ptr(pc); + return src[0] | (src[1] << 8) | (src[2] << 16) | (src[3] << 24); + }; + m_do_r64 = [this](offs_t pc) -> u64 { + fill(pc, 8); + const u8 *src = get_ptr(pc); + return src[0] | (src[1] << 8) | (src[2] << 16) | (src[3] << 24) | + (u64(src[4]) << 32) | (u64(src[5]) << 40) | (u64(src[6]) << 48) | (u64(src[7]) << 56); + }; + } + break; + case ENDIANNESS_BIG: + if(m_page_mask) { + m_do_r16 = [this](offs_t pc) -> u16 { + fill(pc, 2); + u16 r = 0; + for(int j=0; j != 2; j++) { + r |= get(pc) << ((1-j)*8); + pc = (pc & ~m_page_mask) | ((pc + 1) & m_page_mask); + } + return r; + }; + m_do_r32 = [this](offs_t pc) -> u32 { + fill(pc, 4); + u32 r = 0; + for(int j=0; j != 4; j++) { + r |= get(pc) << ((3-j)*8); + pc = (pc & ~m_page_mask) | ((pc + 1) & m_page_mask); + } + return r; + }; + m_do_r64 = [this](offs_t pc) -> u64 { + fill(pc, 8); + u64 r = 0; + for(int j=0; j != 8; j++) { + r |= u64(get(pc)) << ((7-j)*8); + pc = (pc & ~m_page_mask) | ((pc + 1) & m_page_mask); + } + return r; + }; + } else { + m_do_r16 = [this](offs_t pc) -> u16 { + fill(pc, 2); + const u8 *src = get_ptr(pc); + return (src[0] << 8) | src[1]; + }; + m_do_r32 = [this](offs_t pc) -> u32 { + fill(pc, 4); + const u8 *src = get_ptr(pc); + return (src[0] << 24) | (src[1] << 16) | (src[2] << 8) | src[3]; + }; + m_do_r64 = [this](offs_t pc) -> u64 { + fill(pc, 8); + const u8 *src = get_ptr(pc); + return (u64(src[0]) << 56) | (u64(src[1]) << 32) | (u64(src[2]) << 40) | (u64(src[3]) << 32) | + (src[4] << 24) | (src[5] << 16) | (src[6] << 8) | src[7]; + }; + } + break; + } + break; + + case 3: // bus granularity 1, u16 storage, no paging + assert(endian == ENDIANNESS_LITTLE); + assert(!m_page_mask); + m_do_r8 = [](offs_t pc) -> u8 { throw emu_fatalerror("debug_disasm_buffer::debug_data_buffer: r8 access on 1-bit/16 wide granularity bus\n"); }; + m_do_r16 = [this](offs_t pc) -> u16 { + fill(pc, 16); + const u16 *src = reinterpret_cast(&m_buffer[0]) + ((pc - m_lstart) >> 4); + return src[0]; + }; + m_do_r32 = [this](offs_t pc) -> u32 { + fill(pc, 32); + const u16 *src = reinterpret_cast(&m_buffer[0]) + ((pc - m_lstart) >> 4); + return src[0] | (src[1] << 16); + }; + m_do_r64 = [this](offs_t pc) -> u64 { + fill(pc, 64); + const u16 *src = reinterpret_cast(&m_buffer[0]) + ((pc - m_lstart) >> 4); + return src[0] | (src[1] << 16) | (u64(src[2]) << 32) | (u64(src[3]) << 48); + }; + break; + } + } + + // Define the data -> string conversion + switch(shift) { + case -3: + m_data_to_string = [this](offs_t pc, offs_t size) { + std::ostringstream out; + for(offs_t i=0; i != size; i++) { + if(i) + out << ' '; + util::stream_format(out, "%016x", r64(pc)); + pc = m_next_pc_wrap(pc, 1); + } + return out.str(); + }; + break; + + case -2: + switch(alignment) { + case 1: + m_data_to_string = [this](offs_t pc, offs_t size) { + std::ostringstream out; + for(offs_t i=0; i != size; i++) { + if(i) + out << ' '; + util::stream_format(out, "%08x", r32(pc)); + pc = m_next_pc_wrap(pc, 1); + } + return out.str(); + }; + break; + + case 2: + m_data_to_string = [this](offs_t pc, offs_t size) { + std::ostringstream out; + for(offs_t i=0; i != size; i += 2) { + if(i) + out << ' '; + util::stream_format(out, "%016x", r64(pc)); + pc = m_next_pc_wrap(pc, 2); + } + return out.str(); + }; + break; + } + break; + + case -1: + switch(alignment) { + case 1: + m_data_to_string = [this](offs_t pc, offs_t size) { + std::ostringstream out; + for(offs_t i=0; i != size; i++) { + if(i) + out << ' '; + util::stream_format(out, "%04x", r16(pc)); + pc = m_next_pc_wrap(pc, 1); + } + return out.str(); + }; + break; + + case 2: + m_data_to_string = [this](offs_t pc, offs_t size) { + std::ostringstream out; + for(offs_t i=0; i != size; i += 2) { + if(i) + out << ' '; + util::stream_format(out, "%08x", r32(pc)); + pc = m_next_pc_wrap(pc, 2); + } + return out.str(); + }; + break; + + case 4: + m_data_to_string = [this](offs_t pc, offs_t size) { + std::ostringstream out; + for(offs_t i=0; i != size; i += 4) { + if(i) + out << ' '; + util::stream_format(out, "%016x", r64(pc)); + pc = m_next_pc_wrap(pc, 4); + } + return out.str(); + }; + break; + } + break; + + case 0: + switch(alignment) { + case 1: + m_data_to_string = [this](offs_t pc, offs_t size) { + std::ostringstream out; + for(offs_t i=0; i != size; i++) { + if(i) + out << ' '; + util::stream_format(out, "%02x", r8(pc)); + pc = m_next_pc_wrap(pc, 1); + } + return out.str(); + }; + break; + + case 2: + m_data_to_string = [this](offs_t pc, offs_t size) { + std::ostringstream out; + for(offs_t i=0; i != size; i += 2) { + if(i) + out << ' '; + util::stream_format(out, "%04x", r16(pc)); + pc = m_next_pc_wrap(pc, 2); + } + return out.str(); + }; + break; + + case 4: + m_data_to_string = [this](offs_t pc, offs_t size) { + std::ostringstream out; + for(offs_t i=0; i != size; i += 4) { + if(i) + out << ' '; + util::stream_format(out, "%08x", r32(pc)); + pc = m_next_pc_wrap(pc, 4); + } + return out.str(); + }; + break; + + case 8: + m_data_to_string = [this](offs_t pc, offs_t size) { + std::ostringstream out; + for(offs_t i=0; i != size; i += 8) { + if(i) + out << ' '; + util::stream_format(out, "%016x", r64(pc)); + pc = m_next_pc_wrap(pc, 8); + } + return out.str(); + }; + break; + } + break; + + case 3: + m_data_to_string = [this](offs_t pc, offs_t size) { + std::ostringstream out; + for(offs_t i=0; i != size; i += 16) { + if(i) + out << ' '; + util::stream_format(out, "%04x", r16(pc)); + pc = m_next_pc_wrap(pc, 16); + } + return out.str(); + }; + break; + } + + // Define the data extraction + switch(shift) { + case -3: + m_data_get = [this](offs_t pc, offs_t size, std::vector &data) { + for(offs_t i=0; i != size; i++) { + u64 r = r64(pc); + for(int j=0; j != 8; j++) + data.push_back(r >> (8*j)); + pc = m_next_pc_wrap(pc, 1); + } + }; + break; + + case -2: + m_data_get = [this](offs_t pc, offs_t size, std::vector &data) { + for(offs_t i=0; i != size; i++) { + u32 r = r32(pc); + for(int j=0; j != 4; j++) + data.push_back(r >> (8*j)); + pc = m_next_pc_wrap(pc, 1); + } + }; + break; + + case -1: + m_data_get = [this](offs_t pc, offs_t size, std::vector &data) { + for(offs_t i=0; i != size; i++) { + u16 r = r16(pc); + for(int j=0; j != 2; j++) + data.push_back(r >> (8*j)); + pc = m_next_pc_wrap(pc, 1); + } + }; + break; + + case 0: + m_data_get = [this](offs_t pc, offs_t size, std::vector &data) { + for(offs_t i=0; i != size; i++) { + data.push_back(r8(pc)); + pc = m_next_pc_wrap(pc, 1); + } + }; + break; + + case 3: + m_data_get = [this](offs_t pc, offs_t size, std::vector &data) { + for(offs_t i=0; i != size >> 4; i++) { + u16 r = r16(pc); + for(int j=0; j != 2; j++) + data.push_back(r >> (8*j)); + pc = m_next_pc_wrap(pc, 16); + } + }; + break; + } + + // Wrapped next pc computation + if(m_intf->interface_flags() & util::disasm_interface::NONLINEAR_PC) { + // lfsr pc is always paged + m_next_pc_wrap = [this](offs_t pc, offs_t size) { + offs_t lpc = m_intf->pc_real_to_linear(pc); + offs_t lpce = (lpc & ~m_page_mask) | ((lpc + size) & m_page_mask); + return m_intf->pc_linear_to_real(lpce); + }; + } else if(m_intf->interface_flags() & util::disasm_interface::PAGED) { + m_next_pc_wrap = [this](offs_t pc, offs_t size) { + offs_t pce = (pc & ~m_page_mask) | ((pc + size) & m_page_mask); + return pce; + }; + } else { + m_next_pc_wrap = [this](offs_t pc, offs_t size) { + return (pc + size) & m_pc_mask; + }; + } +} + +debug_disasm_buffer::debug_disasm_buffer(device_t &device) : + m_buf_raw(dynamic_cast(device).get_disassembler()), + m_buf_opcodes(dynamic_cast(device).get_disassembler()), + m_buf_params(dynamic_cast(device).get_disassembler()) +{ + m_dintf = dynamic_cast(&device)->get_disassembler(); + m_mintf = dynamic_cast(&device); + + m_flags = m_dintf->interface_flags(); + + if(m_flags & util::disasm_interface::INTERNAL_DECRYPTION) { + m_buf_raw.set_source(m_mintf->space(AS_PROGRAM)); + m_buf_opcodes.set_source(m_buf_raw, true); + if((m_flags & util::disasm_interface::SPLIT_DECRYPTION) == util::disasm_interface::SPLIT_DECRYPTION) + m_buf_params.set_source(m_buf_raw, false); + } else { + if(m_mintf->has_space(AS_OPCODES)) { + m_buf_opcodes.set_source(m_mintf->space(AS_OPCODES)); + m_buf_params.set_source(m_mintf->space(AS_PROGRAM)); + } else + m_buf_opcodes.set_source(m_mintf->space(AS_PROGRAM)); + } + + m_pc_mask = m_mintf->space(AS_PROGRAM).logaddrmask(); + + if(m_flags & util::disasm_interface::PAGED) + m_page_mask = (1 << m_dintf->page_address_bits()) - 1; + else + m_page_mask = 0; + + // Next pc computation + if(m_flags & util::disasm_interface::NONLINEAR_PC) { + // lfsr pc is always paged + m_next_pc = [this](offs_t pc, offs_t size) { + offs_t lpc = m_dintf->pc_real_to_linear(pc); + offs_t lpce = lpc + size; + if((lpc ^ lpce) & ~m_page_mask) + lpce = (lpc | m_page_mask) + 1; + lpce &= m_pc_mask; + return m_dintf->pc_linear_to_real(lpce); + }; + m_next_pc_wrap = [this](offs_t pc, offs_t size) { + offs_t lpc = m_dintf->pc_real_to_linear(pc); + offs_t lpce = (lpc & ~m_page_mask) | ((lpc + size) & m_page_mask); + return m_dintf->pc_linear_to_real(lpce); + }; + + } else if(m_flags & util::disasm_interface::PAGED) { + m_next_pc = [this](offs_t pc, offs_t size) { + offs_t pce = pc + size; + if((pc ^ pce) & ~m_page_mask) + pce = (pc | m_page_mask) + 1; + pce &= m_pc_mask; + return pce; + }; + m_next_pc_wrap = [this](offs_t pc, offs_t size) { + offs_t pce = (pc & ~m_page_mask) | ((pc + size) & m_page_mask); + return pce; + }; + + } else { + m_next_pc = [this](offs_t pc, offs_t size) { + return (pc + size) & m_pc_mask; + }; + m_next_pc_wrap = [this](offs_t pc, offs_t size) { + return (pc + size) & m_pc_mask; + }; + } + + // pc to string conversion + int aw = m_mintf->space(AS_PROGRAM).addr_width(); + bool is_octal = m_mintf->space(AS_PROGRAM).is_octal(); + if((m_flags & util::disasm_interface::PAGED2LEVEL) == util::disasm_interface::PAGED2LEVEL) { + int bits1 = m_dintf->page_address_bits(); + int bits2 = m_dintf->page2_address_bits(); + int bits3 = aw - bits1 - bits2; + offs_t sm1 = (1 << bits1) - 1; + int sh2 = bits1; + offs_t sm2 = (1 << bits2) - 1; + int sh3 = bits1+bits2; + + if(is_octal) { + int nc1 = (bits1+2)/3; + int nc2 = (bits2+2)/3; + int nc3 = (bits3+2)/3; + m_pc_to_string = [nc1, nc2, nc3, sm1, sm2, sh2, sh3](offs_t pc) -> std::string { + return util::string_format("%0*o:%0*o:%0*o", + nc3, pc >> sh3, + nc2, (pc >> sh2) & sm2, + nc1, pc & sm1); + }; + } else { + int nc1 = (bits1+3)/4; + int nc2 = (bits2+3)/4; + int nc3 = (bits3+3)/4; + m_pc_to_string = [nc1, nc2, nc3, sm1, sm2, sh2, sh3](offs_t pc) -> std::string { + return util::string_format("%0*x:%0*x:%0*x", + nc3, pc >> sh3, + nc2, (pc >> sh2) & sm2, + nc1, pc & sm1); + }; + } + + } else if(m_flags & util::disasm_interface::PAGED) { + int bits1 = m_dintf->page_address_bits(); + int bits2 = aw - bits1; + offs_t sm1 = (1 << bits1) - 1; + int sh2 = bits1; + + if(is_octal) { + int nc1 = (bits1+2)/3; + int nc2 = (bits2+2)/3; + m_pc_to_string = [nc1, nc2, sm1, sh2](offs_t pc) -> std::string { + return util::string_format("%0*o:%0*o", + nc2, pc >> sh2, + nc1, pc & sm1); + }; + } else { + int nc1 = (bits1+3)/4; + int nc2 = (bits2+3)/4; + m_pc_to_string = [nc1, nc2, sm1, sh2](offs_t pc) -> std::string { + return util::string_format("%0*x:%0*x", + nc2, pc >> sh2, + nc1, pc & sm1); + }; + } + + } else { + int bits1 = aw; + + if(is_octal) { + int nc1 = (bits1+2)/3; + m_pc_to_string = [nc1](offs_t pc) -> std::string { + return util::string_format("%0*o", + nc1, pc); + }; + } else { + int nc1 = (bits1+3)/4; + m_pc_to_string = [nc1](offs_t pc) -> std::string { + return util::string_format("%0*x", + nc1, pc); + }; + } + } +} + +void debug_disasm_buffer::disassemble(offs_t pc, std::string &instruction, offs_t &next_pc, offs_t &size, u32 &info) const +{ + std::ostringstream out; + u32 result = m_dintf->disassemble(out, pc, m_buf_opcodes, m_buf_params.active() ? m_buf_params : m_buf_opcodes); + instruction = out.str(); + size = result & util::disasm_interface::LENGTHMASK; + next_pc = m_next_pc(pc, size); + info = result; +} + + +u32 debug_disasm_buffer::disassemble_info(offs_t pc) const +{ + std::ostringstream out; + return m_dintf->disassemble(out, pc, m_buf_opcodes, m_buf_params.active() ? m_buf_params : m_buf_opcodes); +} + +std::string debug_disasm_buffer::pc_to_string(offs_t pc) const +{ + return m_pc_to_string(pc); +} + +std::string debug_disasm_buffer::data_to_string(offs_t pc, offs_t size, bool opcode) const +{ + if(!opcode && !m_buf_params.active()) + return std::string(); + return (opcode ? m_buf_opcodes : m_buf_params).data_to_string(pc, size); +} + +void debug_disasm_buffer::data_get(offs_t pc, offs_t size, bool opcode, std::vector &data) const +{ + data.clear(); + if(!opcode && !m_buf_params.active()) + return; + (opcode ? m_buf_opcodes : m_buf_params).data_get(pc, size, data); +} + +offs_t debug_disasm_buffer::next_pc(offs_t pc, offs_t step) const +{ + return m_next_pc(pc, step); +} + +offs_t debug_disasm_buffer::next_pc_wrap(offs_t pc, offs_t step) const +{ + return m_next_pc_wrap(pc, step); +} diff --git a/src/emu/debug/debugbuf.h b/src/emu/debug/debugbuf.h new file mode 100644 index 00000000000..ec6a95619e1 --- /dev/null +++ b/src/emu/debug/debugbuf.h @@ -0,0 +1,97 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert + +// Buffering interface for the disassembly windows + +#ifndef MAME_EMU_DEBUG_DEBUGBUF_H +#define MAME_EMU_DEBUG_DEBUGBUF_H + +#pragma once + +class debug_disasm_buffer +{ +public: + debug_disasm_buffer(device_t &device); + + void disassemble(offs_t pc, std::string &instruction, offs_t &next_pc, offs_t &size, u32 &info) const; + u32 disassemble_info(offs_t pc) const; + std::string pc_to_string(offs_t pc) const; + std::string data_to_string(offs_t pc, offs_t size, bool opcode) const; + void data_get(offs_t pc, offs_t size, bool opcode, std::vector &data) const; + + offs_t next_pc(offs_t pc, offs_t step) const; + offs_t next_pc_wrap(offs_t pc, offs_t step) const; + +private: + class debug_data_buffer : public util::disasm_interface::data_buffer + { + public: + debug_data_buffer(util::disasm_interface *intf); + ~debug_data_buffer() = default; + + virtual u8 r8 (offs_t pc) const override; + virtual u16 r16(offs_t pc) const override; + virtual u32 r32(offs_t pc) const override; + virtual u64 r64(offs_t pc) const override; + + void set_source(address_space &space); + void set_source(debug_data_buffer &back, bool opcode); + + bool active() const; + + address_space *get_underlying_space() const; + std::string data_to_string(offs_t pc, offs_t size) const; + void data_get(offs_t pc, offs_t size, std::vector &data) const; + + private: + util::disasm_interface *m_intf; + + std::function m_pc_delta_to_bytes; + std::function m_do_fill; + std::function m_do_r8; + std::function m_do_r16; + std::function m_do_r32; + std::function m_do_r64; + std::function m_data_to_string; + std::function &)> m_data_get; + std::function m_next_pc_wrap; + + address_space *m_space; + debug_data_buffer *m_back; + bool m_opcode; + offs_t m_page_mask, m_pc_mask; + mutable offs_t m_lstart, m_lend; + mutable bool m_wrapped; + mutable std::vector m_buffer; + + template T *get_ptr(offs_t lpc) { + return reinterpret_cast(&m_buffer[0]) + ((lpc - m_lstart) & m_pc_mask); + } + + template const T *get_ptr(offs_t lpc) const { + return reinterpret_cast(&m_buffer[0]) + ((lpc - m_lstart) & m_pc_mask); + } + + template T get(offs_t lpc) const { + return reinterpret_cast(&m_buffer[0])[(lpc - m_lstart) & m_pc_mask]; + } + + void setup_methods(); + void fill(offs_t lstart, offs_t size) const; + + }; + + util::disasm_interface *m_dintf; + device_memory_interface *m_mintf; + + std::function m_next_pc; + std::function m_next_pc_wrap; + std::function m_pc_to_string; + + debug_data_buffer m_buf_raw, m_buf_opcodes, m_buf_params; + u32 m_flags; + offs_t m_page_mask, m_pc_mask; +}; + +#endif + diff --git a/src/emu/debug/debugcmd.cpp b/src/emu/debug/debugcmd.cpp index c1e96054164..c5afe1b366c 100644 --- a/src/emu/debug/debugcmd.cpp +++ b/src/emu/debug/debugcmd.cpp @@ -14,6 +14,7 @@ #include "debugcmd.h" #include "debugcon.h" #include "debugcpu.h" +#include "debugbuf.h" #include "express.h" #include "debughlp.h" #include "debugvw.h" @@ -2403,10 +2404,7 @@ void debugger_commands::execute_find(int ref, const std::vector &pa void debugger_commands::execute_dasm(int ref, const std::vector ¶ms) { u64 offset, length, bytes = 1; - int minbytes, maxbytes, byteswidth; - address_space *space, *decrypted_space; - FILE *f; - int j; + address_space *space; /* validate parameters */ if (!validate_number_parameter(params[1], offset)) @@ -2417,10 +2415,6 @@ void debugger_commands::execute_dasm(int ref, const std::vector &pa return; if (!validate_cpu_space_parameter(params.size() > 4 ? params[4].c_str() : nullptr, AS_PROGRAM, space)) return; - if (space->device().memory().has_space(AS_OPCODES)) - decrypted_space = &space->device().memory().space(AS_OPCODES); - else - decrypted_space = space; /* determine the width of the bytes */ device_disasm_interface *dasmintf; @@ -2429,104 +2423,72 @@ void debugger_commands::execute_dasm(int ref, const std::vector &pa m_console.printf("No disassembler available for %s\n", space->device().name()); return; } - minbytes = dasmintf->min_opcode_bytes(); - maxbytes = dasmintf->max_opcode_bytes(); - byteswidth = 0; - if (bytes) - { - byteswidth = (maxbytes + (minbytes - 1)) / minbytes; - byteswidth *= (2 * minbytes) + 1; - } - /* open the file */ - f = fopen(params[0].c_str(), "w"); - if (!f) - { - m_console.printf("Error opening file '%s'\n", params[0].c_str()); - return; - } + /* build the data, check the maximum size of the opcodes and disasm */ + std::vector pcs; + std::vector instructions; + std::vector tpc; + std::vector topcodes; + int max_opcodes_size = 0; + int max_disasm_size = 0; + + debug_disasm_buffer buffer(space->device()); - /* now write the data out */ - util::ovectorstream output; - util::ovectorstream disasm; - output.reserve(512); for (u64 i = 0; i < length; ) { - int pcbyte = space->address_to_byte(offset + i) & space->bytemask(); - const char *comment; - offs_t tempaddr; - int numbytes = 0; - output.clear(); - output.rdbuf()->clear(); - disasm.clear(); - disasm.seekp(0); + std::string instruction; + offs_t next_offset; + offs_t size; + u32 info; + buffer.disassemble(offset, instruction, next_offset, size, info); + pcs.push_back(offset); + instructions.emplace_back(instruction); + tpc.emplace_back(buffer.pc_to_string(offset)); + topcodes.emplace_back(buffer.data_to_string(offset, size, true)); - /* print the address */ - stream_format(output, "%0*X: ", space->logaddrchars(), u32(space->byte_to_address(pcbyte))); + int osize = topcodes.back().size(); + if(osize > max_opcodes_size) + max_opcodes_size = osize; - /* make sure we can translate the address */ - tempaddr = pcbyte; - if (space->device().memory().translate(space->spacenum(), TRANSLATE_FETCH_DEBUG, tempaddr)) - { - { - u8 opbuf[64], argbuf[64]; + int dsize = instructions.back().size(); + if(dsize > max_disasm_size) + max_disasm_size = dsize; - /* fetch the bytes up to the maximum */ - for (numbytes = 0; numbytes < maxbytes; numbytes++) - { - opbuf[numbytes] = m_cpu.read_opcode(*decrypted_space, pcbyte + numbytes, 1); - argbuf[numbytes] = m_cpu.read_opcode(*space, pcbyte + numbytes, 1); - } + i += size; + offset = next_offset; + } - /* disassemble the result */ - i += numbytes = dasmintf->disassemble(disasm, offset + i, opbuf, argbuf) & DASMFLAG_LENGTHMASK; - } + /* write the data */ + std::ofstream f(params[0]); + if (!f.good()) + { + m_console.printf("Error opening file '%s'\n", params[0]); + return; + } - /* print the bytes */ - if (bytes) - { - auto const startdex = output.tellp(); - numbytes = space->address_to_byte(numbytes); - for (j = 0; j < numbytes; j += minbytes) - stream_format(output, "%0*X ", minbytes * 2, m_cpu.read_opcode(*decrypted_space, pcbyte + j, minbytes)); - if ((output.tellp() - startdex) < byteswidth) - stream_format(output, "%*s", byteswidth - (output.tellp() - startdex), ""); - stream_format(output, " "); - } - } - else + if (bytes) + { + for(unsigned int i=0; i != pcs.size(); i++) { - disasm << ""; - i += minbytes; + const char *comment = space->device().debug()->comment_text(pcs[i]); + if (comment) + util::stream_format(f, "%s: %-*s %-*s // %s\n", tpc[i], max_opcodes_size, topcodes[i], max_disasm_size, instructions[i], comment); + else + util::stream_format(f, "%s: %-*s %s\n", tpc[i], max_opcodes_size, topcodes[i], instructions[i]); } - - /* add the disassembly */ - disasm.put('\0'); - stream_format(output, "%s", &disasm.vec()[0]); - - /* attempt to add the comment */ - comment = space->device().debug()->comment_text(tempaddr); - if (comment != nullptr) + } + else + { + for(unsigned int i=0; i != pcs.size(); i++) { - /* somewhat arbitrary guess as to how long most disassembly lines will be [column 60] */ - if (output.tellp() < 60) - { - /* pad the comment space out to 60 characters and null-terminate */ - while (output.tellp() < 60) output.put(' '); - - stream_format(output, "// %s", comment); - } + const char *comment = space->device().debug()->comment_text(pcs[i]); + if (comment) + util::stream_format(f, "%s: %-*s // %s\n", tpc[i], max_disasm_size, instructions[i], comment); else - stream_format(output, "\t// %s", comment); + util::stream_format(f, "%s: %s\n", tpc[i], instructions[i]); } - - /* output the result */ - auto const &text(output.vec()); - fprintf(f, "%.*s\n", int(unsigned(text.size())), &text[0]); } - /* close the file */ - fclose(f); m_console.printf("Data dumped successfully\n"); } @@ -2640,13 +2602,9 @@ void debugger_commands::execute_traceflush(int ref, const std::vector ¶ms) { /* validate parameters */ - address_space *space, *decrypted_space; + address_space *space; if (!validate_cpu_space_parameter(!params.empty() ? params[0].c_str() : nullptr, AS_PROGRAM, space)) return; - if (space->device().memory().has_space(AS_OPCODES)) - decrypted_space = &space->device().memory().space(AS_OPCODES); - else - decrypted_space = space; u64 count = device_debug::HISTORY_SIZE; if (params.size() > 1 && !validate_number_parameter(params[1], count)) @@ -2665,25 +2623,19 @@ void debugger_commands::execute_history(int ref, const std::vector m_console.printf("No disassembler available for %s\n", space->device().name()); return; } - int maxbytes = dasmintf->max_opcode_bytes(); + + debug_disasm_buffer buffer(space->device()); + for (int index = 0; index < (int) count; index++) { offs_t pc = debug->history_pc(-index); + std::string instruction; + offs_t next_offset; + offs_t size; + u32 info; + buffer.disassemble(pc, instruction, next_offset, size, info); - /* fetch the bytes up to the maximum */ - offs_t pcbyte = space->address_to_byte(pc) & space->bytemask(); - u8 opbuf[64], argbuf[64]; - for (int numbytes = 0; numbytes < maxbytes; numbytes++) - { - opbuf[numbytes] = m_cpu.read_opcode(*decrypted_space, pcbyte + numbytes, 1); - argbuf[numbytes] = m_cpu.read_opcode(*space, pcbyte + numbytes, 1); - } - - util::ovectorstream buffer; - dasmintf->disassemble(buffer, pc, opbuf, argbuf); - buffer.put('\0'); - - m_console.printf("%0*X: %s\n", space->logaddrchars(), pc, &buffer.vec()[0]); + m_console.printf("%s: %s\n", buffer.pc_to_string(pc), instruction); } } diff --git a/src/emu/debug/debugcpu.cpp b/src/emu/debug/debugcpu.cpp index 0289ef7f664..216a5ca0603 100644 --- a/src/emu/debug/debugcpu.cpp +++ b/src/emu/debug/debugcpu.cpp @@ -10,6 +10,7 @@ #include "emu.h" #include "debugcpu.h" +#include "debugbuf.h" #include "express.h" #include "debugcon.h" @@ -2487,33 +2488,15 @@ bool device_debug::comment_import(util::xml::data_node const &cpunode, bool is_i u32 device_debug::compute_opcode_crc32(offs_t pc) const { - // Basically the same thing as dasm_wrapped, but with some tiny savings - assert(m_memory != nullptr); + std::vector opbuf; + debug_disasm_buffer buffer(device()); - // determine the adjusted PC - address_space &decrypted_space = m_memory->has_space(AS_OPCODES) ? m_memory->space(AS_OPCODES) : m_memory->space(AS_PROGRAM); - address_space &space = m_memory->space(AS_PROGRAM); - offs_t pcbyte = space.address_to_byte(pc) & space.bytemask(); - - // fetch the bytes up to the maximum - u8 opbuf[64], argbuf[64]; - int maxbytes = (m_disasm != nullptr) ? m_disasm->max_opcode_bytes() : 1; - for (int numbytes = 0; numbytes < maxbytes; numbytes++) - { - opbuf[numbytes] = m_device.machine().debugger().cpu().read_opcode(decrypted_space, pcbyte + numbytes, 1); - argbuf[numbytes] = m_device.machine().debugger().cpu().read_opcode(space, pcbyte + numbytes, 1); - } - - u32 numbytes = maxbytes; - if (m_disasm != nullptr) - { - // disassemble to our buffer - std::ostringstream diasmbuf; - numbytes = m_disasm->disassemble(diasmbuf, pc, opbuf, argbuf) & DASMFLAG_LENGTHMASK; - } + // disassemble the current instruction and get the flags + u32 dasmresult = buffer.disassemble_info(pc); + buffer.data_get(pc, dasmresult & util::disasm_interface::LENGTHMASK, true, opbuf); // return a CRC of the exact count of opcode bytes - return core_crc32(0, opbuf, numbytes); + return core_crc32(0, &opbuf[0], opbuf.size()); } @@ -2593,26 +2576,29 @@ void device_debug::compute_debug_flags() void device_debug::prepare_for_step_overout(offs_t pc) { + debug_disasm_buffer buffer(device()); + // disassemble the current instruction and get the flags - std::string dasmbuffer; - offs_t dasmresult = dasm_wrapped(dasmbuffer, pc); + u32 dasmresult = buffer.disassemble_info(pc); // if flags are supported and it's a call-style opcode, set a temp breakpoint after that instruction - if ((dasmresult & DASMFLAG_SUPPORTED) != 0 && (dasmresult & DASMFLAG_STEP_OVER) != 0) + if ((dasmresult & util::disasm_interface::SUPPORTED) != 0 && (dasmresult & util::disasm_interface::STEP_OVER) != 0) { - int extraskip = (dasmresult & DASMFLAG_OVERINSTMASK) >> DASMFLAG_OVERINSTSHIFT; - pc += dasmresult & DASMFLAG_LENGTHMASK; + int extraskip = (dasmresult & util::disasm_interface::OVERINSTMASK) >> util::disasm_interface::OVERINSTSHIFT; + pc = buffer.next_pc_wrap(pc, dasmresult & util::disasm_interface::LENGTHMASK); // if we need to skip additional instructions, advance as requested - while (extraskip-- > 0) - pc += dasm_wrapped(dasmbuffer, pc) & DASMFLAG_LENGTHMASK; + while (extraskip-- > 0) { + u32 result = buffer.disassemble_info(pc); + pc += buffer.next_pc_wrap(pc, result & util::disasm_interface::LENGTHMASK); + } m_stepaddr = pc; } // if we're stepping out and this isn't a step out instruction, reset the steps until stop to a high number if ((m_flags & DEBUG_FLAG_STEPPING_OUT) != 0) { - if ((dasmresult & DASMFLAG_SUPPORTED) != 0 && (dasmresult & DASMFLAG_STEP_OUT) == 0) + if ((dasmresult & util::disasm_interface::SUPPORTED) != 0 && (dasmresult & util::disasm_interface::STEP_OUT) == 0) m_stepsleft = 100; else m_stepsleft = 1; @@ -2884,38 +2870,6 @@ void device_debug::hotspot_check(address_space &space, offs_t address) } -//------------------------------------------------- -// dasm_wrapped - wraps calls to the disassembler -// by fetching the opcode bytes to a temporary -// buffer and then disassembling them -//------------------------------------------------- - -u32 device_debug::dasm_wrapped(std::string &buffer, offs_t pc) -{ - assert(m_memory != nullptr && m_disasm != nullptr); - - // determine the adjusted PC - address_space &decrypted_space = m_memory->has_space(AS_OPCODES) ? m_memory->space(AS_OPCODES) : m_memory->space(AS_PROGRAM); - address_space &space = m_memory->space(AS_PROGRAM); - offs_t pcbyte = space.address_to_byte(pc) & space.bytemask(); - - // fetch the bytes up to the maximum - u8 opbuf[64], argbuf[64]; - int maxbytes = m_disasm->max_opcode_bytes(); - for (int numbytes = 0; numbytes < maxbytes; numbytes++) - { - opbuf[numbytes] = m_device.machine().debugger().cpu().read_opcode(decrypted_space, pcbyte + numbytes, 1); - argbuf[numbytes] = m_device.machine().debugger().cpu().read_opcode(space, pcbyte + numbytes, 1); - } - - // disassemble to our buffer - std::ostringstream stream; - uint32_t result = m_disasm->disassemble(stream, pc, opbuf, argbuf); - buffer = stream.str(); - return result; -} - - //------------------------------------------------- // get_current_pc - getter callback for a device's // current instruction pointer @@ -3257,35 +3211,24 @@ void device_debug::tracer::update(offs_t pc) if (!m_action.empty()) m_debug.m_device.machine().debugger().console().execute_command(m_action, false); - // print the address - std::string buffer; - int logaddrchars = m_debug.logaddrchars(); - if (m_debug.is_octal()) - { - buffer = string_format("%0*o: ", logaddrchars*3/2, pc); - } - else - { - buffer = string_format("%0*X: ", logaddrchars, pc); - } - - // print the disassembly - std::string dasm; - offs_t dasmresult = m_debug.dasm_wrapped(dasm, pc); - buffer.append(dasm); + debug_disasm_buffer buffer(m_debug.device()); + std::string instruction; + offs_t next_pc, size; + u32 dasmresult; + buffer.disassemble(pc, instruction, next_pc, size, dasmresult); // output the result - fprintf(&m_file, "%s\n", buffer.c_str()); + fprintf(&m_file, "%s: %s\n", buffer.pc_to_string(pc).c_str(), instruction.c_str()); // do we need to step the trace over this instruction? - if (m_trace_over && (dasmresult & DASMFLAG_SUPPORTED) != 0 && (dasmresult & DASMFLAG_STEP_OVER) != 0) + if (m_trace_over && (dasmresult & util::disasm_interface::SUPPORTED) != 0 && (dasmresult & util::disasm_interface::STEP_OVER) != 0) { - int extraskip = (dasmresult & DASMFLAG_OVERINSTMASK) >> DASMFLAG_OVERINSTSHIFT; - offs_t trace_over_target = pc + (dasmresult & DASMFLAG_LENGTHMASK); + int extraskip = (dasmresult & util::disasm_interface::OVERINSTMASK) >> util::disasm_interface::OVERINSTSHIFT; + offs_t trace_over_target = buffer.next_pc_wrap(pc, dasmresult & util::disasm_interface::LENGTHMASK); // if we need to skip additional instructions, advance as requested while (extraskip-- > 0) - trace_over_target += m_debug.dasm_wrapped(dasm, trace_over_target) & DASMFLAG_LENGTHMASK; + trace_over_target = buffer.next_pc_wrap(trace_over_target, buffer.disassemble_info(trace_over_target) & util::disasm_interface::LENGTHMASK); m_trace_over_target = trace_over_target; } diff --git a/src/emu/debug/debugcpu.h b/src/emu/debug/debugcpu.h index 2ea78c3fe20..e00ac9576cc 100644 --- a/src/emu/debug/debugcpu.h +++ b/src/emu/debug/debugcpu.h @@ -278,7 +278,6 @@ private: // internal helpers void prepare_for_step_overout(offs_t pc); - u32 dasm_wrapped(std::string &buffer, offs_t pc); void errorlog_write_line(const char *line); // breakpoint and watchpoint helpers diff --git a/src/emu/debug/dvdisasm.cpp b/src/emu/debug/dvdisasm.cpp index 1051365c561..9ad6cb968c2 100644 --- a/src/emu/debug/dvdisasm.cpp +++ b/src/emu/debug/dvdisasm.cpp @@ -1,5 +1,5 @@ // license:BSD-3-Clause -// copyright-holders:Aaron Giles +// copyright-holders:Aaron Giles, Olivier Galibert /********************************************************************* dvdisasm.c @@ -14,7 +14,6 @@ #include "debugcpu.h" #include "debugger.h" - //************************************************************************** // DEBUG VIEW DISASM SOURCE //************************************************************************** @@ -25,7 +24,6 @@ debug_view_disasm_source::debug_view_disasm_source(const char *name, device_t &device) : debug_view_source(name, &device), - m_disasmintf(dynamic_cast(&device)), m_space(device.memory().space(AS_PROGRAM)), m_decrypted_space(device.memory().has_space(AS_OPCODES) ? device.memory().space(AS_OPCODES) : device.memory().space(AS_PROGRAM)) { @@ -49,23 +47,17 @@ debug_view_disasm::debug_view_disasm(running_machine &machine, debug_view_osd_up m_right_column(DASM_RIGHTCOL_RAW), m_backwards_steps(3), m_dasm_width(DEFAULT_DASM_WIDTH), - m_last_direct_raw(nullptr), - m_last_direct_decrypted(nullptr), - m_last_change_count(0), - m_last_pcbyte(0), - m_divider1(0), - m_divider2(0), - m_divider3(0), + m_previous_pc(1), m_expression(machine) { // fail if no available sources enumerate_sources(); - if (m_source_list.count() == 0) + if(m_source_list.count() == 0) throw std::bad_alloc(); // count the number of comments int total_comments = 0; - for (const debug_view_source &source : m_source_list) + for(const debug_view_source &source : m_source_list) { const debug_view_disasm_source &dasmsource = downcast(source); total_comments += dasmsource.device()->debug()->comment_count(); @@ -98,10 +90,10 @@ void debug_view_disasm::enumerate_sources() // iterate over devices with disassembly interfaces std::string name; - for (device_disasm_interface &dasm : disasm_interface_iterator(machine().root_device())) + for(device_disasm_interface &dasm : disasm_interface_iterator(machine().root_device())) { name = string_format("%s '%s'", dasm.device().name(), dasm.device().tag()); - if (dasm.device().memory().space_config(AS_PROGRAM)!=nullptr) + if(dasm.device().memory().space_config(AS_PROGRAM)!=nullptr) m_source_list.append(*global_alloc(debug_view_disasm_source(name.c_str(), dasm.device()))); } @@ -117,10 +109,10 @@ void debug_view_disasm::enumerate_sources() void debug_view_disasm::view_notify(debug_view_notification type) { - if (type == VIEW_NOTIFY_CURSOR_CHANGED) + if(type == VIEW_NOTIFY_CURSOR_CHANGED) adjust_visible_y_for_cursor(); - else if (type == VIEW_NOTIFY_SOURCE_CHANGED) + else if(type == VIEW_NOTIFY_SOURCE_CHANGED) m_expression.set_context(&downcast(m_source)->device()->debug()->symtable()); } @@ -136,29 +128,29 @@ void debug_view_disasm::view_char(int chval) u8 end_buffer = 3; s32 temp; - switch (chval) + switch(chval) { case DCH_UP: - if (m_cursor.y > 0) + if(m_cursor.y > 0) m_cursor.y--; break; case DCH_DOWN: - if (m_cursor.y < m_total.y - 1) + if(m_cursor.y < m_total.y - 1) m_cursor.y++; break; case DCH_PUP: - temp = m_cursor.y - (m_visible.y - end_buffer); - if (temp < 0) + temp = m_cursor.y -(m_visible.y - end_buffer); + if(temp < 0) m_cursor.y = 0; else m_cursor.y = temp; break; case DCH_PDOWN: - temp = m_cursor.y + (m_visible.y - end_buffer); - if (temp > m_total.y - 1) + temp = m_cursor.y +(m_visible.y - end_buffer); + if(temp > m_total.y - 1) m_cursor.y = m_total.y - 1; else m_cursor.y = temp; @@ -167,11 +159,11 @@ void debug_view_disasm::view_char(int chval) case DCH_HOME: // set the active column to the PC { const debug_view_disasm_source &source = downcast(*m_source); - offs_t pc = source.m_space.address_to_byte(source.device()->safe_pcbase()) & source.m_space.logbytemask(); + offs_t pc = source.device()->safe_pcbase() & source.m_space.logaddrmask(); // figure out which row the pc is on - for (unsigned int curline = 0; curline < m_dasm.size(); curline++) - if (m_dasm[curline].m_byteaddress == pc) + for(unsigned int curline = 0; curline < m_dasm.size(); curline++) + if(m_dasm[curline].m_address == pc) m_cursor.y = curline; break; } @@ -186,7 +178,7 @@ void debug_view_disasm::view_char(int chval) } /* send a cursor changed notification */ - if (m_cursor.y != origcursor.y) + if(m_cursor.y != origcursor.y) { begin_update(); view_notify(VIEW_NOTIFY_CURSOR_CHANGED); @@ -208,7 +200,7 @@ void debug_view_disasm::view_click(const int button, const debug_view_xy& pos) /* cursor popup|toggle */ bool cursorVisible = true; - if (m_cursor.y == origcursor.y) + if(m_cursor.y == origcursor.y) { cursorVisible = !m_cursor_visible; } @@ -221,218 +213,174 @@ void debug_view_disasm::view_click(const int button, const debug_view_xy& pos) end_update(); } +void debug_view_disasm::generate_from_address(debug_disasm_buffer &buffer, offs_t address) +{ + m_dasm.clear(); + for(int i=0; i != m_total.y; i++) { + std::string dasm; + offs_t size; + offs_t next_address; + u32 info; + buffer.disassemble(address, dasm, next_address, size, info); + m_dasm.emplace_back(address, size, dasm); + address = next_address; + } +} -//------------------------------------------------- -// find_pc_backwards - back up the specified -// number of instructions from the given PC -//------------------------------------------------- - -offs_t debug_view_disasm::find_pc_backwards(offs_t targetpc, int numinstrs) +bool debug_view_disasm::generate_with_pc(debug_disasm_buffer &buffer, offs_t pc) { - auto dis = machine().disable_side_effect(); + // Consider that instructions are 64 bytes max const debug_view_disasm_source &source = downcast(*m_source); + int shift = source.m_space.addrbus_shift(); - // compute the increment - int minlen = source.m_space.byte_to_address(source.m_disasmintf->min_opcode_bytes()); - if (minlen == 0) minlen = 1; - int maxlen = source.m_space.byte_to_address(source.m_disasmintf->max_opcode_bytes()); - if (maxlen == 0) maxlen = 1; - - // start off numinstrs back - offs_t curpc = targetpc - minlen * numinstrs; - if (curpc > targetpc) - curpc = 0; - - /* loop until we find what we are looking for */ - offs_t targetpcbyte = source.m_space.address_to_byte(targetpc) & source.m_space.logbytemask(); - offs_t fillpcbyte = targetpcbyte; - offs_t lastgoodpc = targetpc; - while (1) - { - // fill the buffer up to the target - offs_t curpcbyte = source.m_space.address_to_byte(curpc) & source.m_space.logbytemask(); - u8 opbuf[1024], argbuf[1024]; - while (curpcbyte < fillpcbyte) - { - fillpcbyte--; - opbuf[1000 + fillpcbyte - targetpcbyte] = machine().debugger().cpu().read_opcode(source.m_decrypted_space, fillpcbyte, 1); - argbuf[1000 + fillpcbyte - targetpcbyte] = machine().debugger().cpu().read_opcode(source.m_space, fillpcbyte, 1); + offs_t backwards_offset; + if(shift < 0) + backwards_offset = 64 >> -shift; + else if(shift == 0) + backwards_offset = 64; + else + backwards_offset = 64 << shift; + + m_dasm.clear(); + offs_t address = (pc - m_backwards_steps*backwards_offset) & source.m_space.logaddrmask(); + // Handle wrap at 0 + if(address > pc) + address = 0; + + util::disasm_interface *intf = dynamic_cast(*source.device()).get_disassembler(); + if(intf->interface_flags() & util::disasm_interface::NONLINEAR_PC) { + offs_t lpc = intf->pc_real_to_linear(pc); + while(intf->pc_real_to_linear(address) < lpc) { + std::string dasm; + offs_t size; + offs_t next_address; + u32 info; + buffer.disassemble(address, dasm, next_address, size, info); + m_dasm.emplace_back(address, size, dasm); + if(intf->pc_real_to_linear(address) > intf->pc_real_to_linear(next_address)) + return false; + address = next_address; } - // loop until we get past the target instruction - int instcount = 0; - int instlen; - offs_t scanpc; - for (scanpc = curpc; scanpc < targetpc; scanpc += instlen) - { - offs_t scanpcbyte = source.m_space.address_to_byte(scanpc) & source.m_space.logbytemask(); - offs_t physpcbyte = scanpcbyte; - - // get the disassembly, but only if mapped - instlen = 1; - if (source.m_space.device().memory().translate(source.m_space.spacenum(), TRANSLATE_FETCH, physpcbyte)) - { - std::ostringstream dasmbuffer; - instlen = source.m_disasmintf->disassemble(dasmbuffer, scanpc, &opbuf[1000 + scanpcbyte - targetpcbyte], &argbuf[1000 + scanpcbyte - targetpcbyte]) & DASMFLAG_LENGTHMASK; - } - - // count this one - instcount++; + } else { + while(address < pc) { + std::string dasm; + offs_t size; + offs_t next_address; + u32 info; + buffer.disassemble(address, dasm, next_address, size, info); + m_dasm.emplace_back(address, size, dasm); + if(address > next_address) + return false; + address = next_address; } + } - // if we ended up right on targetpc, this is a good candidate - if (scanpc == targetpc && instcount <= numinstrs) - lastgoodpc = curpc; - - // we're also done if we go back too far - if (targetpc - curpc >= numinstrs * maxlen) - break; + if(address != pc) + return false; - // and if we hit 0, we're done - if (curpc == 0) - break; + if(m_dasm.size() > m_backwards_steps) + m_dasm.erase(m_dasm.begin(), m_dasm.begin() + (m_dasm.size() - m_backwards_steps)); - // back up one more and try again - curpc -= minlen; - if (curpc > targetpc) - curpc = 0; + while(m_dasm.size() < m_total.y) { + std::string dasm; + offs_t size; + offs_t next_address; + u32 info; + buffer.disassemble(address, dasm, next_address, size, info); + m_dasm.emplace_back(address, size, dasm); + address = next_address; } - - return lastgoodpc; + return true; } - -//------------------------------------------------- -// generate_bytes - generate the opcode byte -// values -//------------------------------------------------- - -std::string debug_view_disasm::generate_bytes(offs_t pcbyte, int numbytes, int granularity, bool encrypted) +int debug_view_disasm::address_position(offs_t pc) const { - const debug_view_disasm_source &source = downcast(*m_source); - const int char_num = source.m_space.is_octal() ? 3 : 2; - std::ostringstream ostr; - - for (int byte = 0; byte < numbytes; byte += granularity) { - if (byte) - ostr << ' '; - util::stream_format(ostr, source.m_space.is_octal() ? "%0*o" : "%0*X", granularity * char_num, machine().debugger().cpu().read_opcode(encrypted ? source.m_space : source.m_decrypted_space, pcbyte + byte, granularity)); - } - - return ostr.str(); + for(int i=0; i != int(m_dasm.size()); i++) + if(m_dasm[i].m_address == pc) + return i; + return -1; } - -//------------------------------------------------- -// recompute - recompute selected info for the -// disassembly view -//------------------------------------------------- - -bool debug_view_disasm::recompute(offs_t pc, int startline, int lines) +void debug_view_disasm::generate_dasm(debug_disasm_buffer &buffer, offs_t pc) { - auto dis = machine().disable_side_effect(); - - bool changed = false; - const debug_view_disasm_source &source = downcast(*m_source); - const int char_num = source.m_space.is_octal() ? 3 : 2; - - // determine how many characters we need for an address and set the divider - m_divider1 = 1 + (source.m_space.logaddrchars()/2*char_num) + 1; + bool pc_changed = pc != m_previous_pc; + m_previous_pc = pc; + if(strcmp(m_expression.string(), "curpc")) { + if(m_expression.dirty()) { + m_topleft.x = 0; + m_topleft.y = 0; + } + generate_from_address(buffer, m_expression.value()); + return; + } - // assume a fixed number of characters for the disassembly - m_divider2 = m_divider1 + 1 + m_dasm_width + 1; + if(address_position(pc) != -1) { + generate_from_address(buffer, m_dasm[0].m_address); + int pos = address_position(pc); + if(pos != -1) { + if(!pc_changed) + return; + if(pos >= m_topleft.y && pos < m_topleft.y + m_visible.y) + return; + if(pos < m_total.y - m_visible.y) { + m_topleft.x = 0; + m_topleft.y = pos - m_backwards_steps; + return; + } + } + } - // determine how many bytes we might need to display - const int minbytes = source.m_disasmintf->min_opcode_bytes(); - const int maxbytes = source.m_disasmintf->max_opcode_bytes(); + m_topleft.x = 0; + m_topleft.y = 0; - // ensure that the PC is aligned to the minimum opcode size - pc &= ~source.m_space.byte_to_address_end(minbytes - 1); + if(generate_with_pc(buffer, pc)) + return; - // set the width of the third column according to display mode - if (m_right_column == DASM_RIGHTCOL_RAW || m_right_column == DASM_RIGHTCOL_ENCRYPTED) - { - int const maxbytes_clamped = (std::min)(maxbytes, DASM_MAX_BYTES); - m_total.x = m_divider2 + 1 + char_num * maxbytes_clamped + (maxbytes_clamped / minbytes - 1) + 1; - } - else if (m_right_column == DASM_RIGHTCOL_COMMENTS) - m_total.x = m_divider2 + 1 + 50; // DEBUG_COMMENT_MAX_LINE_LENGTH - else - m_total.x = m_divider2 + 1; + generate_from_address(buffer, pc); +} - // allocate dasm array - m_dasm.resize(m_total.y); +void debug_view_disasm::complete_information(const debug_view_disasm_source &source, debug_disasm_buffer &buffer, offs_t pc) +{ + for(auto &dasm : m_dasm) { + offs_t adr = dasm.m_address; - // comparison buffer to detect whether data changed when doing only one line - dasm_line comparison_buffer; + dasm.m_tadr = buffer.pc_to_string(adr); + dasm.m_topcodes = buffer.data_to_string(adr, dasm.m_size, true); + dasm.m_tparams = buffer.data_to_string(adr, dasm.m_size, false); - // iterate over lines - for (int line = 0; line < lines; line++) - { - // convert PC to a byte offset - const offs_t pcbyte = source.m_space.address_to_byte(pc) & source.m_space.logbytemask(); - - // save a copy of the previous line as a backup if we're only doing one line - const auto instr = startline + line; - if (lines == 1) - comparison_buffer = m_dasm[instr]; - - // convert back and set the address of this instruction - std::ostringstream oadr; - m_dasm[instr].m_byteaddress = pcbyte; - util::stream_format(oadr, - source.m_space.is_octal() ? " %0*o " : " %0*X ", - source.m_space.logaddrchars()/2*char_num, source.m_space.byte_to_address(pcbyte)); - m_dasm[instr].m_adr = oadr.str(); - - // make sure we can translate the address, and then disassemble the result - std::ostringstream dasm; - int numbytes = 0; - offs_t physpcbyte = pcbyte; - if (source.m_space.device().memory().translate(source.m_space.spacenum(), TRANSLATE_FETCH_DEBUG, physpcbyte)) - { - u8 opbuf[64], argbuf[64]; + dasm.m_is_pc = adr == pc; - // fetch the bytes up to the maximum - for (numbytes = 0; numbytes < maxbytes; numbytes++) - { - opbuf[numbytes] = machine().debugger().cpu().read_opcode(source.m_decrypted_space, pcbyte + numbytes, 1); - argbuf[numbytes] = machine().debugger().cpu().read_opcode(source.m_space, pcbyte + numbytes, 1); + dasm.m_is_bp = false; + for(device_debug::breakpoint *bp = source.device()->debug()->breakpoint_first(); bp != nullptr; bp = bp->next()) + if(adr ==(bp->address() & source.m_space.logaddrmask())) { + dasm.m_is_bp = true; + break; } - // disassemble the result - pc += numbytes = source.m_disasmintf->disassemble(dasm, pc & source.m_space.logaddrmask(), opbuf, argbuf) & DASMFLAG_LENGTHMASK; - } - else - dasm << ""; - - m_dasm[instr].m_dasm = dasm.str(); + dasm.m_is_visited = source.device()->debug()->track_pc_visited(adr); - // generate the byte views - std::ostringstream bytes_raw; - numbytes = source.m_space.address_to_byte(numbytes) & source.m_space.logbytemask(); - m_dasm[instr].m_rawdata = generate_bytes(pcbyte, numbytes, minbytes, false); - m_dasm[instr].m_encdata = generate_bytes(pcbyte, numbytes, minbytes, true); + const char *comment = source.device()->debug()->comment_text(adr); + if(comment) + dasm.m_comment = comment; + } +} - // get and add the comment, if present - const offs_t comment_address = source.m_space.byte_to_address(m_dasm[instr].m_byteaddress); - const char *const text = source.device()->debug()->comment_text(comment_address); - if (text != nullptr) - m_dasm[instr].m_comment = text; +//------------------------------------------------- +// view_update - update the contents of the +// disassembly view +//------------------------------------------------- - // see if the line changed at all - if (lines == 1 && m_dasm[instr] != comparison_buffer) - changed = true; - } +void debug_view_disasm::view_update() +{ + const debug_view_disasm_source &source = downcast(*m_source); + debug_disasm_buffer buffer(*source.device()); + offs_t pc = source.device()->safe_pcbase() & source.m_space.logaddrmask(); - // update opcode base information - m_last_direct_decrypted = source.m_decrypted_space.direct().ptr(); - m_last_direct_raw = source.m_space.direct().ptr(); - m_last_change_count = source.device()->debug()->comment_change_count(); + generate_dasm(buffer, pc); - // no longer need to recompute - m_recompute = false; - return changed; + complete_information(source, buffer, pc); + redraw(); } @@ -443,11 +391,11 @@ bool debug_view_disasm::recompute(offs_t pc, int startline, int lines) void debug_view_disasm::print(int row, std::string text, int start, int end, u8 attrib) { int view_end = end - m_topleft.x; - if (view_end < 0) + if(view_end < 0) return; int string_0 = start - m_topleft.x; - if (string_0 >= m_visible.x) + if(string_0 >= m_visible.x) return; int view_start = string_0 > 0 ? string_0 : 0; @@ -458,152 +406,63 @@ void debug_view_disasm::print(int row, std::string text, int start, int end, u8 for(int pos = view_start; pos < view_end; pos++) { int spos = pos - string_0; - if (spos >= int(text.size())) + if(spos >= int(text.size())) *dest++ = { ' ', attrib }; else *dest++ = { u8(text[spos]), attrib }; - } + } } + //------------------------------------------------- -// view_update - update the contents of the -// disassembly view +// redraw - update the view from the data //------------------------------------------------- -void debug_view_disasm::view_update() +void debug_view_disasm::redraw() { - const debug_view_disasm_source &source = downcast(*m_source); - - offs_t pc = source.device()->safe_pcbase(); - offs_t pcbyte = source.m_space.address_to_byte(pc) & source.m_space.logbytemask(); - - // update our context; if the expression is dirty, recompute - if (m_expression.dirty()) - m_recompute = true; - - // if we're tracking a value, make sure it is visible - u64 previous = m_expression.last_value(); - u64 result = m_expression.value(); - if (result != previous) - { - offs_t resultbyte = source.m_space.address_to_byte(result) & source.m_space.logbytemask(); - - // see if the new result is an address we already have - u32 row; - for (row = 0; row < m_dasm.size(); row++) - if (m_dasm[row].m_byteaddress == resultbyte) - break; - - // if we didn't find it, or if it's really close to the bottom, recompute - if (row == m_dasm.size() || row >= m_total.y - m_visible.y) - m_recompute = true; - - // otherwise, if it's not visible, adjust the view so it is - else if (row < m_topleft.y || row >= m_topleft.y + m_visible.y - 2) - m_topleft.y = (row > 3) ? row - 3 : 0; - } - - // if the opcode base has changed, rework things - if (source.m_decrypted_space.direct().ptr() != m_last_direct_decrypted || source.m_space.direct().ptr() != m_last_direct_raw) - m_recompute = true; - - // if the comments have changed, redo it - if (m_last_change_count != source.device()->debug()->comment_change_count()) - m_recompute = true; - - // if we need to recompute, do it - bool recomputed_this_time = false; -recompute: - if (m_recompute) - { - // recompute the view - if (!m_dasm.empty() && m_last_change_count != source.device()->debug()->comment_change_count()) - { - // smoosh us against the left column, but not the top row - m_topleft.x = 0; - - // recompute from where we last recomputed! - recompute(source.m_space.byte_to_address(m_dasm[0].m_byteaddress), 0, m_total.y); - } - else - { - // determine the addresses of what we will display - offs_t backpc = find_pc_backwards(u32(m_expression.value()), m_backwards_steps); - - // put ourselves back in the top left - m_topleft.y = 0; - m_topleft.x = 0; - - recompute(backpc, 0, m_total.y); - } - recomputed_this_time = true; - } + // determine how many characters we need for an address and set the divider + int m_divider1 = 1 + m_dasm[0].m_tadr.size() + 1; - // figure out the row where the PC is and recompute the disassembly - if (pcbyte != m_last_pcbyte) - { - // find the row with the PC on it - for (u32 row = 0; row < m_visible.y; row++) - { - u32 effrow = m_topleft.y + row; - if (effrow >= m_dasm.size()) - break; - if (pcbyte == m_dasm[effrow].m_byteaddress) - { - // see if we changed - bool changed = recompute(pc, effrow, 1); - if (changed && !recomputed_this_time) - { - m_recompute = true; - goto recompute; - } + // assume a fixed number of characters for the disassembly + int m_divider2 = m_divider1 + 1 + m_dasm_width + 1; - // set the effective row and PC - m_cursor.y = effrow; - view_notify(VIEW_NOTIFY_CURSOR_CHANGED); - } - } - m_last_pcbyte = pcbyte; - } + // set the width of the third column to max comment length + m_total.x = m_divider2 + 1 + 50; // DEBUG_COMMENT_MAX_LINE_LENGTH // loop over visible rows - for (u32 row = 0; row < m_visible.y; row++) + for(u32 row = 0; row < m_visible.y; row++) { u32 effrow = m_topleft.y + row; // if this visible row is valid, add it to the buffer u8 attrib = DCA_NORMAL; - if (effrow < m_dasm.size()) + if(effrow < m_dasm.size()) { - // if we're on the line with the PC, recompute and hilight it - if (pcbyte == m_dasm[effrow].m_byteaddress) + // if we're on the line with the PC, hilight it + if(m_dasm[effrow].m_is_pc) attrib = DCA_CURRENT; // if we're on a line with a breakpoint, tag it changed - else - { - for (device_debug::breakpoint *bp = source.device()->debug()->breakpoint_first(); bp != nullptr; bp = bp->next()) - if (m_dasm[effrow].m_byteaddress == (source.m_space.address_to_byte(bp->address()) & source.m_space.logbytemask())) - attrib = DCA_CHANGED; - } + else if(m_dasm[effrow].m_is_bp) + attrib = DCA_CHANGED; // if we're on the active column and everything is couth, highlight it - if (m_cursor_visible && effrow == m_cursor.y) + if(m_cursor_visible && effrow == m_cursor.y) attrib |= DCA_SELECTED; // if we've visited this pc, mark it as such - if (source.device()->debug()->track_pc_visited(m_dasm[effrow].m_byteaddress)) + if(m_dasm[effrow].m_is_visited) attrib |= DCA_VISITED; - print(row, m_dasm[effrow].m_adr, 0, m_divider1, attrib | DCA_ANCILLARY); + print(row, ' ' + m_dasm[effrow].m_tadr, 0, m_divider1, attrib | DCA_ANCILLARY); print(row, ' ' + m_dasm[effrow].m_dasm, m_divider1, m_divider2, attrib); - if (m_right_column == DASM_RIGHTCOL_RAW || m_right_column == DASM_RIGHTCOL_ENCRYPTED) { - std::string text = ' ' + (m_right_column == DASM_RIGHTCOL_RAW ? m_dasm[effrow].m_rawdata : m_dasm[effrow].m_encdata); + if(m_right_column == DASM_RIGHTCOL_RAW || m_right_column == DASM_RIGHTCOL_ENCRYPTED) { + std::string text = ' ' +(m_right_column == DASM_RIGHTCOL_RAW ? m_dasm[effrow].m_topcodes : m_dasm[effrow].m_tparams); print(row, text, m_divider2, m_visible.x, attrib | DCA_ANCILLARY); if(int(text.size()) > m_visible.x - m_divider2) { int base = m_total.x - 3; - if (base < m_divider2) + if(base < m_divider2) base = m_divider2; print(row, "...", base, m_visible.x, attrib | DCA_ANCILLARY); } @@ -624,7 +483,7 @@ recompute: offs_t debug_view_disasm::selected_address() { flush_updates(); - return downcast(*m_source).m_space.byte_to_address(m_dasm[m_cursor.y].m_byteaddress); + return m_dasm[m_cursor.y].m_address; } @@ -679,7 +538,7 @@ void debug_view_disasm::set_disasm_width(u32 width) { begin_update(); m_dasm_width = width; - m_recompute = m_update_pending = true; + m_update_pending = true; end_update(); } @@ -692,10 +551,9 @@ void debug_view_disasm::set_disasm_width(u32 width) void debug_view_disasm::set_selected_address(offs_t address) { const debug_view_disasm_source &source = downcast(*m_source); - offs_t byteaddress = source.m_space.address_to_byte(address) & source.m_space.logbytemask(); - for (int line = 0; line < m_total.y; line++) - if (m_dasm[line].m_byteaddress == byteaddress) - { + address = address & source.m_space.logaddrmask(); + for(int line = 0; line < m_total.y; line++) + if(m_dasm[line].m_address == address) { m_cursor.y = line; set_cursor_position(m_cursor); break; diff --git a/src/emu/debug/dvdisasm.h b/src/emu/debug/dvdisasm.h index 85ebd7cfef2..dcf756117b8 100644 --- a/src/emu/debug/dvdisasm.h +++ b/src/emu/debug/dvdisasm.h @@ -14,6 +14,7 @@ #pragma once #include "debugvw.h" +#include "debugbuf.h" #include "vecstream.h" @@ -51,7 +52,6 @@ public: private: // internal state - device_disasm_interface *m_disasmintf; // disassembly interface address_space & m_space; // address space to display address_space & m_decrypted_space; // address space to display for decrypted opcodes }; @@ -90,49 +90,42 @@ protected: private: // The information of one disassembly line. May become the actual - // external interface at one point + // external interface at one point. struct dasm_line { - offs_t m_byteaddress; // address of the first byte of the instruction - std::string m_adr; // instruction address as a string + offs_t m_address; // address of the instruction + offs_t m_size; // size of the instruction + + std::string m_tadr; // instruction address as a string std::string m_dasm; // disassembly - std::string m_rawdata; // textual representation of the instruction values - std::string m_encdata; // textual representation of encrypted instruction values + std::string m_topcodes; // textual representation of opcode/default values + std::string m_tparams; // textual representation of parameter values std::string m_comment; // comment, when present - bool operator == (const dasm_line &right) const { - return - m_byteaddress == right.m_byteaddress && - m_adr == right.m_adr && - m_dasm == right.m_dasm && - m_rawdata == right.m_rawdata && - m_encdata == right.m_encdata && - m_comment == right.m_comment; - } - - bool operator != (const dasm_line &right) const { - return !(*this == right); - } + bool m_is_pc; // this line's address is PC + bool m_is_bp; // this line's address is a breakpoint + bool m_is_visited; // this line has been visited + + dasm_line(offs_t address, offs_t size, std::string dasm) : m_address(address), m_size(size), m_dasm(dasm), m_is_pc(false), m_is_bp(false), m_is_visited(false) {} }; // internal helpers + void generate_from_address(debug_disasm_buffer &buffer, offs_t address); + bool generate_with_pc(debug_disasm_buffer &buffer, offs_t pc); + int address_position(offs_t pc) const; + void generate_dasm(debug_disasm_buffer &buffer, offs_t pc); + void complete_information(const debug_view_disasm_source &source, debug_disasm_buffer &buffer, offs_t pc); + void enumerate_sources(); - offs_t find_pc_backwards(offs_t targetpc, int numinstrs); - std::string generate_bytes(offs_t pcbyte, int numbytes, int granularity, bool encrypted); - bool recompute(offs_t pc, int startline, int lines); void print(int row, std::string text, int start, int end, u8 attrib); + void redraw(); // internal state - disasm_right_column m_right_column; // right column contents - u32 m_backwards_steps; // number of backwards steps - u32 m_dasm_width; // width of the disassembly area - u8 * m_last_direct_raw; // last direct raw value - u8 * m_last_direct_decrypted;// last direct decrypted value - u32 m_last_change_count; // last comment change count - offs_t m_last_pcbyte; // last PC byte value - int m_divider1, m_divider2; // left and right divider columns - int m_divider3; // comment divider column - debug_view_expression m_expression; // expression-related information - std::vector m_dasm; // disassembled instructions + disasm_right_column m_right_column; // right column contents + u32 m_backwards_steps; // number of backwards steps + u32 m_dasm_width; // width of the disassembly area + offs_t m_previous_pc; // previous pc, to detect whether it changed + debug_view_expression m_expression; // expression-related information + std::vector m_dasm; // disassembled instructions // constants static constexpr int DEFAULT_DASM_LINES = 1000; diff --git a/src/emu/devcpu.h b/src/emu/devcpu.h index 1c4bce13506..35c8c3b2a9e 100644 --- a/src/emu/devcpu.h +++ b/src/emu/devcpu.h @@ -49,15 +49,6 @@ -//************************************************************************** -// MACROS -//************************************************************************** - -#define CPU_DISASSEMBLE_NAME(name) cpu_disassemble_##name -#define CPU_DISASSEMBLE(name) offs_t CPU_DISASSEMBLE_NAME(name)(cpu_device *device, std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, int options) -#define CPU_DISASSEMBLE_CALL(name) CPU_DISASSEMBLE_NAME(name)(device, stream, pc, oprom, opram, options) - - //************************************************************************** // TYPE DEFINITIONS //************************************************************************** @@ -86,7 +77,4 @@ private: }; -typedef offs_t (*cpu_disassemble_func)(cpu_device *device, std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, int options); - - #endif /* MAME_EMU_DEVCPU_H */ diff --git a/src/emu/didisasm.cpp b/src/emu/didisasm.cpp index 95353889a65..51a96915a04 100644 --- a/src/emu/didisasm.cpp +++ b/src/emu/didisasm.cpp @@ -11,82 +11,93 @@ #include "emu.h" -//************************************************************************** -// DEVICE DISASM INTERFACE -//************************************************************************** - -//------------------------------------------------- -// device_disasm_interface - constructor -//------------------------------------------------- - device_disasm_interface::device_disasm_interface(const machine_config &mconfig, device_t &device) : device_interface(device, "disasm") { } +util::disasm_interface *device_disasm_interface::get_disassembler() +{ + if(!m_disasm) { + if(m_dasm_override.isnull()) + m_disasm.reset(create_disassembler()); + else + m_disasm = std::make_unique(create_disassembler(), m_dasm_override); + } + return m_disasm.get(); +} -//------------------------------------------------- -// ~device_disasm_interface - destructor -//------------------------------------------------- +void device_disasm_interface::interface_pre_start() +{ + m_dasm_override.bind_relative_to(*device().owner()); +} -device_disasm_interface::~device_disasm_interface() +void device_disasm_interface::set_dasm_override(dasm_override_delegate dasm_override) { + m_dasm_override = dasm_override; } +device_disasm_indirect::device_disasm_indirect(util::disasm_interface *upper, dasm_override_delegate &dasm_override) : m_dasm_override(dasm_override) +{ + m_disasm.reset(upper); +} -//------------------------------------------------- -// interface_pre_start - work to be done prior to -// actually starting a device -//------------------------------------------------- +u32 device_disasm_indirect::interface_flags() const +{ + return m_disasm->interface_flags(); +} -void device_disasm_interface::interface_pre_start() +u32 device_disasm_indirect::page_address_bits() const { - // bind delegate - m_dasm_override.bind_relative_to(*device().owner()); + return m_disasm->page_address_bits(); } +u32 device_disasm_indirect::page2_address_bits() const +{ + return m_disasm->page2_address_bits(); +} -//------------------------------------------------- -// static_set_dasm_override - configuration -// helper to override disassemble function -//------------------------------------------------- +offs_t device_disasm_indirect::pc_linear_to_real(offs_t pc) const +{ + return m_disasm->pc_linear_to_real(pc); +} -void device_disasm_interface::static_set_dasm_override(device_t &device, dasm_override_delegate dasm_override) +offs_t device_disasm_indirect::pc_real_to_linear(offs_t pc) const { - device_disasm_interface *dasm; - if (!device.interface(dasm)) - throw emu_fatalerror("MCFG_DEVICE_DISASSEMBLE_OVERRIDE called on device '%s' with no disasm interface", device.tag()); - dasm->m_dasm_override = dasm_override; + return m_disasm->pc_real_to_linear(pc); } +u8 device_disasm_indirect::decrypt8 (u8 value, offs_t pc, bool opcode) const +{ + return m_disasm->decrypt8(value, pc, opcode); +} -//------------------------------------------------- -// disassemble - interface for disassembly -//------------------------------------------------- +u16 device_disasm_indirect::decrypt16(u16 value, offs_t pc, bool opcode) const +{ + return m_disasm->decrypt16(value, pc, opcode); +} -offs_t device_disasm_interface::disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) +u32 device_disasm_indirect::decrypt32(u32 value, offs_t pc, bool opcode) const { - offs_t result = 0; + return m_disasm->decrypt32(value, pc, opcode); +} - // check for disassembler override - if (!m_dasm_override.isnull()) - result = m_dasm_override(device(), stream, pc, oprom, opram, options); - if (result == 0) - result = disasm_disassemble(stream, pc, oprom, opram, options); +u64 device_disasm_indirect::decrypt64(u64 value, offs_t pc, bool opcode) const +{ + return m_disasm->decrypt64(value, pc, opcode); +} - // make sure we get good results - assert((result & DASMFLAG_LENGTHMASK) != 0); -#ifdef MAME_DEBUG - device_memory_interface *memory; - if (device().interface(memory)) - { - address_space &space = memory->space(AS_PROGRAM); - int bytes = space.address_to_byte(result & DASMFLAG_LENGTHMASK); - assert(bytes >= min_opcode_bytes()); - assert(bytes <= max_opcode_bytes()); - (void) bytes; // appease compiler - } -#endif +u32 device_disasm_indirect::opcode_alignment() const +{ + return m_disasm->opcode_alignment(); +} +offs_t device_disasm_indirect::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) +{ + offs_t result = m_dasm_override(stream, pc, opcodes, params); + if(!result) + result = m_disasm->disassemble(stream, pc, opcodes, params); return result; } + + diff --git a/src/emu/didisasm.h b/src/emu/didisasm.h index edd56b3352f..9636b67a6db 100644 --- a/src/emu/didisasm.h +++ b/src/emu/didisasm.h @@ -17,79 +17,70 @@ #ifndef MAME_EMU_DIDISASM_H #define MAME_EMU_DIDISASM_H - -//************************************************************************** -// CONSTANTS -//************************************************************************** - -// Disassembler constants -constexpr u32 DASMFLAG_SUPPORTED = 0x80000000; // are disassembly flags supported? -constexpr u32 DASMFLAG_STEP_OUT = 0x40000000; // this instruction should be the end of a step out sequence -constexpr u32 DASMFLAG_STEP_OVER = 0x20000000; // this instruction should be stepped over by setting a breakpoint afterwards -constexpr u32 DASMFLAG_OVERINSTMASK = 0x18000000; // number of extra instructions to skip when stepping over -constexpr u32 DASMFLAG_OVERINSTSHIFT = 27; // bits to shift after masking to get the value -constexpr u32 DASMFLAG_LENGTHMASK = 0x0000ffff; // the low 16-bits contain the actual length - - - -//************************************************************************** -// MACROS -//************************************************************************** - -#define DASMFLAG_STEP_OVER_EXTRA(x) ((x) << DASMFLAG_OVERINSTSHIFT) - - - -//************************************************************************** -// INTERFACE CONFIGURATION MACROS -//************************************************************************** +#include "disasmintf.h" #define MCFG_DEVICE_DISASSEMBLE_OVERRIDE(_class, _func) \ - device_disasm_interface::static_set_dasm_override(*device, dasm_override_delegate(&_class::_func, #_class "::" #_func, nullptr, (_class *)nullptr)); - - + dynamic_cast(device)->set_dasm_override(dasm_override_delegate(&_class::_func, #_class "::" #_func, nullptr, (_class *)nullptr)); //************************************************************************** // TYPE DEFINITIONS //************************************************************************** -typedef device_delegate dasm_override_delegate; +typedef device_delegate dasm_override_delegate; // ======================> device_disasm_interface - + // class representing interface-specific live disasm class device_disasm_interface : public device_interface { public: // construction/destruction device_disasm_interface(const machine_config &mconfig, device_t &device); - virtual ~device_disasm_interface(); + virtual ~device_disasm_interface() = default; - // configuration access - u32 min_opcode_bytes() const { return disasm_min_opcode_bytes(); } - u32 max_opcode_bytes() const { return disasm_max_opcode_bytes(); } + // Override + void set_dasm_override(dasm_override_delegate dasm_override); - // static inline configuration helpers - static void static_set_dasm_override(device_t &device, dasm_override_delegate dasm_override); - - // interface for disassembly - offs_t disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options = 0); + // disassembler request + util::disasm_interface *get_disassembler(); protected: - // required operation overrides - virtual u32 disasm_min_opcode_bytes() const = 0; - virtual u32 disasm_max_opcode_bytes() const = 0; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const u8 *oprom, const u8 *opram, u32 options) = 0; + // disassembler creation + virtual util::disasm_interface *create_disassembler() = 0; - // interface-level overrides + // delegate resolving virtual void interface_pre_start() override; private: - dasm_override_delegate m_dasm_override; // provided override function + std::unique_ptr m_disasm; + dasm_override_delegate m_dasm_override; }; // iterator typedef device_interface_iterator disasm_interface_iterator; +class device_disasm_indirect : public util::disasm_interface +{ +public: + device_disasm_indirect(util::disasm_interface *upper, dasm_override_delegate &dasm_override); + virtual ~device_disasm_indirect() = default; + + virtual u32 interface_flags() const override; + virtual u32 page_address_bits() const override; + virtual u32 page2_address_bits() const override; + virtual offs_t pc_linear_to_real(offs_t pc) const override; + virtual offs_t pc_real_to_linear(offs_t pc) const override; + virtual u8 decrypt8 (u8 value, offs_t pc, bool opcode) const override; + virtual u16 decrypt16(u16 value, offs_t pc, bool opcode) const override; + virtual u32 decrypt32(u32 value, offs_t pc, bool opcode) const override; + virtual u64 decrypt64(u64 value, offs_t pc, bool opcode) const override; + + virtual u32 opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; + +private: + std::unique_ptr m_disasm; + dasm_override_delegate &m_dasm_override; +}; #endif /* MAME_EMU_DIDISASM_H */ diff --git a/src/emu/emumem.h b/src/emu/emumem.h index 19edc918aaa..509144eb345 100644 --- a/src/emu/emumem.h +++ b/src/emu/emumem.h @@ -185,6 +185,7 @@ public: endianness_t endianness() const { return m_endianness; } int data_width() const { return m_databus_width; } int addr_width() const { return m_addrbus_width; } + int addrbus_shift() const { return m_addrbus_shift; } // address-to-byte conversion helpers inline offs_t addr2byte(offs_t address) const { return (m_addrbus_shift < 0) ? (address << -m_addrbus_shift) : (address >> m_addrbus_shift); } @@ -240,6 +241,7 @@ public: int data_width() const { return m_config.data_width(); } int addr_width() const { return m_config.addr_width(); } endianness_t endianness() const { return m_config.endianness(); } + int addrbus_shift() const { return m_config.addrbus_shift(); } u64 unmap() const { return m_unmap; } bool is_octal() const { return m_config.m_is_octal; } diff --git a/src/lib/util/disasmintf.cpp b/src/lib/util/disasmintf.cpp new file mode 100644 index 00000000000..9699f68e823 --- /dev/null +++ b/src/lib/util/disasmintf.cpp @@ -0,0 +1,47 @@ +#include "disasmintf.h" + +util::u32 util::disasm_interface::interface_flags() const +{ + return 0; +} + +util::u32 util::disasm_interface::page_address_bits() const +{ + throw ("unimplemented page_address_bits called"); +} + +util::u32 util::disasm_interface::page2_address_bits() const +{ + throw ("unimplemented page2_address_bits called"); +} + +util::disasm_interface::offs_t util::disasm_interface::pc_linear_to_real(offs_t pc) const +{ + throw ("unimplemented pc_linear_to_real called"); +} + +util::disasm_interface::offs_t util::disasm_interface::pc_real_to_linear(offs_t pc) const +{ + throw ("unimplemented pc_real_to_linear called"); +} + +util::u8 util::disasm_interface::decrypt8(u8 value, offs_t pc, bool opcode) const +{ + throw ("unimplemented decrypt8 called"); +} + +util::u16 util::disasm_interface::decrypt16(u16 value, offs_t pc, bool opcode) const +{ + throw ("unimplemented decrypt16 called"); +} + +util::u32 util::disasm_interface::decrypt32(u32 value, offs_t pc, bool opcode) const +{ + throw ("unimplemented decrypt32 called"); +} + +util::u64 util::disasm_interface::decrypt64(u64 value, offs_t pc, bool opcode) const +{ + throw ("unimplemented decrypt64 called"); +} + diff --git a/src/lib/util/disasmintf.h b/src/lib/util/disasmintf.h new file mode 100644 index 00000000000..908bd762bdb --- /dev/null +++ b/src/lib/util/disasmintf.h @@ -0,0 +1,69 @@ +// license:BSD-3-Clause +// copyright-holders:Olivier Galibert +/*************************************************************************** + + disasmintf.h + + Generic disassembler interface. + +***************************************************************************/ + +#pragma once + +#ifndef MAME_UTIL_DISASMINTF_H +#define MAME_UTIL_DISASMINTF_H + +#include "coretmpl.h" + +namespace util { +// class implementing a disassembler +class disasm_interface +{ +public: + using offs_t = u32; + + // Disassembler constants for the return value + static constexpr u32 SUPPORTED = 0x80000000; // are disassembly flags supported? + static constexpr u32 STEP_OUT = 0x40000000; // this instruction should be the end of a step out sequence + static constexpr u32 STEP_OVER = 0x20000000; // this instruction should be stepped over by setting a breakpoint afterwards + static constexpr u32 OVERINSTMASK = 0x18000000; // number of extra instructions to skip when stepping over + static constexpr u32 OVERINSTSHIFT = 27; // bits to shift after masking to get the value + static constexpr u32 LENGTHMASK = 0x0000ffff; // the low 16-bits contain the actual length + + static inline u32 step_over_extra(u32 x) { + return x << OVERINSTSHIFT; + } + + class data_buffer { + public: + virtual ~data_buffer() = default; + virtual u8 r8 (offs_t pc) const = 0; + virtual u16 r16(offs_t pc) const = 0; + virtual u32 r32(offs_t pc) const = 0; + virtual u64 r64(offs_t pc) const = 0; + }; + + enum { + NONLINEAR_PC = 0x00000001, + PAGED = 0x00000002, + PAGED2LEVEL = 0x00000006, + INTERNAL_DECRYPTION = 0x00000008, + SPLIT_DECRYPTION = 0x00000018 + }; + + virtual u32 interface_flags() const; + virtual u32 page_address_bits() const; + virtual u32 page2_address_bits() const; + virtual offs_t pc_linear_to_real(offs_t pc) const; + virtual offs_t pc_real_to_linear(offs_t pc) const; + virtual u8 decrypt8 (u8 value, offs_t pc, bool opcode) const; + virtual u16 decrypt16(u16 value, offs_t pc, bool opcode) const; + virtual u32 decrypt32(u32 value, offs_t pc, bool opcode) const; + virtual u64 decrypt64(u64 value, offs_t pc, bool opcode) const; + + virtual u32 opcode_alignment() const = 0; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) = 0; +}; +} + +#endif diff --git a/src/mame/drivers/palm.cpp b/src/mame/drivers/palm.cpp index 2e9ffa1d340..f37ac1c9d37 100644 --- a/src/mame/drivers/palm.cpp +++ b/src/mame/drivers/palm.cpp @@ -58,7 +58,7 @@ public: required_ioport m_io_penb; required_ioport m_io_portd; - offs_t palm_dasm_override(device_t &device, std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, int options); + offs_t palm_dasm_override(std::ostream &stream, offs_t pc, const util::disasm_interface::data_buffer &opcodes, const util::disasm_interface::data_buffer ¶ms); }; diff --git a/src/mame/drivers/palm_dbg.hxx b/src/mame/drivers/palm_dbg.hxx index 44b952b2260..13d4a18e0ac 100644 --- a/src/mame/drivers/palm_dbg.hxx +++ b/src/mame/drivers/palm_dbg.hxx @@ -1162,18 +1162,16 @@ static const char *lookup_trap(uint16_t opcode) return nullptr; } -offs_t palm_state::palm_dasm_override(device_t &device, std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, int options) +offs_t palm_state::palm_dasm_override(std::ostream &stream, offs_t pc, const util::disasm_interface::data_buffer &opcodes, const util::disasm_interface::data_buffer ¶ms) { - uint16_t opcode; unsigned result = 0; const char *trap; - opcode = *((uint16_t *) oprom); - opcode = ((opcode >> 8) & 0x00ff) | ((opcode << 8) & 0xff00); + uint16_t opcode = opcodes.r16(pc); + if (opcode == 0x4E4F) { - uint16_t callnum = *((uint16_t *) (oprom + 2)); - callnum = ((callnum >> 8) & 0x00ff) | ((callnum << 8) & 0xff00); + uint16_t callnum = opcodes.r16(pc+2); trap = lookup_trap(callnum); result = 2; stream << (trap ? trap : "trap #$f"); diff --git a/src/mame/drivers/vgmplay.cpp b/src/mame/drivers/vgmplay.cpp index 0a5b117c45c..ed094c13dbe 100644 --- a/src/mame/drivers/vgmplay.cpp +++ b/src/mame/drivers/vgmplay.cpp @@ -37,6 +37,16 @@ #define AS_IO16 1 #define MCFG_CPU_IO16_MAP MCFG_CPU_DATA_MAP +class vgmplay_disassembler : public util::disasm_interface +{ +public: + vgmplay_disassembler() = default; + virtual ~vgmplay_disassembler() = default; + + virtual uint32_t opcode_alignment() const override; + virtual offs_t disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) override; +}; + class vgmplay_device : public cpu_device { public: @@ -90,9 +100,7 @@ public: virtual void state_export(const device_state_entry &entry) override; virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; - virtual uint32_t disasm_min_opcode_bytes() const override; - virtual uint32_t disasm_max_opcode_bytes() const override; - virtual offs_t disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual util::disasm_interface *create_disassembler() override; READ8_MEMBER(segapcm_rom_r); READ8_MEMBER(ymf271_rom_r); @@ -580,104 +588,104 @@ void vgmplay_device::state_string_export(const device_state_entry &entry, std::s { } -uint32_t vgmplay_device::disasm_min_opcode_bytes() const +util::disasm_interface *vgmplay_device::create_disassembler() { - return 1; + return new vgmplay_disassembler; } -uint32_t vgmplay_device::disasm_max_opcode_bytes() const +uint32_t vgmplay_disassembler::opcode_alignment() const { - return 9; + return 1; } -offs_t vgmplay_device::disasm_disassemble(std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) +offs_t vgmplay_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms) { - switch(oprom[0]) { + switch(opcodes.r8(pc)) { case 0x4f: - util::stream_format(stream, "psg r06 = %02x", oprom[1]); - return 2 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "psg r06 = %02x", opcodes.r8(pc+1)); + return 2 | SUPPORTED; case 0x50: - util::stream_format(stream, "psg write %02x", oprom[1]); - return 2 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "psg write %02x", opcodes.r8(pc+1)); + return 2 | SUPPORTED; case 0x51: - util::stream_format(stream, "ym2413 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ym2413 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0x52: - util::stream_format(stream, "ym2612.0 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ym2612.0 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0x53: - util::stream_format(stream, "ym2612.1 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ym2612.1 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0x54: - util::stream_format(stream, "ym2151 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ym2151 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0x55: - util::stream_format(stream, "ym2203a r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ym2203a r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0x56: - util::stream_format(stream, "ym2608.0 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ym2608.0 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0x57: - util::stream_format(stream, "ym2608.1 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ym2608.1 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0x58: - util::stream_format(stream, "ym2610.0 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ym2610.0 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0x59: - util::stream_format(stream, "ym2610.1 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ym2610.1 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0x5a: - util::stream_format(stream, "ym3812 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ym3812 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0x5b: - util::stream_format(stream, "ym3526 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ym3526 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0x5c: - util::stream_format(stream, "y8950 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "y8950 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0x5d: - util::stream_format(stream, "ymz280b r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ymz280b r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0x5e: - util::stream_format(stream, "ymf262.0 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ymf262.0 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0x5f: - util::stream_format(stream, "ymf262.1 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ymf262.1 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0x61: { - uint32_t duration = oprom[1] | (oprom[2] << 8); + uint32_t duration = opcodes.r8(pc+1) | (opcodes.r8(pc+2) << 8); util::stream_format(stream, "wait %d", duration); - return 3 | DASMFLAG_SUPPORTED; + return 3 | SUPPORTED; } case 0x62: util::stream_format(stream, "wait 735"); - return 1 | DASMFLAG_SUPPORTED; + return 1 | SUPPORTED; case 0x63: util::stream_format(stream, "wait 882"); - return 1 | DASMFLAG_SUPPORTED; + return 1 | SUPPORTED; case 0x66: util::stream_format(stream, "end"); - return 1 | DASMFLAG_SUPPORTED; + return 1 | SUPPORTED; case 0x67: { static const char *const basic_types[8] = { @@ -725,8 +733,8 @@ offs_t vgmplay_device::disasm_disassemble(std::ostream &stream, offs_t pc, const "es5503 ram" }; - uint8_t type = oprom[2]; - uint32_t size = oprom[3] | (oprom[4] << 8) | (oprom[5] << 16) | (oprom[6] << 24); + uint8_t type = opcodes.r8(pc+2); + uint32_t size = opcodes.r8(pc+3) | (opcodes.r8(pc+4) << 8) | (opcodes.r8(pc+5) << 16) | (opcodes.r8(pc+6) << 24); if(type < 0x8) util::stream_format(stream, "data-block %x, %s", size, basic_types[type]); else if(type < 0x40) @@ -736,7 +744,7 @@ offs_t vgmplay_device::disasm_disassemble(std::ostream &stream, offs_t pc, const else if(type < 0x7f) util::stream_format(stream, "data-block %x comp., %02x", size, type & 0x3f); else if(type < 0x80) - util::stream_format(stream, "decomp-table %x, %02x/%02x", size, oprom[7], oprom[8]); + util::stream_format(stream, "decomp-table %x, %02x/%02x", size, opcodes.r8(pc+7), opcodes.r8(pc+8)); else if(type < 0x94) util::stream_format(stream, "data-block %x, %s", size, rom_types[type & 0x7f]); else if(type < 0xc0) @@ -749,135 +757,135 @@ offs_t vgmplay_device::disasm_disassemble(std::ostream &stream, offs_t pc, const util::stream_format(stream, "data-block %x, %s", size, ram2_types[type & 0x1f]); else util::stream_format(stream, "data-block %x, ram %02x", size, type); - return (7+size) | DASMFLAG_SUPPORTED; + return (7+size) | SUPPORTED; } case 0x70: case 0x71: case 0x72: case 0x73: case 0x74: case 0x75: case 0x76: case 0x77: case 0x78: case 0x79: case 0x7a: case 0x7b: case 0x7c: case 0x7d: case 0x7e: case 0x7f: - util::stream_format(stream, "wait %d", 1+(oprom[0] & 0x0f)); - return 1 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "wait %d", 1+(opcodes.r8(pc) & 0x0f)); + return 1 | SUPPORTED; case 0x80: util::stream_format(stream, "ym2612.0 r2a = rom++"); - return 1 | DASMFLAG_SUPPORTED; + return 1 | SUPPORTED; case 0x81: case 0x82: case 0x83: case 0x84: case 0x85: case 0x86: case 0x87: case 0x88: case 0x89: case 0x8a: case 0x8b: case 0x8c: case 0x8d: case 0x8e: case 0x8f: - util::stream_format(stream, "ym2612.0 r2a = rom++; wait %d", oprom[0] & 0xf); - return 1 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ym2612.0 r2a = rom++; wait %d", opcodes.r8(pc) & 0xf); + return 1 | SUPPORTED; case 0xa0: - util::stream_format(stream, "ay8910 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ay8910 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0xa5: - util::stream_format(stream, "ym2203b r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ym2203b r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0xb0: - util::stream_format(stream, "rf5c68 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "rf5c68 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0xb1: - util::stream_format(stream, "rf5c164 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "rf5c164 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0xb2: - util::stream_format(stream, "pwm r%x = %03x", oprom[1] >> 4, oprom[2] | ((oprom[1] & 0xf) << 8)); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "pwm r%x = %03x", opcodes.r8(pc+1) >> 4, opcodes.r8(pc+2) | ((opcodes.r8(pc+1) & 0xf) << 8)); + return 3 | SUPPORTED; case 0xb3: - util::stream_format(stream, "dmg r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "dmg r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0xb4: - util::stream_format(stream, "nesapu r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "nesapu r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0xb5: - util::stream_format(stream, "multipcm r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "multipcm r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0xb6: - util::stream_format(stream, "upd7759 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "upd7759 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0xb7: - util::stream_format(stream, "okim6258 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "okim6258 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0xb8: - util::stream_format(stream, "okim6295 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "okim6295 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0xb9: - util::stream_format(stream, "huc6280 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "huc6280 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0xba: - util::stream_format(stream, "k053260 r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "k053260 r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0xbb: - util::stream_format(stream, "pokey r%02x = %02x", oprom[1], oprom[2]); - return 3 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "pokey r%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2)); + return 3 | SUPPORTED; case 0xc0: - util::stream_format(stream, "segapcm %04x = %02x", oprom[1] | (oprom[2] << 8), oprom[3]); - return 4 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "segapcm %04x = %02x", opcodes.r8(pc+1) | (opcodes.r8(pc+2) << 8), opcodes.r8(pc+3)); + return 4 | SUPPORTED; case 0xc1: - util::stream_format(stream, "rf5c68 %04x = %02x", oprom[1] | (oprom[2] << 8), oprom[3]); - return 4 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "rf5c68 %04x = %02x", opcodes.r8(pc+1) | (opcodes.r8(pc+2) << 8), opcodes.r8(pc+3)); + return 4 | SUPPORTED; case 0xc2: - util::stream_format(stream, "rf5c163 %04x = %02x", oprom[1] | (oprom[2] << 8), oprom[3]); - return 4 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "rf5c163 %04x = %02x", opcodes.r8(pc+1) | (opcodes.r8(pc+2) << 8), opcodes.r8(pc+3)); + return 4 | SUPPORTED; case 0xc3: - util::stream_format(stream, "multipcm c%02x.off = %04x", oprom[1], oprom[2] | (oprom[3] << 8)); - return 4 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "multipcm c%02x.off = %04x", opcodes.r8(pc+1), opcodes.r8(pc+2) | (opcodes.r8(pc+3) << 8)); + return 4 | SUPPORTED; case 0xc4: - util::stream_format(stream, "qsound %02x = %04x", oprom[3], oprom[2] | (oprom[1] << 8)); - return 4 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "qsound %02x = %04x", opcodes.r8(pc+3), opcodes.r8(pc+2) | (opcodes.r8(pc+1) << 8)); + return 4 | SUPPORTED; case 0xd0: - util::stream_format(stream, "ymf278b r%02x.%02x = %02x", oprom[1], oprom[2], oprom[3]); - return 4 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ymf278b r%02x.%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2), opcodes.r8(pc+3)); + return 4 | SUPPORTED; case 0xd1: - util::stream_format(stream, "ymf271 r%02x.%02x = %02x", oprom[1], oprom[2], oprom[3]); - return 4 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "ymf271 r%02x.%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2), opcodes.r8(pc+3)); + return 4 | SUPPORTED; case 0xd2: - util::stream_format(stream, "scc1 r%02x.%02x = %02x", oprom[1], oprom[2], oprom[3]); - return 4 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "scc1 r%02x.%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2), opcodes.r8(pc+3)); + return 4 | SUPPORTED; case 0xd3: - util::stream_format(stream, "k054539 r%02x.%02x = %02x", oprom[1], oprom[2], oprom[3]); - return 4 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "k054539 r%02x.%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2), opcodes.r8(pc+3)); + return 4 | SUPPORTED; case 0xd4: - util::stream_format(stream, "c140 r%02x.%02x = %02x", oprom[1], oprom[2], oprom[3]); - return 4 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "c140 r%02x.%02x = %02x", opcodes.r8(pc+1), opcodes.r8(pc+2), opcodes.r8(pc+3)); + return 4 | SUPPORTED; case 0xe0: { - uint32_t off = oprom[1] | (oprom[2] << 8) | (oprom[3] << 16) | (oprom[4] << 24); + uint32_t off = opcodes.r8(pc+1) | (opcodes.r8(pc+2) << 8) | (opcodes.r8(pc+3) << 16) | (opcodes.r8(pc+4) << 24); util::stream_format(stream, "ym2612 offset = %x", off); - return 5 | DASMFLAG_SUPPORTED; + return 5 | SUPPORTED; } case 0xe1: { - uint16_t addr = (oprom[1] << 8) | oprom[2]; - uint16_t data = (oprom[3] << 8) | oprom[4]; + uint16_t addr = (opcodes.r8(pc+1) << 8) | opcodes.r8(pc+2); + uint16_t data = (opcodes.r8(pc+3) << 8) | opcodes.r8(pc+4); util::stream_format(stream, "c352 r%04x = %04x", addr, data); - return 5 | DASMFLAG_SUPPORTED; + return 5 | SUPPORTED; } default: - util::stream_format(stream, "?? %02x", oprom[0]); - return 1 | DASMFLAG_SUPPORTED; + util::stream_format(stream, "?? %02x", opcodes.r8(pc)); + return 1 | SUPPORTED; } } diff --git a/src/mame/etc/template_cpu.cpp b/src/mame/etc/template_cpu.cpp index 626e02171fb..a3094005e2c 100644 --- a/src/mame/etc/template_cpu.cpp +++ b/src/mame/etc/template_cpu.cpp @@ -123,7 +123,7 @@ void xxx_cpu_device::state_string_export(const device_state_entry &entry, std::s } -offs_t xxx_cpu_device::disasm_disassemble(char *buffer, offs_t pc, const uint32_t *oprom, const uint32_t *opram, uint32_t options) +offs_t xxx_cpu_device::disassemble(char *buffer, offs_t pc, const uint32_t *oprom, const uint32_t *opram, uint32_t options) { - return CPU_DISASSEMBLE_NAME(xxx)(this, buffer, pc, oprom, opram, options); + return CPU_DISASSEMBLE_NAME(xxx)(this, buffer, pc, opcodes, params, options); } diff --git a/src/mame/etc/template_cpu.h b/src/mame/etc/template_cpu.h index 300d18b0464..72a0c78f89e 100644 --- a/src/mame/etc/template_cpu.h +++ b/src/mame/etc/template_cpu.h @@ -45,9 +45,8 @@ protected: virtual void state_string_export(const device_state_entry &entry, std::string &str) const override; // device_disasm_interface overrides - virtual uint32_t disasm_min_opcode_bytes() const override { return 4; } - virtual uint32_t disasm_max_opcode_bytes() const override { return 4; } - virtual offs_t disasm_disassemble(char *buffer, offs_t pc, const uint8_t *oprom, const uint8_t *opram, uint32_t options) override; + virtual uint32_t opcode_alignment() const override { return 4; } + virtual offs_t disassemble(char *buffer, offs_t pc, const data_buffer &opcodes, const data_buffer ¶ms, uint32_t options) override; private: address_space_config m_program_config; diff --git a/src/mame/includes/coco.h b/src/mame/includes/coco.h index db443136174..698e5863d05 100644 --- a/src/mame/includes/coco.h +++ b/src/mame/includes/coco.h @@ -132,8 +132,8 @@ public: virtual address_space &cartridge_space() override; // disassembly override - static offs_t os9_dasm_override(device_t &device, std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, int options); - offs_t dasm_override(device_t &device, std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, int options); + static offs_t os9_dasm_override(std::ostream &stream, offs_t pc, const util::disasm_interface::data_buffer &opcodes, const util::disasm_interface::data_buffer ¶ms); + offs_t dasm_override(std::ostream &stream, offs_t pc, const util::disasm_interface::data_buffer &opcodes, const util::disasm_interface::data_buffer ¶ms); protected: // device-level overrides diff --git a/src/mame/includes/dgn_beta.h b/src/mame/includes/dgn_beta.h index 9e6d7f24c7c..cd7cdad4d92 100644 --- a/src/mame/includes/dgn_beta.h +++ b/src/mame/includes/dgn_beta.h @@ -230,7 +230,7 @@ public: void ScanInKeyboard(void); void dgn_beta_frame_interrupt (int data); - offs_t dgnbeta_dasm_override(device_t &device, std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, int options); + offs_t dgnbeta_dasm_override(std::ostream &stream, offs_t pc, const util::disasm_interface::data_buffer &opcodes, const util::disasm_interface::data_buffer ¶ms); private: void execute_beta_key_dump(int ref, const std::vector ¶ms); diff --git a/src/mame/includes/mac.h b/src/mame/includes/mac.h index 67428390589..6c3cb4f9e41 100644 --- a/src/mame/includes/mac.h +++ b/src/mame/includes/mac.h @@ -523,7 +523,7 @@ public: void mac_driver_init(model_t model); void mac_install_memory(offs_t memory_begin, offs_t memory_end, offs_t memory_size, void *memory_data, int is_rom, const char *bank); - offs_t mac_dasm_override(device_t &device, std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, int options); + offs_t mac_dasm_override(std::ostream &stream, offs_t pc, const util::disasm_interface::data_buffer &opcodes, const util::disasm_interface::data_buffer ¶ms); }; #endif /* MAC_H_ */ diff --git a/src/mame/machine/apollo_dbg.cpp b/src/mame/machine/apollo_dbg.cpp index 63b05d162c5..208a563b7c3 100644 --- a/src/mame/machine/apollo_dbg.cpp +++ b/src/mame/machine/apollo_dbg.cpp @@ -11,6 +11,7 @@ #define VERBOSE 1 #include "emu.h" +#include "debug/debugbuf.h" #include "includes/apollo.h" #include "cpu/m68000/m68kcpu.h" @@ -1034,11 +1035,10 @@ static const char* get_svc_call(m68000_base_device *m68k, int trap_no, return sb; } +// WTF? static const std::string &disassemble(m68000_base_device *m68k, offs_t pc, std::string& sb) { - uint8_t oprom[10]; - uint8_t opram[10]; - uint32_t options = 0; + debug_disasm_buffer buffer(*m68k); // remember bus error state uint32_t tmp_buserror_occurred = m68k->mmu_tmp_buserror_occurred; @@ -1047,25 +1047,9 @@ static const std::string &disassemble(m68000_base_device *m68k, offs_t pc, std:: m68k->mmu_tmp_buserror_occurred = 0; m68k->mmu_tmp_rw = 1; - int i; - for (i = 0; i < sizeof(oprom); i++) - { - oprom[i] = opram[i] = m68k->read8(pc + i); - if (m68k->mmu_tmp_buserror_occurred) - { - sb = string_format("- (apollo_disassemble failed at %08x)", pc + i); - - // restore previous bus error state - m68k->mmu_tmp_buserror_occurred = tmp_buserror_occurred; - m68k->mmu_tmp_buserror_address = tmp_buserror_address; - - return sb; - } - } - - std::ostringstream stream; - m68k->disassemble(stream, pc, oprom, opram, options); - sb = stream.str(); + offs_t next_pc, size; + u32 info; + buffer.disassemble(pc, sb, next_pc, size, info); // restore previous bus error state m68k->mmu_tmp_buserror_occurred = tmp_buserror_occurred; diff --git a/src/mame/machine/coco.cpp b/src/mame/machine/coco.cpp index 6de238dadbc..6750d1403c7 100644 --- a/src/mame/machine/coco.cpp +++ b/src/mame/machine/coco.cpp @@ -1399,16 +1399,16 @@ static const char *const os9syscalls[] = // os9_dasm_override //------------------------------------------------- -offs_t coco_state::os9_dasm_override(device_t &device, std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, int options) +offs_t coco_state::os9_dasm_override(std::ostream &stream, offs_t pc, const util::disasm_interface::data_buffer &opcodes, const util::disasm_interface::data_buffer ¶ms) { unsigned call; offs_t result = 0; // Microware OS-9 (on the CoCo) and a number of other 6x09 based systems used the SWI2 // instruction for syscalls. This checks for a SWI2 and looks up the syscall as appropriate - if ((oprom[0] == 0x10) && (oprom[1] == 0x3F)) + if ((opcodes.r8(pc) == 0x10) && (opcodes.r8(pc+1) == 0x3F)) { - call = oprom[2]; + call = opcodes.r8(pc+2); if ((call < ARRAY_LENGTH(os9syscalls)) && (os9syscalls[call] != nullptr)) { util::stream_format(stream, "OS9 %s", os9syscalls[call]); @@ -1419,7 +1419,7 @@ offs_t coco_state::os9_dasm_override(device_t &device, std::ostream &stream, off } -offs_t coco_state::dasm_override(device_t &device, std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, int options) +offs_t coco_state::dasm_override(std::ostream &stream, offs_t pc, const util::disasm_interface::data_buffer &opcodes, const util::disasm_interface::data_buffer ¶ms) { - return os9_dasm_override(device, stream, pc, oprom, opram, options); + return os9_dasm_override(stream, pc, opcodes, params); } diff --git a/src/mame/machine/deco222.cpp b/src/mame/machine/deco222.cpp index 50478cc48bc..5be4df0bb60 100644 --- a/src/mame/machine/deco222.cpp +++ b/src/mame/machine/deco222.cpp @@ -34,7 +34,20 @@ uint8_t deco_222_device::mi_decrypt::read_sync(uint16_t adr) return BITSWAP8(direct->read_byte(adr) ,7,5,6,4,3,2,1,0); } +util::disasm_interface *deco_222_device::create_disassembler() +{ + return new disassembler; +} + +u32 deco_222_device::disassembler::interface_flags() const +{ + return SPLIT_DECRYPTION; +} +u8 deco_222_device::disassembler::decrypt8(u8 value, offs_t pc, bool opcode) const +{ + return opcode ? BITSWAP8(value,7,5,6,4,3,2,1,0) : value; +} deco_c10707_device::deco_c10707_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) : m6502_device(mconfig, DECO_C10707, tag, owner, clock) @@ -57,3 +70,18 @@ uint8_t deco_c10707_device::mi_decrypt::read_sync(uint16_t adr) { return BITSWAP8(direct->read_byte(adr) ,7,5,6,4,3,2,1,0); } + +util::disasm_interface *deco_c10707_device::create_disassembler() +{ + return new disassembler; +} + +u32 deco_c10707_device::disassembler::interface_flags() const +{ + return SPLIT_DECRYPTION; +} + +u8 deco_c10707_device::disassembler::decrypt8(u8 value, offs_t pc, bool opcode) const +{ + return opcode ? BITSWAP8(value,7,5,6,4,3,2,1,0) : value; +} diff --git a/src/mame/machine/deco222.h b/src/mame/machine/deco222.h index c7bf940acac..a633aec519c 100644 --- a/src/mame/machine/deco222.h +++ b/src/mame/machine/deco222.h @@ -5,6 +5,7 @@ #pragma once +#include "cpu/m6502/m6502d.h" #include "cpu/m6502/m6502.h" class deco_222_device : public m6502_device { @@ -20,9 +21,17 @@ protected: virtual uint8_t read_sync(uint16_t adr) override; }; + class disassembler : public m6502_disassembler { + public: + disassembler() = default; + virtual ~disassembler() = default; + virtual u32 interface_flags() const override; + virtual u8 decrypt8(u8 value, offs_t pc, bool opcode) const override; + }; + virtual void device_start() override; virtual void device_reset() override; - + virtual util::disasm_interface *create_disassembler() override; }; @@ -40,9 +49,18 @@ protected: virtual uint8_t read_sync(uint16_t adr) override; }; + + class disassembler : public m6502_disassembler { + public: + disassembler() = default; + virtual ~disassembler() = default; + virtual u32 interface_flags() const override; + virtual u8 decrypt8(u8 value, offs_t pc, bool opcode) const override; + }; + virtual void device_start() override; virtual void device_reset() override; - + virtual util::disasm_interface *create_disassembler() override; }; diff --git a/src/mame/machine/decocpu6.cpp b/src/mame/machine/decocpu6.cpp index 3d855e2864d..9e068e73adb 100644 --- a/src/mame/machine/decocpu6.cpp +++ b/src/mame/machine/decocpu6.cpp @@ -35,3 +35,18 @@ uint8_t deco_cpu6_device::mi_decrypt::read_sync(uint16_t adr) else return direct->read_byte(adr); } + +util::disasm_interface *deco_cpu6_device::create_disassembler() +{ + return new disassembler; +} + +u32 deco_cpu6_device::disassembler::interface_flags() const +{ + return SPLIT_DECRYPTION; +} + +u8 deco_cpu6_device::disassembler::decrypt8(u8 value, offs_t pc, bool opcode) const +{ + return opcode && (pc & 1) ? BITSWAP8(value,6,4,7,5,3,2,1,0) : value; +} diff --git a/src/mame/machine/decocpu6.h b/src/mame/machine/decocpu6.h index 21e649ed5ac..a4c5002ab40 100644 --- a/src/mame/machine/decocpu6.h +++ b/src/mame/machine/decocpu6.h @@ -5,6 +5,7 @@ #pragma once +#include "cpu/m6502/m6502d.h" #include "cpu/m6502/m6502.h" class deco_cpu6_device : public m6502_device { @@ -17,10 +18,17 @@ protected: virtual ~mi_decrypt() {} virtual uint8_t read_sync(uint16_t adr) override; }; + class disassembler : public m6502_disassembler { + public: + disassembler() = default; + virtual ~disassembler() = default; + virtual u32 interface_flags() const override; + virtual u8 decrypt8(u8 value, offs_t pc, bool opcode) const override; + }; virtual void device_start() override; virtual void device_reset() override; - + virtual util::disasm_interface *create_disassembler() override; }; DECLARE_DEVICE_TYPE(DECO_CPU6, deco_cpu6_device) diff --git a/src/mame/machine/decocpu7.cpp b/src/mame/machine/decocpu7.cpp index 332cea3ac45..50144063bb4 100644 --- a/src/mame/machine/decocpu7.cpp +++ b/src/mame/machine/decocpu7.cpp @@ -40,3 +40,22 @@ void deco_cpu7_device::mi_decrypt::write(uint16_t adr, uint8_t val) program->write_byte(adr, val); had_written = true; } + +util::disasm_interface *deco_cpu7_device::create_disassembler() +{ + return new disassembler(static_cast(mintf)); +} + +deco_cpu7_device::disassembler::disassembler(mi_decrypt *mi) : mintf(mi) +{ +} + +u32 deco_cpu7_device::disassembler::interface_flags() const +{ + return SPLIT_DECRYPTION; +} + +u8 deco_cpu7_device::disassembler::decrypt8(u8 value, offs_t pc, bool opcode) const +{ + return opcode && mintf->had_written && ((pc & 0x104) == 0x104) ? BITSWAP8(value,6,5,3,4,2,7,1,0) : value; +} diff --git a/src/mame/machine/decocpu7.h b/src/mame/machine/decocpu7.h index 4f854816f21..404ed43c466 100644 --- a/src/mame/machine/decocpu7.h +++ b/src/mame/machine/decocpu7.h @@ -5,6 +5,7 @@ #pragma once +#include "cpu/m6502/m6502d.h" #include "cpu/m6502/m6502.h" class deco_cpu7_device : public m6502_device { @@ -21,9 +22,19 @@ protected: virtual void write(uint16_t adr, uint8_t val) override; }; + class disassembler : public m6502_disassembler { + public: + mi_decrypt *mintf; + + disassembler(mi_decrypt *m); + virtual ~disassembler() = default; + virtual u32 interface_flags() const override; + virtual u8 decrypt8(u8 value, offs_t pc, bool opcode) const override; + }; + virtual void device_start() override; virtual void device_reset() override; - + virtual util::disasm_interface *create_disassembler() override; }; DECLARE_DEVICE_TYPE(DECO_CPU7, deco_cpu7_device) diff --git a/src/mame/machine/dgn_beta.cpp b/src/mame/machine/dgn_beta.cpp index dab45919b06..e15f23ffe0f 100644 --- a/src/mame/machine/dgn_beta.cpp +++ b/src/mame/machine/dgn_beta.cpp @@ -946,9 +946,9 @@ void dgn_beta_state::machine_start() OS9 Syscalls for disassembly ****************************************************************************/ -offs_t dgn_beta_state::dgnbeta_dasm_override(device_t &device, std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, int options) +offs_t dgn_beta_state::dgnbeta_dasm_override(std::ostream &stream, offs_t pc, const util::disasm_interface::data_buffer &opcodes, const util::disasm_interface::data_buffer ¶ms) { - return coco_state::os9_dasm_override(device, stream, pc, oprom, opram, options); + return coco_state::os9_dasm_override(stream, pc, opcodes, params); } void dgn_beta_state::execute_beta_dat_log(int ref, const std::vector ¶ms) diff --git a/src/mame/machine/mac.cpp b/src/mame/machine/mac.cpp index 41b6546655a..57a9bed5901 100644 --- a/src/mame/machine/mac.cpp +++ b/src/mame/machine/mac.cpp @@ -3190,20 +3190,20 @@ const char *lookup_trap(uint16_t opcode) -offs_t mac_state::mac_dasm_override(device_t &device, std::ostream &stream, offs_t pc, const uint8_t *oprom, const uint8_t *opram, int options) +offs_t mac_state::mac_dasm_override(std::ostream &stream, offs_t pc, const util::disasm_interface::data_buffer &opcodes, const util::disasm_interface::data_buffer ¶ms) { uint16_t opcode; unsigned result = 0; const char *trap; - opcode = oprom[0]<<8 | oprom[1]; + opcode = opcodes.r16(pc); if ((opcode & 0xF000) == 0xA000) { trap = lookup_trap(opcode); if (trap != nullptr) { stream << trap; - result = 2; + result = 2 | util::disasm_interface::SUPPORTED; } } return result; diff --git a/src/tools/unidasm.cpp b/src/tools/unidasm.cpp index eafca32f14f..1f093df9416 100644 --- a/src/tools/unidasm.cpp +++ b/src/tools/unidasm.cpp @@ -9,41 +9,246 @@ ****************************************************************************/ #include "emu.h" -#include "cpu/sparc/sparcdasm.h" #include #include #include +#include "cpu/8x300/8x300dasm.h" +#include "cpu/adsp2100/2100dasm.h" +#include "cpu/alph8201/8201dasm.h" +#include "cpu/alto2/alto2dsm.h" +#include "cpu/am29000/am29dasm.h" +#include "cpu/amis2000/amis2000d.h" +#include "cpu/apexc/apexcdsm.h" +#include "cpu/arc/arcdasm.h" +#include "cpu/arcompact/arcompactdasm.h" +#include "cpu/arm/armdasm.h" +#include "cpu/arm7/arm7dasm.h" +#include "cpu/asap/asapdasm.h" +#include "cpu/avr8/avr8dasm.h" +#include "cpu/capricorn/capricorn_dasm.h" +#include "cpu/ccpu/ccpudasm.h" +#include "cpu/clipper/clipperd.h" +#include "cpu/cop400/cop410ds.h" +#include "cpu/cop400/cop420ds.h" +#include "cpu/cop400/cop424ds.h" +#include "cpu/cop400/cop444ds.h" +#include "cpu/cosmac/cosdasm.h" +#include "cpu/cp1610/1610dasm.h" +#include "cpu/cubeqcpu/cubedasm.h" +#include "cpu/dsp16/dsp16dis.h" +#include "cpu/dsp32/dsp32dis.h" +#include "cpu/dsp56k/dsp56dsm.h" +#include "cpu/e0c6200/e0c6200d.h" +#include "cpu/e132xs/32xsdasm.h" +#include "cpu/es5510/es5510d.h" +#include "cpu/esrip/esripdsm.h" +#include "cpu/f8/f8dasm.h" +#include "cpu/g65816/g65816ds.h" +#include "cpu/h6280/6280dasm.h" +#include "cpu/h8/h8d.h" +#include "cpu/h8/h8hd.h" +#include "cpu/h8/h8s2000d.h" +#include "cpu/h8/h8s2600d.h" +#include "cpu/hcd62121/hcd62121d.h" +#include "cpu/hd61700/hd61700d.h" +#include "cpu/hmcs40/hmcs40d.h" +#include "cpu/hphybrid/hphybrid_dasm.h" +#include "cpu/i386/i386dasm.h" +#include "cpu/i8008/8008dasm.h" +#include "cpu/i8085/8085dasm.h" +#include "cpu/i8089/i8089_dasm.h" +#include "cpu/i860/i860dis.h" +#include "cpu/i960/i960dis.h" +#include "cpu/ie15/ie15dasm.h" +#include "cpu/jaguar/jagdasm.h" +#include "cpu/lc8670/lc8670dsm.h" +#include "cpu/lh5801/5801dasm.h" +#include "cpu/lr35902/lr35902d.h" +#include "cpu/m37710/m7700ds.h" +#include "cpu/m6502/m4510d.h" +#include "cpu/m6502/m6502d.h" +#include "cpu/m6502/m6509d.h" +#include "cpu/m6502/m6510d.h" +#include "cpu/m6502/m65c02d.h" +#include "cpu/m6502/m65ce02d.h" +#include "cpu/m6502/m740d.h" +#include "cpu/m6800/6800dasm.h" +#include "cpu/m68000/m68kdasm.h" +#include "cpu/m6805/6805dasm.h" +#include "cpu/m6809/6x09dasm.h" +#include "cpu/mb86233/mb86233d.h" +#include "cpu/mb86235/mb86235d.h" +#include "cpu/mb88xx/mb88dasm.h" +#include "cpu/mc68hc11/hc11dasm.h" +#include "cpu/mcs40/mcs40dasm.h" +#include "cpu/mcs48/mcs48dsm.h" +#include "cpu/mcs51/mcs51dasm.h" +#include "cpu/mcs96/i8x9xd.h" +#include "cpu/mcs96/i8xc196d.h" +#include "cpu/melps4/melps4d.h" +#include "cpu/minx/minxd.h" +#include "cpu/mips/mips3dsm.h" +#include "cpu/mips/r3kdasm.h" +#include "cpu/mn10200/mn102dis.h" +#include "cpu/nanoprocessor/nanoprocessor_dasm.h" +#include "cpu/nec/necdasm.h" +#include "cpu/patinhofeio/patinho_feio_dasm.h" +#include "cpu/pdp1/pdp1dasm.h" +#include "cpu/pdp1/tx0dasm.h" +#include "cpu/pdp8/pdp8dasm.h" +#include "cpu/pic16c5x/16c5xdsm.h" +#include "cpu/pic16c62x/16c62xdsm.h" +#include "cpu/powerpc/ppc_dasm.h" +#include "cpu/pps4/pps4dasm.h" +#include "cpu/psx/psxdasm.h" +#include "cpu/rsp/rsp_dasm.h" +#include "cpu/s2650/2650dasm.h" +#include "cpu/saturn/saturnds.h" +#include "cpu/sc61860/scdasm.h" +#include "cpu/scmp/scmpdasm.h" +#include "cpu/score/scoredsm.h" +#include "cpu/scudsp/scudspdasm.h" +#include "cpu/se3208/se3208dis.h" +#include "cpu/sh/sh_dasm.h" +#include "cpu/sharc/sharcdsm.h" +#include "cpu/sm510/sm510d.h" +#include "cpu/sm8500/sm8500d.h" +#include "cpu/sparc/sparcdasm.h" +#include "cpu/spc700/spc700ds.h" +#include "cpu/ssem/ssemdasm.h" +#include "cpu/ssp1601/ssp1601d.h" +#include "cpu/superfx/sfx_dasm.h" +#include "cpu/t11/t11dasm.h" +#include "cpu/tlcs870/tlcs870d.h" +#include "cpu/tlcs90/tlcs90d.h" +#include "cpu/tlcs900/dasm900.h" +#include "cpu/tms1000/tms1k_dasm.h" +#include "cpu/tms32010/32010dsm.h" +#include "cpu/tms32025/32025dsm.h" +#include "cpu/tms32031/dis32031.h" +#include "cpu/tms32051/dis32051.h" +#include "cpu/tms32082/dis_mp.h" +#include "cpu/tms32082/dis_pp.h" +#include "cpu/tms34010/34010dsm.h" +#include "cpu/tms57002/57002dsm.h" +#include "cpu/tms7000/7000dasm.h" +#include "cpu/tms9900/9900dasm.h" +#include "cpu/tms9900/tms99com.h" +#include "cpu/ucom4/ucom4d.h" +#include "cpu/unsp/unspdasm.h" +#include "cpu/upd7725/dasm7725.h" +#include "cpu/upd7810/upd7810_dasm.h" +#include "cpu/v60/v60d.h" +#include "cpu/v810/v810dasm.h" +#include "cpu/z180/z180dasm.h" +#include "cpu/z8/z8dasm.h" +#include "cpu/z80/z80dasm.h" +#include "cpu/z8000/8000dasm.h" + +// Configuration classes -enum display_type +// Selected through dasm name +struct arm7_unidasm_t : public arm7_disassembler::config { - _8bit, - _8bitx, - _16be, - _16le, - _24be, - _24le, - _32be, - _32le, - _40be, - _40le, - _48be, - _48le, - _56be, - _56le, - _64be, - _64le -}; + bool t_flag; + arm7_unidasm_t() { t_flag = false; } + virtual ~arm7_unidasm_t() override = default; + virtual bool get_t_flag() const override { return t_flag; } +} arm7_unidasm; + +// Configuration missing +struct g65816_unidasm_t : g65816_disassembler::config +{ + bool m_flag; + bool x_flag; + + g65816_unidasm_t() { m_flag = false; x_flag = false; } + virtual ~g65816_unidasm_t() override = default; + virtual bool get_m_flag() const override { return m_flag; } + virtual bool get_x_flag() const override { return x_flag; } +} g65816_unidasm; + +// Configuration missing +struct m740_unidasm_t : m740_disassembler::config +{ + u32 inst_state_base; + m740_unidasm_t() { inst_state_base = 0; } + virtual ~m740_unidasm_t() override = default; + virtual u32 get_state_base() const override { return inst_state_base; } +} m740_unidasm; + +// Configuration missing +struct m7700_unidasm_t : m7700_disassembler::config +{ + bool m_flag; + bool x_flag; + + m7700_unidasm_t() { m_flag = false; x_flag = false; } + virtual ~m7700_unidasm_t() override = default; + virtual bool get_m_flag() const override { return m_flag; } + virtual bool get_x_flag() const override { return x_flag; } +} m7700_unidasm; + + +// Configuration missing +struct s2650_unidasm_t : s2650_disassembler::config +{ + bool z80_mnemonics; + s2650_unidasm_t() { z80_mnemonics = false; } + virtual ~s2650_unidasm_t() override = default; + virtual bool get_z80_mnemonics_mode() const override { return z80_mnemonics; } +} s2650_unidasm; + +// Configuration missing +struct saturn_unidasm_t : saturn_disassembler::config +{ + bool nonstandard_mnemonics; + saturn_unidasm_t() { nonstandard_mnemonics = false; } + virtual ~saturn_unidasm_t() override = default; + virtual bool get_nonstandard_mnemonics_mode() const override { return nonstandard_mnemonics; } +} saturn_unidasm; +// Configuration missing +struct superfx_unidasm_t : superfx_disassembler::config +{ + u16 sfr; + superfx_unidasm_t() { sfr = superfx_disassembler::SUPERFX_SFR_ALT0; } + virtual ~superfx_unidasm_t() override = default; + virtual u16 get_alt() const override { return sfr; } +} superfx_unidasm; + +// Selected through dasm name +struct i386_unidasm_t : i386_disassembler::config +{ + int mode; + i386_unidasm_t() { mode = 32; } + virtual ~i386_unidasm_t() override = default; + virtual int get_mode() const override { return mode; } +} i386_unidasm; + +// Configuration missing +struct z8000_unidasm_t : z8000_disassembler::config +{ + bool segmented_mode; + z8000_unidasm_t() { segmented_mode = false; } + virtual ~z8000_unidasm_t() override = default; + virtual bool get_segmented_mode() const override { return segmented_mode; } +} z8000_unidasm; + + + + +enum endianness { le, be }; struct dasm_table_entry { const char * name; - display_type display; - int8_t pcshift; - cpu_disassemble_func func; + endianness endian; + int8_t pcshift; + std::function alloc; }; @@ -51,363 +256,575 @@ struct options { const char * filename; offs_t basepc; - uint8_t norawbytes; - uint8_t lower; - uint8_t upper; - uint8_t flipped; + uint8_t norawbytes; + uint8_t lower; + uint8_t upper; + uint8_t flipped; int mode; const dasm_table_entry *dasm; - uint32_t skip; - uint32_t count; + uint32_t skip; + uint32_t count; }; +static const dasm_table_entry dasm_table[] = +{ + { "8x300", be, 0, []() -> util::disasm_interface * { return new n8x300_disassembler; } }, + { "adsp21xx", le, -2, []() -> util::disasm_interface * { return new adsp21xx_disassembler; } }, + { "alpha8201", le, 0, []() -> util::disasm_interface * { return new alpha8201_disassembler; } }, + { "alto2", be, -2, []() -> util::disasm_interface * { return new alto2_disassembler; } }, + { "am29000", be, 0, []() -> util::disasm_interface * { return new am29000_disassembler; } }, + { "amis2000", le, 0, []() -> util::disasm_interface * { return new amis2000_disassembler; } }, + { "apexc", be, 0, []() -> util::disasm_interface * { return new apexc_disassembler; } }, + { "arc", be, 0, []() -> util::disasm_interface * { return new arc_disassembler; } }, + { "arcompact", le, 0, []() -> util::disasm_interface * { return new arcompact_disassembler; } }, + { "arm", le, 0, []() -> util::disasm_interface * { return new arm_disassembler; } }, + { "arm_be", be, 0, []() -> util::disasm_interface * { return new arm_disassembler; } }, + { "arm7", le, 0, []() -> util::disasm_interface * { arm7_unidasm.t_flag = false; return new arm7_disassembler(&arm7_unidasm); } }, + { "arm7_be", be, 0, []() -> util::disasm_interface * { arm7_unidasm.t_flag = false; return new arm7_disassembler(&arm7_unidasm); } }, + { "arm7thumb", le, 0, []() -> util::disasm_interface * { arm7_unidasm.t_flag = true; return new arm7_disassembler(&arm7_unidasm); } }, + { "arm7thumbb", be, 0, []() -> util::disasm_interface * { arm7_unidasm.t_flag = true; return new arm7_disassembler(&arm7_unidasm); } }, + { "asap", le, 0, []() -> util::disasm_interface * { return new asap_disassembler; } }, + { "avr8", le, 0, []() -> util::disasm_interface * { return new avr8_disassembler; } }, + { "capricorn", le, 0, []() -> util::disasm_interface * { return new capricorn_disassembler; } }, + { "ccpu", le, 0, []() -> util::disasm_interface * { return new ccpu_disassembler; } }, + { "cdp1801", le, 0, []() -> util::disasm_interface * { return new cosmac_disassembler(cosmac_disassembler::TYPE_1801); } }, + { "cdp1802", le, 0, []() -> util::disasm_interface * { return new cosmac_disassembler(cosmac_disassembler::TYPE_1802); } }, + { "clipper", le, 0, []() -> util::disasm_interface * { return new clipper_disassembler; } }, + { "coldfire", be, 0, []() -> util::disasm_interface * { return new m68k_disassembler(m68k_disassembler::TYPE_COLDFIRE); } }, + { "cop410", le, 0, []() -> util::disasm_interface * { return new cop410_disassembler; } }, + { "cop420", le, 0, []() -> util::disasm_interface * { return new cop420_disassembler; } }, + { "cop444", le, 0, []() -> util::disasm_interface * { return new cop444_disassembler; } }, + { "cop424", le, 0, []() -> util::disasm_interface * { return new cop424_disassembler; } }, + { "cp1610", be, -1, []() -> util::disasm_interface * { return new cp1610_disassembler; } }, + { "cquestlin", be, -3, []() -> util::disasm_interface * { return new cquestlin_disassembler; } }, + { "cquestrot", be, -3, []() -> util::disasm_interface * { return new cquestrot_disassembler; } }, + { "cquestsnd", be, -3, []() -> util::disasm_interface * { return new cquestsnd_disassembler; } }, + { "ds5002fp", le, 0, []() -> util::disasm_interface * { return new ds5002fp_disassembler; } }, + { "dsp16a", le, -1, []() -> util::disasm_interface * { return new dsp16a_disassembler; } }, + { "dsp32c", le, 0, []() -> util::disasm_interface * { return new dsp32c_disassembler; } }, + { "dsp56k", le, -1, []() -> util::disasm_interface * { return new dsp56k_disassembler; } }, + { "e0c6200", be, -1, []() -> util::disasm_interface * { return new e0c6200_disassembler; } }, +// { "es5510", be, 0, []() -> util::disasm_interface * { return new es5510_disassembler; } }, // Currently does nothing + { "esrip", be, 0, []() -> util::disasm_interface * { return new esrip_disassembler; } }, + { "f8", le, 0, []() -> util::disasm_interface * { return new f8_disassembler; } }, + { "g65816", le, 0, []() -> util::disasm_interface * { return new g65816_disassembler(&g65816_unidasm); } }, + { "h6280", le, 0, []() -> util::disasm_interface * { return new h6280_disassembler; } }, + { "h8", be, 0, []() -> util::disasm_interface * { return new h8_disassembler; } }, + { "h8h", be, 0, []() -> util::disasm_interface * { return new h8h_disassembler; } }, + { "h8s2000", be, 0, []() -> util::disasm_interface * { return new h8s2000_disassembler; } }, + { "h8s2600", be, 0, []() -> util::disasm_interface * { return new h8s2600_disassembler; } }, + { "hc11", le, 0, []() -> util::disasm_interface * { return new hc11_disassembler; } }, + { "hcd62121", le, 0, []() -> util::disasm_interface * { return new hcd62121_disassembler; } }, + { "hd61700", le, 0, []() -> util::disasm_interface * { return new hd61700_disassembler; } }, + { "hd6301", le, 0, []() -> util::disasm_interface * { return new m680x_disassembler(6301); } }, + { "hd6309", le, 0, []() -> util::disasm_interface * { return new hd6309_disassembler; } }, + { "hd63701", le, 0, []() -> util::disasm_interface * { return new m680x_disassembler(63701); } }, + { "hmcs40", le, -1, []() -> util::disasm_interface * { return new hmcs40_disassembler; } }, + { "hp_hybrid", be, -1, []() -> util::disasm_interface * { return new hp_hybrid_disassembler; } }, + { "hp_5061_3001", be, -1, []() -> util::disasm_interface * { return new hp_5061_3001_disassembler; } }, + { "hyperstone", be, 0, []() -> util::disasm_interface * { return new hyperstone_disassembler; } }, + { "i4004", le, 0, []() -> util::disasm_interface * { return new i4004_disassembler; } }, + { "i4040", le, 0, []() -> util::disasm_interface * { return new i4040_disassembler; } }, + { "i8008", le, 0, []() -> util::disasm_interface * { return new i8008_disassembler; } }, + { "i8051", le, 0, []() -> util::disasm_interface * { return new i8051_disassembler; } }, + { "i8052", le, 0, []() -> util::disasm_interface * { return new i8052_disassembler; } }, + { "i8085", le, 0, []() -> util::disasm_interface * { return new i8085_disassembler; } }, + { "i8089", le, 0, []() -> util::disasm_interface * { return new i8089_disassembler; } }, + { "i80c51", le, 0, []() -> util::disasm_interface * { return new i80c51_disassembler; } }, + { "i80c52", le, 0, []() -> util::disasm_interface * { return new i80c52_disassembler; } }, + { "i860", le, 0, []() -> util::disasm_interface * { return new i860_disassembler; } }, + { "i8x9x", le, 0, []() -> util::disasm_interface * { return new i8x9x_disassembler; } }, + { "i8xc196", le, 0, []() -> util::disasm_interface * { return new i8xc196_disassembler; } }, + { "i960", le, 0, []() -> util::disasm_interface * { return new i960_disassembler; } }, + { "ie15", le, 0, []() -> util::disasm_interface * { return new ie15_disassembler; } }, + { "jaguardsp", be, 0, []() -> util::disasm_interface * { return new jaguar_disassembler(jaguar_disassembler::JAGUAR_VARIANT_DSP); } }, + { "jaguargpu", be, 0, []() -> util::disasm_interface * { return new jaguar_disassembler(jaguar_disassembler::JAGUAR_VARIANT_GPU); } }, + { "konami", le, 0, []() -> util::disasm_interface * { return new konami_disassembler; } }, + { "lc8670", be, 0, []() -> util::disasm_interface * { return new lc8670_disassembler; } }, + { "lh5801", le, 0, []() -> util::disasm_interface * { return new lh5801_disassembler; } }, + { "lr35902", le, 0, []() -> util::disasm_interface * { return new lr35902_disassembler; } }, + { "m146805", le, 0, []() -> util::disasm_interface * { return new m146805_disassembler; } }, + { "m37710", le, 0, []() -> util::disasm_interface * { return new m7700_disassembler(&m7700_unidasm); } }, + { "m4510", le, 0, []() -> util::disasm_interface * { return new m4510_disassembler; } }, + { "m58846", le, -1, []() -> util::disasm_interface * { return new melps4_disassembler; } }, + { "m6502", le, 0, []() -> util::disasm_interface * { return new m6502_disassembler; } }, + { "m6509", le, 0, []() -> util::disasm_interface * { return new m6509_disassembler; } }, + { "m6510", le, 0, []() -> util::disasm_interface * { return new m6510_disassembler; } }, + { "m65c02", le, 0, []() -> util::disasm_interface * { return new m65c02_disassembler; } }, + { "m65ce02", le, 0, []() -> util::disasm_interface * { return new m65ce02_disassembler; } }, + { "m6800", le, 0, []() -> util::disasm_interface * { return new m680x_disassembler(6800); } }, + { "m68000", be, 0, []() -> util::disasm_interface * { return new m68k_disassembler(m68k_disassembler::TYPE_68000); } }, + { "m68008", be, 0, []() -> util::disasm_interface * { return new m68k_disassembler(m68k_disassembler::TYPE_68008); } }, + { "m6801", le, 0, []() -> util::disasm_interface * { return new m680x_disassembler(6801); } }, + { "m68010", be, 0, []() -> util::disasm_interface * { return new m68k_disassembler(m68k_disassembler::TYPE_68010); } }, + { "m6802", le, 0, []() -> util::disasm_interface * { return new m680x_disassembler(6802); } }, + { "m68020", be, 0, []() -> util::disasm_interface * { return new m68k_disassembler(m68k_disassembler::TYPE_68020); } }, + { "m6803", le, 0, []() -> util::disasm_interface * { return new m680x_disassembler(6803); } }, + { "m68030", be, 0, []() -> util::disasm_interface * { return new m68k_disassembler(m68k_disassembler::TYPE_68030); } }, + { "m68040", be, 0, []() -> util::disasm_interface * { return new m68k_disassembler(m68k_disassembler::TYPE_68040); } }, + { "m6805", le, 0, []() -> util::disasm_interface * { return new m6805_disassembler; } }, + { "m6808", le, 0, []() -> util::disasm_interface * { return new m680x_disassembler(6808); } }, + { "m6809", le, 0, []() -> util::disasm_interface * { return new m6809_disassembler; } }, + { "m68340", be, 0, []() -> util::disasm_interface * { return new m68k_disassembler(m68k_disassembler::TYPE_68340); } }, + { "m68hc05", le, 0, []() -> util::disasm_interface * { return new m68hc05_disassembler; } }, + { "m740", le, 0, []() -> util::disasm_interface * { return new m740_disassembler(&m740_unidasm); } }, + { "mb86233", le, -2, []() -> util::disasm_interface * { return new mb86233_disassembler; } }, + { "mb86235", le, -3, []() -> util::disasm_interface * { return new mb86235_disassembler; } }, + { "mb88", le, 0, []() -> util::disasm_interface * { return new mb88_disassembler; } }, + { "mcs48", le, 0, []() -> util::disasm_interface * { return new mcs48_disassembler(false); } }, + { "minx", le, 0, []() -> util::disasm_interface * { return new minx_disassembler; } }, + { "mips3be", be, 0, []() -> util::disasm_interface * { return new mips3_disassembler; } }, + { "mips3le", le, 0, []() -> util::disasm_interface * { return new mips3_disassembler; } }, + { "mn10200", le, 0, []() -> util::disasm_interface * { return new mn10200_disassembler; } }, + { "nanoprocessor", le, 0, []() -> util::disasm_interface * { return new hp_nanoprocessor_disassembler; } }, + { "nec", le, 0, []() -> util::disasm_interface * { return new nec_disassembler; } }, + { "nsc8105", le, 0, []() -> util::disasm_interface * { return new m680x_disassembler(8105); } }, + { "patinho_feio", le, 0, []() -> util::disasm_interface * { return new patinho_feio_disassembler; } }, + { "pdp1", be, 0, []() -> util::disasm_interface * { return new pdp1_disassembler; } }, + { "pdp8", be, 0, []() -> util::disasm_interface * { return new pdp8_disassembler; } }, + { "pic16c5x", le, -1, []() -> util::disasm_interface * { return new pic16c5x_disassembler; } }, + { "pic16c62x", le, -1, []() -> util::disasm_interface * { return new pic16c62x_disassembler; } }, + { "powerpc", be, 0, []() -> util::disasm_interface * { return new powerpc_disassembler; } }, + { "pps4", le, 0, []() -> util::disasm_interface * { return new pps4_disassembler; } }, + { "psxcpu", le, 0, []() -> util::disasm_interface * { return new psxcpu_disassembler; } }, + { "r3000be", be, 0, []() -> util::disasm_interface * { return new r3000_disassembler; } }, + { "r3000le", le, 0, []() -> util::disasm_interface * { return new r3000_disassembler; } }, + { "rsp", le, 0, []() -> util::disasm_interface * { return new rsp_disassembler; } }, + { "s2650", le, 0, []() -> util::disasm_interface * { return new s2650_disassembler(&s2650_unidasm); } }, + { "saturn", le, 0, []() -> util::disasm_interface * { return new saturn_disassembler(&saturn_unidasm); } }, + { "sc61860", le, 0, []() -> util::disasm_interface * { return new sc61860_disassembler; } }, + { "scmp", le, 0, []() -> util::disasm_interface * { return new scmp_disassembler; } }, + { "scudsp", be, 0, []() -> util::disasm_interface * { return new scudsp_disassembler; } }, + { "se3208", le, 0, []() -> util::disasm_interface * { return new se3208_disassembler; } }, + { "sh2", be, 0, []() -> util::disasm_interface * { return new sh_disassembler(false); } }, + { "sh4", le, 0, []() -> util::disasm_interface * { return new sh_disassembler(true); } }, + { "sh4be", be, 0, []() -> util::disasm_interface * { return new sh_disassembler(true); } }, + { "sharc", le, -2, []() -> util::disasm_interface * { return new sharc_disassembler; } }, + { "sm500", le, 0, []() -> util::disasm_interface * { return new sm500_disassembler; } }, + { "sm510", le, 0, []() -> util::disasm_interface * { return new sm510_disassembler; } }, + { "sm511", le, 0, []() -> util::disasm_interface * { return new sm511_disassembler; } }, + { "sm590", le, 0, []() -> util::disasm_interface * { return new sm590_disassembler; } }, + { "sm5a", le, 0, []() -> util::disasm_interface * { return new sm5a_disassembler; } }, + { "sm8500", le, 0, []() -> util::disasm_interface * { return new sm8500_disassembler; } }, + { "sparcv7", be, 0, []() -> util::disasm_interface * { return new sparc_disassembler(nullptr, 7); } }, + { "sparcv8", be, 0, []() -> util::disasm_interface * { return new sparc_disassembler(nullptr, 8); } }, + { "sparcv9", be, 0, []() -> util::disasm_interface * { return new sparc_disassembler(nullptr, 9); } }, + { "sparcv9vis1", be, 0, []() -> util::disasm_interface * { return new sparc_disassembler(nullptr, 9, sparc_disassembler::vis_1); } }, + { "sparcv9vis2", be, 0, []() -> util::disasm_interface * { return new sparc_disassembler(nullptr, 9, sparc_disassembler::vis_2); } }, + { "sparcv9vis2p", be, 0, []() -> util::disasm_interface * { return new sparc_disassembler(nullptr, 9, sparc_disassembler::vis_2p); } }, + { "sparcv9vis3", be, 0, []() -> util::disasm_interface * { return new sparc_disassembler(nullptr, 9, sparc_disassembler::vis_3); } }, + { "sparcv9vis3b", be, 0, []() -> util::disasm_interface * { return new sparc_disassembler(nullptr, 9, sparc_disassembler::vis_3b); } }, + { "spc700", le, 0, []() -> util::disasm_interface * { return new spc700_disassembler; } }, + { "ssem", le, 0, []() -> util::disasm_interface * { return new ssem_disassembler; } }, + { "ssp1601", be, -1, []() -> util::disasm_interface * { return new ssp1601_disassembler; } }, + { "superfx", le, 0, []() -> util::disasm_interface * { return new superfx_disassembler(&superfx_unidasm); } }, + { "t11", le, 0, []() -> util::disasm_interface * { return new t11_disassembler; } }, + { "tlcs870", le, 0, []() -> util::disasm_interface * { return new tlcs870_disassembler; } }, + { "tlcs90", le, 0, []() -> util::disasm_interface * { return new tlcs90_disassembler; } }, + { "tlcs900", le, 0, []() -> util::disasm_interface * { return new tlcs900_disassembler; } }, + { "tms0980", be, 0, []() -> util::disasm_interface * { return new tms0980_disassembler; } }, + { "tms1000", le, 0, []() -> util::disasm_interface * { return new tms1000_disassembler; } }, + { "tms1100", le, 0, []() -> util::disasm_interface * { return new tms1100_disassembler; } }, + { "tms32010", be, -1, []() -> util::disasm_interface * { return new tms32010_disassembler; } }, + { "tms32025", be, -1, []() -> util::disasm_interface * { return new tms32025_disassembler; } }, + { "tms32031", le, -2, []() -> util::disasm_interface * { return new tms32031_disassembler; } }, + { "tms32051", le, -1, []() -> util::disasm_interface * { return new tms32051_disassembler; } }, + { "tms32082_mp", be, 0, []() -> util::disasm_interface * { return new tms32082_mp_disassembler; } }, + { "tms32082_pp", be, 0, []() -> util::disasm_interface * { return new tms32082_pp_disassembler; } }, + { "tms34010", le, 3, []() -> util::disasm_interface * { return new tms34010_disassembler(false); } }, + { "tms34020", le, 3, []() -> util::disasm_interface * { return new tms34010_disassembler(true); } }, + { "tms57002", le, -2, []() -> util::disasm_interface * { return new tms57002_disassembler; } }, + { "tms7000", le, 0, []() -> util::disasm_interface * { return new tms7000_disassembler; } }, + { "tms9900", be, 0, []() -> util::disasm_interface * { return new tms9900_disassembler(TMS9900_ID); } }, + { "tms9980", le, 0, []() -> util::disasm_interface * { return new tms9900_disassembler(TMS9980_ID); } }, + { "tms9995", le, 0, []() -> util::disasm_interface * { return new tms9900_disassembler(TMS9995_ID); } }, + { "tp0320", be, 0, []() -> util::disasm_interface * { return new tp0320_disassembler; } }, + { "tx0_64kw", be, -2, []() -> util::disasm_interface * { return new tx0_64kw_disassembler; } }, + { "tx0_8kw", be, -2, []() -> util::disasm_interface * { return new tx0_8kw_disassembler; } }, + { "ucom4", le, 0, []() -> util::disasm_interface * { return new ucom4_disassembler; } }, + { "unsp", be, 0, []() -> util::disasm_interface * { return new unsp_disassembler; } }, + { "upd7725", be, 0, []() -> util::disasm_interface * { return new necdsp_disassembler; } }, + { "upd7801", le, 0, []() -> util::disasm_interface * { return new upd7801_disassembler; } }, + { "upd7807", le, 0, []() -> util::disasm_interface * { return new upd7807_disassembler; } }, + { "upd7810", le, 0, []() -> util::disasm_interface * { return new upd7810_disassembler; } }, + { "upd78c05", le, 0, []() -> util::disasm_interface * { return new upd78c05_disassembler; } }, + { "upi41", le, 0, []() -> util::disasm_interface * { return new mcs48_disassembler(true); } }, + { "v60", le, 0, []() -> util::disasm_interface * { return new v60_disassembler; } }, + { "v810", le, 0, []() -> util::disasm_interface * { return new v810_disassembler; } }, + { "x86_16", le, 0, []() -> util::disasm_interface * { i386_unidasm.mode = 16; return new i386_disassembler(&i386_unidasm); } }, + { "x86_32", le, 0, []() -> util::disasm_interface * { i386_unidasm.mode = 32; return new i386_disassembler(&i386_unidasm); } }, + { "x86_64", le, 0, []() -> util::disasm_interface * { i386_unidasm.mode = 64; return new i386_disassembler(&i386_unidasm); } }, + { "z180", le, 0, []() -> util::disasm_interface * { return new z180_disassembler; } }, + { "z8", le, 0, []() -> util::disasm_interface * { return new z8_disassembler; } }, + { "z80", le, 0, []() -> util::disasm_interface * { return new z80_disassembler; } }, + { "z8000", be, 0, []() -> util::disasm_interface * { return new z8000_disassembler(&z8000_unidasm); } }, +}; + +class unidasm_data_buffer : public util::disasm_interface::data_buffer +{ +public: + std::vector data; + offs_t base_pc; + u32 size; -CPU_DISASSEMBLE( adsp21xx ); -CPU_DISASSEMBLE( alpha8201 ); -CPU_DISASSEMBLE( am29000 ); -CPU_DISASSEMBLE( amis2000 ); -CPU_DISASSEMBLE( apexc ); -CPU_DISASSEMBLE( arcompact ); -CPU_DISASSEMBLE( arm ); -CPU_DISASSEMBLE( arm_be ); -CPU_DISASSEMBLE( arm7arm ); -CPU_DISASSEMBLE( arm7arm_be ); -CPU_DISASSEMBLE( arm7thumb ); -CPU_DISASSEMBLE( arm7thumb_be ); -CPU_DISASSEMBLE( asap ); -CPU_DISASSEMBLE( avr8 ); -CPU_DISASSEMBLE( capricorn ); -CPU_DISASSEMBLE( ccpu ); -CPU_DISASSEMBLE( cdp1801 ); -CPU_DISASSEMBLE( cdp1802 ); -CPU_DISASSEMBLE( clipper ); -CPU_DISASSEMBLE( coldfire ); -CPU_DISASSEMBLE( cop410 ); -CPU_DISASSEMBLE( cop420 ); -CPU_DISASSEMBLE( cop444 ); -CPU_DISASSEMBLE( cop424 ); -CPU_DISASSEMBLE( cp1610 ); -CPU_DISASSEMBLE( cquestlin ); -CPU_DISASSEMBLE( cquestrot ); -CPU_DISASSEMBLE( cquestsnd ); -CPU_DISASSEMBLE( ds5002fp ); -CPU_DISASSEMBLE( dsp16a ); -CPU_DISASSEMBLE( dsp32c ); -CPU_DISASSEMBLE( dsp56k ); -CPU_DISASSEMBLE( e0c6200 ); -CPU_DISASSEMBLE( esrip ); -CPU_DISASSEMBLE( f8 ); -CPU_DISASSEMBLE( g65816_generic ); -CPU_DISASSEMBLE( h6280 ); -CPU_DISASSEMBLE( hc11 ); -CPU_DISASSEMBLE( hcd62121 ); -CPU_DISASSEMBLE( hd61700 ); -CPU_DISASSEMBLE( hd6301 ); -CPU_DISASSEMBLE( hd6309 ); -CPU_DISASSEMBLE( hd63701 ); -CPU_DISASSEMBLE( hmcs40 ); -CPU_DISASSEMBLE( hp_hybrid ); -CPU_DISASSEMBLE( hp_5061_3001 ); -CPU_DISASSEMBLE( hp_nanoprocessor ); -CPU_DISASSEMBLE( hyperstone_generic ); -CPU_DISASSEMBLE( i4004 ); -CPU_DISASSEMBLE( i4040 ); -CPU_DISASSEMBLE( i8008 ); -CPU_DISASSEMBLE( i8051 ); -CPU_DISASSEMBLE( i8052 ); -CPU_DISASSEMBLE( i8085 ); -CPU_DISASSEMBLE( i8089 ); -CPU_DISASSEMBLE( i80c51 ); -CPU_DISASSEMBLE( i80c52 ); -CPU_DISASSEMBLE( i860 ); -CPU_DISASSEMBLE( i960 ); -CPU_DISASSEMBLE( ie15 ); -CPU_DISASSEMBLE( jaguardsp ); -CPU_DISASSEMBLE( jaguargpu ); -CPU_DISASSEMBLE( konami ); -CPU_DISASSEMBLE( lh5801 ); -CPU_DISASSEMBLE( lr35902 ); -CPU_DISASSEMBLE( m58846 ); -CPU_DISASSEMBLE( m37710_generic ); -CPU_DISASSEMBLE( m6800 ); -CPU_DISASSEMBLE( m68000 ); -CPU_DISASSEMBLE( m68008 ); -CPU_DISASSEMBLE( m6801 ); -CPU_DISASSEMBLE( m68010 ); -CPU_DISASSEMBLE( m6802 ); -CPU_DISASSEMBLE( m68020 ); -CPU_DISASSEMBLE( m6803 ); -CPU_DISASSEMBLE( m68030 ); -CPU_DISASSEMBLE( m68040 ); -CPU_DISASSEMBLE( m6805 ); -CPU_DISASSEMBLE( m146805 ); -CPU_DISASSEMBLE( m68hc05 ); -CPU_DISASSEMBLE( m6808 ); -CPU_DISASSEMBLE( m6809 ); -CPU_DISASSEMBLE( m68340 ); -CPU_DISASSEMBLE( mb86233 ); -CPU_DISASSEMBLE( mb88 ); -CPU_DISASSEMBLE( mcs48 ); -CPU_DISASSEMBLE( minx ); -CPU_DISASSEMBLE( mips3be ); -CPU_DISASSEMBLE( mips3le ); -CPU_DISASSEMBLE( mn10200 ); -CPU_DISASSEMBLE( n8x300 ); -CPU_DISASSEMBLE( nec ); -CPU_DISASSEMBLE( nsc8105 ); -CPU_DISASSEMBLE( pdp1 ); -CPU_DISASSEMBLE( pdp8 ); -CPU_DISASSEMBLE( pic16c5x ); -CPU_DISASSEMBLE( pic16c62x ); -CPU_DISASSEMBLE( powerpc ); -CPU_DISASSEMBLE( pps4 ); -CPU_DISASSEMBLE( psxcpu_generic ); -CPU_DISASSEMBLE( r3000be ); -CPU_DISASSEMBLE( r3000le ); -CPU_DISASSEMBLE( rsp ); -CPU_DISASSEMBLE( s2650 ); -CPU_DISASSEMBLE( saturn ); -CPU_DISASSEMBLE( sc61860 ); -CPU_DISASSEMBLE( scmp ); -CPU_DISASSEMBLE( scudsp ); -CPU_DISASSEMBLE( se3208 ); -CPU_DISASSEMBLE( sh2 ); -CPU_DISASSEMBLE( sh4 ); -CPU_DISASSEMBLE( sh4be ); -CPU_DISASSEMBLE( sharc ); -CPU_DISASSEMBLE( sm500 ); -CPU_DISASSEMBLE( sm510 ); -CPU_DISASSEMBLE( sm511 ); -CPU_DISASSEMBLE( sm5a ); -CPU_DISASSEMBLE( sm8500 ); -CPU_DISASSEMBLE( spc700 ); -CPU_DISASSEMBLE( ssem ); -CPU_DISASSEMBLE( ssp1601 ); -CPU_DISASSEMBLE( superfx ); -CPU_DISASSEMBLE( t11 ); -CPU_DISASSEMBLE( t90 ); -CPU_DISASSEMBLE( tlcs900 ); -CPU_DISASSEMBLE( tms0980 ); -CPU_DISASSEMBLE( tms1000 ); -CPU_DISASSEMBLE( tms1100 ); -CPU_DISASSEMBLE( tms32010 ); -CPU_DISASSEMBLE( tms32025 ); -CPU_DISASSEMBLE( tms3203x ); -CPU_DISASSEMBLE( tms32051 ); -CPU_DISASSEMBLE( tms34010 ); -CPU_DISASSEMBLE( tms34020 ); -CPU_DISASSEMBLE( tms57002 ); -CPU_DISASSEMBLE( tms7000 ); -CPU_DISASSEMBLE( tms9900 ); -CPU_DISASSEMBLE( tms9980 ); -CPU_DISASSEMBLE( tms9995 ); -CPU_DISASSEMBLE( tp0320 ); -CPU_DISASSEMBLE( tx0_64kw ); -CPU_DISASSEMBLE( tx0_8kw ); -CPU_DISASSEMBLE( ucom4 ); -CPU_DISASSEMBLE( unsp ); -CPU_DISASSEMBLE( upd7725 ); -CPU_DISASSEMBLE( upd7801 ); -CPU_DISASSEMBLE( upd7807 ); -CPU_DISASSEMBLE( upd7810 ); -CPU_DISASSEMBLE( upd78c05 ); -CPU_DISASSEMBLE( upi41 ); -CPU_DISASSEMBLE( v60 ); -CPU_DISASSEMBLE( v70 ); -CPU_DISASSEMBLE( v810 ); -CPU_DISASSEMBLE( x86_16 ); -CPU_DISASSEMBLE( x86_32 ); -CPU_DISASSEMBLE( x86_64 ); -CPU_DISASSEMBLE( z180 ); -CPU_DISASSEMBLE( z8 ); -CPU_DISASSEMBLE( z80 ); -CPU_DISASSEMBLE( z8000 ); - -CPU_DISASSEMBLE( sparcv7 ) { static sparc_disassembler dasm(nullptr, 7); return dasm.dasm(stream, pc, big_endianize_int32(*reinterpret_cast(oprom))); } -CPU_DISASSEMBLE( sparcv8 ) { static sparc_disassembler dasm(nullptr, 8); return dasm.dasm(stream, pc, big_endianize_int32(*reinterpret_cast(oprom))); } -CPU_DISASSEMBLE( sparcv9 ) { static sparc_disassembler dasm(nullptr, 9); return dasm.dasm(stream, pc, big_endianize_int32(*reinterpret_cast(oprom))); } -CPU_DISASSEMBLE( sparcv9vis1 ) { static sparc_disassembler dasm(nullptr, 9, sparc_disassembler::vis_1); return dasm.dasm(stream, pc, big_endianize_int32(*reinterpret_cast(oprom))); } -CPU_DISASSEMBLE( sparcv9vis2 ) { static sparc_disassembler dasm(nullptr, 9, sparc_disassembler::vis_2); return dasm.dasm(stream, pc, big_endianize_int32(*reinterpret_cast(oprom))); } -CPU_DISASSEMBLE( sparcv9vis2p ) { static sparc_disassembler dasm(nullptr, 9, sparc_disassembler::vis_2p); return dasm.dasm(stream, pc, big_endianize_int32(*reinterpret_cast(oprom))); } -CPU_DISASSEMBLE( sparcv9vis3 ) { static sparc_disassembler dasm(nullptr, 9, sparc_disassembler::vis_3); return dasm.dasm(stream, pc, big_endianize_int32(*reinterpret_cast(oprom))); } -CPU_DISASSEMBLE( sparcv9vis3b ) { static sparc_disassembler dasm(nullptr, 9, sparc_disassembler::vis_3b); return dasm.dasm(stream, pc, big_endianize_int32(*reinterpret_cast(oprom))); } + unidasm_data_buffer(util::disasm_interface *disasm, const dasm_table_entry *entry); + virtual ~unidasm_data_buffer() = default; + void decrypt(const unidasm_data_buffer &buffer, bool opcode); -static const dasm_table_entry dasm_table[] = + virtual u8 r8 (offs_t pc) const override { return lr8 (pc); } + virtual u16 r16(offs_t pc) const override { return lr16(pc); } + virtual u32 r32(offs_t pc) const override { return lr32(pc); } + virtual u64 r64(offs_t pc) const override { return lr64(pc); } + +private: + std::function lr8; + std::function lr16; + std::function lr32; + std::function lr64; + + util::disasm_interface *disasm; + const dasm_table_entry *entry; + + template const T *get_ptr(offs_t pc) const { + if(pc < base_pc) + return nullptr; + offs_t delta = (pc - base_pc) * sizeof(T); + if(delta >= size) + return nullptr; + return reinterpret_cast(&data[delta]); + } + + template T get(offs_t pc) const { + auto p = get_ptr(pc); + return p ? *p : 0; + } +}; + +struct dasm_line { - { "8x300", _16be, 0, CPU_DISASSEMBLE_NAME(n8x300) }, - { "adsp21xx", _24le, -2, CPU_DISASSEMBLE_NAME(adsp21xx) }, - { "alpha8201", _8bit, 0, CPU_DISASSEMBLE_NAME(alpha8201) }, - { "am29000", _32be, 0, CPU_DISASSEMBLE_NAME(am29000) }, - { "amis2000", _8bit, 0, CPU_DISASSEMBLE_NAME(amis2000) }, - { "apexc", _32be, 0, CPU_DISASSEMBLE_NAME(apexc) }, - { "arcompact", _16le, 0, CPU_DISASSEMBLE_NAME(arcompact) }, - { "arm", _32le, 0, CPU_DISASSEMBLE_NAME(arm) }, - { "arm_be", _32be, 0, CPU_DISASSEMBLE_NAME(arm_be) }, - { "arm7", _32le, 0, CPU_DISASSEMBLE_NAME(arm7arm) }, - { "arm7_be", _32be, 0, CPU_DISASSEMBLE_NAME(arm7arm_be) }, - { "arm7thumb", _16le, 0, CPU_DISASSEMBLE_NAME(arm7thumb) }, - { "arm7thumbb", _16be, 0, CPU_DISASSEMBLE_NAME(arm7thumb_be) }, - { "asap", _32le, 0, CPU_DISASSEMBLE_NAME(asap) }, - { "avr8", _16le, 0, CPU_DISASSEMBLE_NAME(avr8) }, - { "capricorn", _8bit, 0, CPU_DISASSEMBLE_NAME(capricorn) }, - { "ccpu", _8bit, 0, CPU_DISASSEMBLE_NAME(ccpu) }, - { "cdp1801", _8bit, 0, CPU_DISASSEMBLE_NAME(cdp1801) }, - { "cdp1802", _8bit, 0, CPU_DISASSEMBLE_NAME(cdp1802) }, - { "clipper", _16le, 0, CPU_DISASSEMBLE_NAME(clipper) }, - { "coldfire", _16be, 0, CPU_DISASSEMBLE_NAME(coldfire) }, - { "cop410", _8bit, 0, CPU_DISASSEMBLE_NAME(cop410) }, - { "cop420", _8bit, 0, CPU_DISASSEMBLE_NAME(cop420) }, - { "cop444", _8bit, 0, CPU_DISASSEMBLE_NAME(cop444) }, - { "cop424", _8bit, 0, CPU_DISASSEMBLE_NAME(cop424) }, - { "cp1610", _16be, -1, CPU_DISASSEMBLE_NAME(cp1610) }, - { "cquestlin", _64be, -3, CPU_DISASSEMBLE_NAME(cquestlin) }, - { "cquestrot", _64be, -3, CPU_DISASSEMBLE_NAME(cquestrot) }, - { "cquestsnd", _64be, -3, CPU_DISASSEMBLE_NAME(cquestsnd) }, - { "ds5002fp", _8bit, 0, CPU_DISASSEMBLE_NAME(ds5002fp) }, - { "dsp16a", _16le, -1, CPU_DISASSEMBLE_NAME(dsp16a) }, - { "dsp32c", _32le, 0, CPU_DISASSEMBLE_NAME(dsp32c) }, - { "dsp56k", _16le, -1, CPU_DISASSEMBLE_NAME(dsp56k) }, - { "e0c6200", _16be, -1, CPU_DISASSEMBLE_NAME(e0c6200) }, - { "esrip", _64be, 0, CPU_DISASSEMBLE_NAME(esrip) }, - { "f8", _8bit, 0, CPU_DISASSEMBLE_NAME(f8) }, - { "g65816", _8bit, 0, CPU_DISASSEMBLE_NAME(g65816_generic) }, - { "h6280", _8bit, 0, CPU_DISASSEMBLE_NAME(h6280) }, -// { "h8", _16be, 0, CPU_DISASSEMBLE_NAME(h8) }, -// { "h8_24", _16be, 0, CPU_DISASSEMBLE_NAME(h8_24) }, -// { "h8_32", _16be, 0, CPU_DISASSEMBLE_NAME(h8_32) }, - { "hc11", _8bit, 0, CPU_DISASSEMBLE_NAME(hc11) }, - { "hcd62121", _8bit, 0, CPU_DISASSEMBLE_NAME(hcd62121) }, - { "hd61700", _8bit, 0, CPU_DISASSEMBLE_NAME(hd61700) }, - { "hd6301", _8bit, 0, CPU_DISASSEMBLE_NAME(hd6301) }, - { "hd6309", _8bit, 0, CPU_DISASSEMBLE_NAME(hd6309) }, - { "hd63701", _8bit, 0, CPU_DISASSEMBLE_NAME(hd63701) }, - { "hmcs40", _16le, -1, CPU_DISASSEMBLE_NAME(hmcs40) }, - { "hp_hybrid", _16be, -1, CPU_DISASSEMBLE_NAME(hp_hybrid) }, - { "hp_5061_3001",_16be, -1, CPU_DISASSEMBLE_NAME(hp_5061_3001) }, - { "hyperstone", _16be, 0, CPU_DISASSEMBLE_NAME(hyperstone_generic) }, - { "i4004", _8bit, 0, CPU_DISASSEMBLE_NAME(i4004) }, - { "i4040", _8bit, 0, CPU_DISASSEMBLE_NAME(i4040) }, - { "i8008", _8bit, 0, CPU_DISASSEMBLE_NAME(i8008) }, - { "i8051", _8bit, 0, CPU_DISASSEMBLE_NAME(i8051) }, - { "i8052", _8bit, 0, CPU_DISASSEMBLE_NAME(i8052) }, - { "i8085", _8bit, 0, CPU_DISASSEMBLE_NAME(i8085) }, - { "i8089", _8bit, 0, CPU_DISASSEMBLE_NAME(i8089) }, - { "i80c51", _8bit, 0, CPU_DISASSEMBLE_NAME(i80c51) }, - { "i80c52", _8bit, 0, CPU_DISASSEMBLE_NAME(i80c52) }, - { "i860", _64le, 0, CPU_DISASSEMBLE_NAME(i860) }, - { "i960", _32le, 0, CPU_DISASSEMBLE_NAME(i960) }, - { "ie15", _8bit, 0, CPU_DISASSEMBLE_NAME(ie15) }, - { "jaguardsp", _16be, 0, CPU_DISASSEMBLE_NAME(jaguardsp) }, - { "jaguargpu", _16be, 0, CPU_DISASSEMBLE_NAME(jaguargpu) }, - { "konami", _8bit, 0, CPU_DISASSEMBLE_NAME(konami) }, - { "lh5801", _8bit, 0, CPU_DISASSEMBLE_NAME(lh5801) }, - { "lr35902", _8bit, 0, CPU_DISASSEMBLE_NAME(lr35902) }, - { "m58846", _16le, -1, CPU_DISASSEMBLE_NAME(m58846) }, - { "m37710", _8bit, 0, CPU_DISASSEMBLE_NAME(m37710_generic) }, - { "m6800", _8bit, 0, CPU_DISASSEMBLE_NAME(m6800) }, - { "m68000", _16be, 0, CPU_DISASSEMBLE_NAME(m68000) }, - { "m68008", _16be, 0, CPU_DISASSEMBLE_NAME(m68008) }, - { "m6801", _8bit, 0, CPU_DISASSEMBLE_NAME(m6801) }, - { "m68010", _16be, 0, CPU_DISASSEMBLE_NAME(m68010) }, - { "m6802", _8bit, 0, CPU_DISASSEMBLE_NAME(m6802) }, - { "m68020", _16be, 0, CPU_DISASSEMBLE_NAME(m68020) }, - { "m6803", _8bit, 0, CPU_DISASSEMBLE_NAME(m6803) }, - { "m68030", _16be, 0, CPU_DISASSEMBLE_NAME(m68030) }, - { "m68040", _16be, 0, CPU_DISASSEMBLE_NAME(m68040) }, - { "m6805", _8bit, 0, CPU_DISASSEMBLE_NAME(m6805) }, - { "m146805", _8bit, 0, CPU_DISASSEMBLE_NAME(m146805) }, - { "m68hc05", _8bit, 0, CPU_DISASSEMBLE_NAME(m68hc05) }, - { "m6808", _8bit, 0, CPU_DISASSEMBLE_NAME(m6808) }, - { "m6809", _8bit, 0, CPU_DISASSEMBLE_NAME(m6809) }, - { "m68340", _16be, 0, CPU_DISASSEMBLE_NAME(m68340) }, - { "mb86233", _32le, -2, CPU_DISASSEMBLE_NAME(mb86233) }, - { "mb88", _8bit, 0, CPU_DISASSEMBLE_NAME(mb88) }, - { "mcs48", _8bit, 0, CPU_DISASSEMBLE_NAME(mcs48) }, - { "minx", _8bit, 0, CPU_DISASSEMBLE_NAME(minx) }, - { "mips3be", _32be, 0, CPU_DISASSEMBLE_NAME(mips3be) }, - { "mips3le", _32le, 0, CPU_DISASSEMBLE_NAME(mips3le) }, - { "mn10200", _16le, 0, CPU_DISASSEMBLE_NAME(mn10200) }, - { "nanoprocessor",_8bit, 0, CPU_DISASSEMBLE_NAME(hp_nanoprocessor) }, - { "nec", _8bit, 0, CPU_DISASSEMBLE_NAME(nec) }, - { "nsc8105", _8bit, 0, CPU_DISASSEMBLE_NAME(nsc8105) }, - { "pdp1", _32be, 0, CPU_DISASSEMBLE_NAME(pdp1) }, - { "pdp8", _16be, 0, CPU_DISASSEMBLE_NAME(pdp8) }, - { "pic16c5x", _16le, -1, CPU_DISASSEMBLE_NAME(pic16c5x) }, - { "pic16c62x", _16le, -1, CPU_DISASSEMBLE_NAME(pic16c62x) }, - { "powerpc", _32be, 0, CPU_DISASSEMBLE_NAME(powerpc) }, - { "pps4", _8bit, 0, CPU_DISASSEMBLE_NAME(pps4) }, - { "psxcpu", _32le, 0, CPU_DISASSEMBLE_NAME(psxcpu_generic) }, - { "r3000be", _32be, 0, CPU_DISASSEMBLE_NAME(r3000be) }, - { "r3000le", _32le, 0, CPU_DISASSEMBLE_NAME(r3000le) }, - { "rsp", _32le, 0, CPU_DISASSEMBLE_NAME(rsp) }, - { "s2650", _8bit, 0, CPU_DISASSEMBLE_NAME(s2650) }, - { "saturn", _8bit, 0, CPU_DISASSEMBLE_NAME(saturn) }, - { "sc61860", _8bit, 0, CPU_DISASSEMBLE_NAME(sc61860) }, - { "scmp", _8bit, 0, CPU_DISASSEMBLE_NAME(scmp) }, - { "scudsp", _32be, 0, CPU_DISASSEMBLE_NAME(scudsp) }, - { "se3208", _16le, 0, CPU_DISASSEMBLE_NAME(se3208) }, - { "sh2", _16be, 0, CPU_DISASSEMBLE_NAME(sh2) }, - { "sh4", _16le, 0, CPU_DISASSEMBLE_NAME(sh4) }, - { "sh4be", _16be, 0, CPU_DISASSEMBLE_NAME(sh4be) }, - { "sharc", _48le, -2, CPU_DISASSEMBLE_NAME(sharc) }, - { "sm500", _8bit, 0, CPU_DISASSEMBLE_NAME(sm500) }, - { "sm510", _8bit, 0, CPU_DISASSEMBLE_NAME(sm510) }, - { "sm511", _8bit, 0, CPU_DISASSEMBLE_NAME(sm511) }, - { "sm5a", _8bit, 0, CPU_DISASSEMBLE_NAME(sm5a) }, - { "sm8500", _8bit, 0, CPU_DISASSEMBLE_NAME(sm8500) }, - { "sparcv7", _32be, 0, CPU_DISASSEMBLE_NAME(sparcv7) }, - { "sparcv8", _32be, 0, CPU_DISASSEMBLE_NAME(sparcv8) }, - { "sparcv9", _32be, 0, CPU_DISASSEMBLE_NAME(sparcv9) }, - { "sparcv9vis1", _32be, 0, CPU_DISASSEMBLE_NAME(sparcv9vis1) }, - { "sparcv9vis2", _32be, 0, CPU_DISASSEMBLE_NAME(sparcv9vis2) }, - { "sparcv9vis2p",_32be, 0, CPU_DISASSEMBLE_NAME(sparcv9vis2p) }, - { "sparcv9vis3", _32be, 0, CPU_DISASSEMBLE_NAME(sparcv9vis3) }, - { "sparcv9vis3b",_32be, 0, CPU_DISASSEMBLE_NAME(sparcv9vis3b) }, - { "spc700", _8bit, 0, CPU_DISASSEMBLE_NAME(spc700) }, - { "ssem", _32le, 0, CPU_DISASSEMBLE_NAME(ssem) }, - { "ssp1601", _16be, -1, CPU_DISASSEMBLE_NAME(ssp1601) }, -// { "superfx", _8bit, 0, CPU_DISASSEMBLE_NAME(superfx) }, - { "t11", _16le, 0, CPU_DISASSEMBLE_NAME(t11) }, -// { "t90", _8bit, 0, CPU_DISASSEMBLE_NAME(t90) }, - { "tlcs900", _8bit, 0, CPU_DISASSEMBLE_NAME(tlcs900) }, - { "tms0980", _16be, 0, CPU_DISASSEMBLE_NAME(tms0980) }, - { "tms1000", _8bit, 0, CPU_DISASSEMBLE_NAME(tms1000) }, - { "tms1100", _8bit, 0, CPU_DISASSEMBLE_NAME(tms1100) }, - { "tms32010", _16be, -1, CPU_DISASSEMBLE_NAME(tms32010) }, - { "tms32025", _16be, -1, CPU_DISASSEMBLE_NAME(tms32025) }, - { "tms3203x", _32le, -2, CPU_DISASSEMBLE_NAME(tms3203x) }, - { "tms32051", _16le, -1, CPU_DISASSEMBLE_NAME(tms32051) }, - { "tms34010", _8bit, 3, CPU_DISASSEMBLE_NAME(tms34010) }, - { "tms34020", _8bit, 3, CPU_DISASSEMBLE_NAME(tms34020) }, - { "tms57002", _32le, -2, CPU_DISASSEMBLE_NAME(tms57002) }, - { "tms7000", _8bit, 0, CPU_DISASSEMBLE_NAME(tms7000) }, - { "tms9900", _16be, 0, CPU_DISASSEMBLE_NAME(tms9900) }, - { "tms9980", _8bit, 0, CPU_DISASSEMBLE_NAME(tms9980) }, - { "tms9995", _8bit, 0, CPU_DISASSEMBLE_NAME(tms9995) }, - { "tp0320", _16be, 0, CPU_DISASSEMBLE_NAME(tp0320) }, - { "tx0_64kw", _32be, -2, CPU_DISASSEMBLE_NAME(tx0_64kw) }, - { "tx0_8kw", _32be, -2, CPU_DISASSEMBLE_NAME(tx0_8kw) }, - { "ucom4", _8bit, 0, CPU_DISASSEMBLE_NAME(ucom4) }, - { "unsp", _16be, 0, CPU_DISASSEMBLE_NAME(unsp) }, - { "upd7725", _32be, 0, CPU_DISASSEMBLE_NAME(upd7725) }, - { "upd7801", _8bit, 0, CPU_DISASSEMBLE_NAME(upd7801) }, - { "upd7807", _8bit, 0, CPU_DISASSEMBLE_NAME(upd7807) }, - { "upd7810", _8bit, 0, CPU_DISASSEMBLE_NAME(upd7810) }, - { "upd78c05", _8bit, 0, CPU_DISASSEMBLE_NAME(upd78c05) }, - { "upi41", _8bit, 0, CPU_DISASSEMBLE_NAME(upi41) }, - { "v60", _8bit, 0, CPU_DISASSEMBLE_NAME(v60) }, - { "v70", _8bit, 0, CPU_DISASSEMBLE_NAME(v70) }, - { "v810", _16le, 0, CPU_DISASSEMBLE_NAME(v810) }, - { "x86_16", _8bit, 0, CPU_DISASSEMBLE_NAME(x86_16) }, - { "x86_32", _8bit, 0, CPU_DISASSEMBLE_NAME(x86_32) }, - { "x86_64", _8bit, 0, CPU_DISASSEMBLE_NAME(x86_64) }, - { "z180", _8bit, 0, CPU_DISASSEMBLE_NAME(z180) }, - { "z8", _8bit, 0, CPU_DISASSEMBLE_NAME(z8) }, - { "z80", _8bit, 0, CPU_DISASSEMBLE_NAME(z80) }, -// { "z8000", _16be, 0, CPU_DISASSEMBLE_NAME(z8000) }, + offs_t pc; + offs_t size; + std::string dasm; }; +unidasm_data_buffer::unidasm_data_buffer(util::disasm_interface *_disasm, const dasm_table_entry *_entry) : disasm(_disasm), entry(_entry) +{ + u32 flags = disasm->interface_flags(); + u32 page_mask = flags & util::disasm_interface::PAGED ? (1 << disasm->page_address_bits()) - 1 : 0; + + if(flags & util::disasm_interface::NONLINEAR_PC) { + switch(entry->pcshift) { + case -1: + lr8 = [](offs_t pc) -> u8 { throw emu_fatalerror("debug_disasm_buffer::debug_data_buffer: r8 access on 16-bits granularity bus\n"); }; + lr16 = [this](offs_t pc) -> u16 { + const u16 *src = get_ptr(pc); + return src[0]; + }; + + switch(entry->endian) { + case le: + lr32 = [this, page_mask](offs_t pc) -> u32 { + offs_t lpc = disasm->pc_real_to_linear(pc); + u32 r = 0; + for(int j=0; j != 2; j++) { + r |= get(disasm->pc_linear_to_real(lpc)) << (j*16); + lpc = (lpc & ~page_mask) | ((lpc + 1) & page_mask); + } + return r; + }; + lr64 = [this, page_mask](offs_t pc) -> u64 { + offs_t lpc = disasm->pc_real_to_linear(pc); + u64 r = 0; + for(int j=0; j != 4; j++) { + r |= u64(get(disasm->pc_linear_to_real(lpc))) << (j*16); + lpc = (lpc & ~page_mask) | ((lpc + 1) & page_mask); + } + return r; + }; + break; + + case be: + lr32 = [this, page_mask](offs_t pc) -> u32 { + offs_t lpc = disasm->pc_real_to_linear(pc); + u32 r = 0; + for(int j=0; j != 2; j++) { + r |= get(disasm->pc_linear_to_real(lpc)) << ((1-j)*16); + lpc = (lpc & ~page_mask) | ((lpc + 1) & page_mask); + } + return r; + }; + lr64 = [this, page_mask](offs_t pc) -> u64 { + offs_t lpc = disasm->pc_real_to_linear(pc); + u64 r = 0; + for(int j=0; j != 4; j++) { + r |= u64(get(disasm->pc_linear_to_real(lpc))) << ((3-j)*16); + lpc = (lpc & ~page_mask) | ((lpc + 1) & page_mask); + } + return r; + }; + break; + } + break; + + case 0: + lr8 = [this](offs_t pc) -> u8 { + const u8 *src = get_ptr(pc); + return src[0]; + }; + + switch(entry->endian) { + case le: + lr16 = [this, page_mask](offs_t pc) -> u16 { + offs_t lpc = disasm->pc_real_to_linear(pc); + u16 r = 0; + for(int j=0; j != 2; j++) { + r |= get(disasm->pc_linear_to_real(lpc)) << (j*8); + lpc = (lpc & ~page_mask) | ((lpc + 1) & page_mask); + } + return r; + }; + lr32 = [this, page_mask](offs_t pc) -> u32 { + offs_t lpc = disasm->pc_real_to_linear(pc); + u32 r = 0; + for(int j=0; j != 2; j++) { + r |= get(disasm->pc_linear_to_real(lpc)) << (j*8); + lpc = (lpc & ~page_mask) | ((lpc + 1) & page_mask); + } + return r; + }; + lr64 = [this, page_mask](offs_t pc) -> u64 { + offs_t lpc = disasm->pc_real_to_linear(pc); + u64 r = 0; + for(int j=0; j != 8; j++) { + r |= u64(get(disasm->pc_linear_to_real(lpc))) << (j*8); + lpc = (lpc & ~page_mask) | ((lpc + 1) & page_mask); + } + return r; + }; + break; + + case be: + lr16 = [this, page_mask](offs_t pc) -> u16 { + offs_t lpc = disasm->pc_real_to_linear(pc); + u16 r = 0; + for(int j=0; j != 2; j++) { + r |= get(disasm->pc_linear_to_real(lpc)) << ((1-j)*8); + lpc = (lpc & ~page_mask) | ((lpc + 1) & page_mask); + } + return r; + }; + lr32 = [this, page_mask](offs_t pc) -> u32 { + offs_t lpc = disasm->pc_real_to_linear(pc); + u32 r = 0; + for(int j=0; j != 2; j++) { + r |= get(disasm->pc_linear_to_real(lpc)) << ((3-j)*8); + lpc = (lpc & ~page_mask) | ((lpc + 1) & page_mask); + } + return r; + }; + lr64 = [this, page_mask](offs_t pc) -> u64 { + offs_t lpc = disasm->pc_real_to_linear(pc); + u64 r = 0; + for(int j=0; j != 8; j++) { + r |= u64(get(disasm->pc_linear_to_real(lpc))) << ((7-j)*8); + lpc = (lpc & ~page_mask) | ((lpc + 1) & page_mask); + } + return r; + }; + break; + } + break; + } + } else { + switch(entry->pcshift) { + case 0: + lr8 = [this](offs_t pc) -> u8 { + const u8 *p = get_ptr(pc); + return p ? + p[0] + : 0x00; + }; + switch(entry->endian) { + case le: + lr16 = [this](offs_t pc) -> u16 { + const u8 *p = get_ptr(pc); + return p ? + p[0] | + (p[1] << 8) + : 0x0000; + }; + lr32 = [this](offs_t pc) -> u32 { + const u8 *p = get_ptr(pc); + return p ? + p[0] | + (p[1] << 8) | + (p[2] << 16) | + (p[3] << 24) + : 0x00000000; + }; + lr64 = [this](offs_t pc) -> u64 { + const u8 *p = get_ptr(pc); + return p ? + p[0] | + (p[1] << 8) | + (p[2] << 16) | + (p[3] << 24) | + (u64(p[4]) << 32) | + (u64(p[5]) << 40) | + (u64(p[6]) << 48) | + (u64(p[7]) << 56) + : 0x0000000000000000; }; + break; + case be: + lr16 = [this](offs_t pc) -> u16 { + const u8 *p = get_ptr(pc); + return p ? + (p[0] << 8) | + p[1] + : 0x0000; + }; + lr32 = [this](offs_t pc) -> u32 { + const u8 *p = get_ptr(pc); + return p ? + (p[0] << 24) | + (p[1] << 16) | + (p[2] << 8) | + p[3] + : 0x00000000; + }; + lr64 = [this](offs_t pc) -> u64 { + const u8 *p = get_ptr(pc); + return p ? + (u64(p[0]) << 56) | + (u64(p[1]) << 48) | + (u64(p[2]) << 40) | + (u64(p[3]) << 32) | + (p[4] << 24) | + (p[5] << 16) | + (p[6] << 8) | + p[7] + : 0x0000000000000000; }; + break; + } + break; + + case -1: + lr8 = [this](offs_t pc) -> u8 { abort(); }; + lr16 = [this](offs_t pc) -> u16 { + const u16 *p = get_ptr(pc); + return p ? + p[0] + : 0x0000; + }; + switch(entry->endian) { + case le: + lr32 = [this](offs_t pc) -> u32 { + const u16 *p = get_ptr(pc); + return p ? + p[0] | + (p[1] << 16) + : 0x00000000; + }; + lr64 = [this](offs_t pc) -> u64 { + const u16 *p = get_ptr(pc); + return p ? + p[0] | + (p[1] << 16) | + (u64(p[2]) << 32) | + (u64(p[3]) << 48) + : 0x0000000000000000; + }; + break; + case be: + lr32 = [this](offs_t pc) -> u32 { + const u16 *p = get_ptr(pc); + return p ? + (p[0] << 16)| + p[1] + : 0x00000000; + }; + lr64 = [this](offs_t pc) -> u64 { + const u16 *p = get_ptr(pc); + return p ? + (u64(p[0]) << 48) | + (u64(p[1]) << 32) | + (p[2] << 16) | + p[3] + : 0x0000000000000000; + }; + break; + } + break; + + case -2: + lr8 = [this](offs_t pc) -> u8 { abort(); }; + lr16 = [this](offs_t pc) -> u16 { abort(); }; + lr32 = [this](offs_t pc) -> u16 { + const u32 *p = get_ptr(pc); + return p ? + p[0] + : 0x00000000; + }; + switch(entry->endian) { + case le: + lr64 = [this](offs_t pc) -> u64 { + const u32 *p = get_ptr(pc); + return p ? + p[0] | + (u64(p[1]) << 32) + : 0x0000000000000000; + }; + break; + case be: + lr64 = [this](offs_t pc) -> u64 { + const u32 *p = get_ptr(pc); + return p ? + (u64(p[0]) << 32) | + p[1] + : 0x0000000000000000; + }; + break; + } + break; + + case -3: + lr8 = [this](offs_t pc) -> u8 { abort(); }; + lr16 = [this](offs_t pc) -> u16 { abort(); }; + lr32 = [this](offs_t pc) -> u32 { abort(); }; + lr64 = [this](offs_t pc) -> u64 { + const u64 *p = get_ptr(pc); + return p ? + p[0] + : 0x0000000000000000; + }; + break; + + case 3: + assert(entry->endian == ); + lr8 = [this](offs_t pc) -> u8 { abort(); }; + lr32 = [this](offs_t pc) -> u32 { abort(); }; + lr64 = [this](offs_t pc) -> u64 { abort(); }; + lr16 = [this](offs_t pc) -> u16 { + if(pc < base_pc) + return 0x0000; + offs_t delta = (pc - base_pc) >> 3; + if(delta >= size) + return 0x0000; + return reinterpret_cast(&data[delta])[0]; + }; + break; + + default: + abort(); + } + } +} + +void unidasm_data_buffer::decrypt(const unidasm_data_buffer &buffer, bool opcode) +{ + abort(); +} static int parse_options(int argc, char *argv[], options *opts) { @@ -420,92 +837,87 @@ static int parse_options(int argc, char *argv[], options *opts) memset(opts, 0, sizeof(*opts)); // loop through arguments - for (unsigned arg = 1; arg < argc; arg++) - { + for(unsigned arg = 1; arg < argc; arg++) { char *curarg = argv[arg]; // is it a switch? - if (curarg[0] == '-') - { - if (pending_base || pending_arch || pending_mode || pending_skip || pending_count) + if(curarg[0] == '-') { + if(pending_base || pending_arch || pending_mode || pending_skip || pending_count) goto usage; - if (tolower((uint8_t)curarg[1]) == 'a') + if(tolower((uint8_t)curarg[1]) == 'a') pending_arch = true; - else if (tolower((uint8_t)curarg[1]) == 'b') + else if(tolower((uint8_t)curarg[1]) == 'b') pending_base = true; - else if (tolower((uint8_t)curarg[1]) == 'f') + else if(tolower((uint8_t)curarg[1]) == 'f') opts->flipped = true; - else if (tolower((uint8_t)curarg[1]) == 'l') + else if(tolower((uint8_t)curarg[1]) == 'l') opts->lower = true; - else if (tolower((uint8_t)curarg[1]) == 'm') + else if(tolower((uint8_t)curarg[1]) == 'm') pending_mode = true; - else if (tolower((uint8_t)curarg[1]) == 's') + else if(tolower((uint8_t)curarg[1]) == 's') pending_skip = true; - else if (tolower((uint8_t)curarg[1]) == 'c') + else if(tolower((uint8_t)curarg[1]) == 'c') pending_count = true; - else if (tolower((uint8_t)curarg[1]) == 'n') + else if(tolower((uint8_t)curarg[1]) == 'n') opts->norawbytes = true; - else if (tolower((uint8_t)curarg[1]) == 'u') + else if(tolower((uint8_t)curarg[1]) == 'u') opts->upper = true; else goto usage; } // base PC - else if (pending_base) + else if(pending_base) { int result; - if (curarg[0] == '0' && curarg[1] == 'x') + if(curarg[0] == '0' && curarg[1] == 'x') result = sscanf(&curarg[2], "%x", &opts->basepc); - else if (curarg[0] == '$') + else if(curarg[0] == '$') result = sscanf(&curarg[1], "%x", &opts->basepc); else result = sscanf(&curarg[0], "%x", &opts->basepc); - if (result != 1) + if(result != 1) goto usage; pending_base = false; } // mode - else if (pending_mode) + else if(pending_mode) { - if (sscanf(curarg, "%d", &opts->mode) != 1) + if(sscanf(curarg, "%d", &opts->mode) != 1) goto usage; pending_mode = false; } // architecture - else if (pending_arch) - { + else if(pending_arch) { int curarch; - for (curarch = 0; curarch < ARRAY_LENGTH(dasm_table); curarch++) - if (core_stricmp(curarg, dasm_table[curarch].name) == 0) + for(curarch = 0; curarch < ARRAY_LENGTH(dasm_table); curarch++) + if(core_stricmp(curarg, dasm_table[curarch].name) == 0) break; - if (curarch == ARRAY_LENGTH(dasm_table)) + if(curarch == ARRAY_LENGTH(dasm_table)) goto usage; opts->dasm = &dasm_table[curarch]; pending_arch = false; } // skip bytes - else if (pending_skip) - { - if (sscanf(curarg, "%d", &opts->skip) != 1) + else if(pending_skip) { + if(sscanf(curarg, "%d", &opts->skip) != 1) goto usage; pending_skip = false; } // size - else if (pending_count) - { - if (sscanf(curarg, "%d", &opts->count) != 1) + else if(pending_count) { + if(sscanf(curarg, "%d", &opts->count) != 1) goto usage; pending_count = false; } // filename - else if (opts->filename == nullptr) + else if(opts->filename == nullptr) opts->filename = curarg; // fail @@ -514,11 +926,11 @@ static int parse_options(int argc, char *argv[], options *opts) } // if we have a dangling option, error - if (pending_base || pending_arch || pending_mode || pending_skip || pending_count) + if(pending_base || pending_arch || pending_mode || pending_skip || pending_count) goto usage; // if no file or no architecture, fail - if (opts->filename == nullptr || opts->dasm == nullptr) + if(opts->filename == nullptr || opts->dasm == nullptr) goto usage; return 0; @@ -531,12 +943,12 @@ usage: const int colwidth = 1 + std::strlen(std::max_element(std::begin(dasm_table), std::end(dasm_table), [](const dasm_table_entry &a, const dasm_table_entry &b) { return std::strlen(a.name) < std::strlen(b.name); })->name); const int columns = std::max(1, 80 / colwidth); const int numrows = (ARRAY_LENGTH(dasm_table) + columns - 1) / columns; - for (unsigned curarch = 0; curarch < numrows * columns; curarch++) + for(unsigned curarch = 0; curarch < numrows * columns; curarch++) { const int row = curarch / columns; const int col = curarch % columns; const int index = col * numrows + row; - if (col == 0) + if(col == 0) printf("\n "); printf("%-*s", colwidth, (index < ARRAY_LENGTH(dasm_table)) ? dasm_table[index].name : ""); } @@ -547,191 +959,311 @@ usage: int main(int argc, char *argv[]) { - osd_file::error filerr; - int displayendian; - int displaychunk; - uint32_t curbyte; - uint32_t length; - int maxchunks; - uint32_t curpc; + // Parse options first options opts; - int numbytes; - void *data; - int result = 0; - - // parse options first - if (parse_options(argc, argv, &opts)) + if(parse_options(argc, argv, &opts)) return 1; - // load the file - filerr = util::core_file::load(opts.filename, &data, length); - if (filerr != osd_file::error::NONE) + // Load the file + void *data; + uint32_t length; + osd_file::error filerr = util::core_file::load(opts.filename, &data, length); + if(filerr != osd_file::error::NONE) { fprintf(stderr, "Error opening file '%s'\n", opts.filename); return 1; } - // precompute parameters - displaychunk = (opts.dasm->display / 2) + 1; - displayendian = opts.dasm->display % 2; - switch (displaychunk) - { - case 1: maxchunks = 6; break; - case 2: maxchunks = 3; break; - default: maxchunks = 1; break; + // Build the disasm object + std::unique_ptr disasm(opts.dasm->alloc()); + u32 flags = disasm->interface_flags(); + + // Compute the granularity in bytes (1-8) + offs_t granularity = opts.dasm->pcshift < 0 ? disasm->opcode_alignment() << -opts.dasm->pcshift : disasm->opcode_alignment() >> opts.dasm->pcshift; + + // Build the base buffer and fill it (with a margin) + unidasm_data_buffer base_buffer(disasm.get(), opts.dasm); + u32 rounded_size = (((length - opts.skip) | (granularity - 1)) & ~(granularity - 1)); + base_buffer.data.resize(rounded_size + 8, 0x00); + base_buffer.size = length; + base_buffer.base_pc = opts.basepc; + memcpy(&base_buffer.data[0], (const u8 *)data + opts.skip, length - opts.skip); + + // Build the decryption buffers if needed + unidasm_data_buffer opcodes_buffer(disasm.get(), opts.dasm), params_buffer(disasm.get(), opts.dasm); + if(flags & util::disasm_interface::INTERNAL_DECRYPTION) { + opcodes_buffer.decrypt(base_buffer, true); + if((flags & util::disasm_interface::SPLIT_DECRYPTION) == util::disasm_interface::SPLIT_DECRYPTION) + params_buffer.decrypt(base_buffer, false); } - // run it - try - { - if (length > opts.skip) - length = length - opts.skip; - if ((length > opts.count) && (opts.count != 0)) - length = opts.count; - curpc = opts.basepc; - - std::stringstream stream; - for (curbyte = 0; curbyte < length; curbyte += numbytes) - { - uint8_t *oprom = (uint8_t *)data + opts.skip + curbyte; - uint32_t pcdelta; - int numchunks; + // Select the buffers to actually use + unidasm_data_buffer *popcodes = opcodes_buffer.data.empty() ? &base_buffer : &opcodes_buffer; + unidasm_data_buffer *pparams = params_buffer.data.empty() ? popcodes : ¶ms_buffer; - // disassemble - stream.str(""); - pcdelta = (*opts.dasm->func)(nullptr, stream, curpc, oprom, oprom, opts.mode) & DASMFLAG_LENGTHMASK; - std::string buffer = stream.str(); + // Compute the pc warparound + offs_t pclength = opts.dasm->pcshift < 0 ? rounded_size >> -opts.dasm->pcshift : rounded_size << opts.dasm->pcshift; + offs_t limit = opts.basepc + pclength; + offs_t pc_mask; + if(!limit) + pc_mask = 0xffffffff; + else { + for(pc_mask = 2; pc_mask && pc_mask < limit; pc_mask *= 2); + pc_mask--; + } - if (opts.dasm->pcshift < 0) - numbytes = pcdelta << -opts.dasm->pcshift; - else - numbytes = pcdelta >> opts.dasm->pcshift; - - // force upper or lower - if (opts.lower) - { - std::transform( - std::begin(buffer), - std::end(buffer), - std::begin(buffer), - [](char c) { return tolower(c); }); - } - else if (opts.upper) - { - std::transform( - std::begin(buffer), - std::end(buffer), - std::begin(buffer), - [](char c) { return toupper(c); }); - } + // Compute the page warparound + offs_t page_mask = flags & util::disasm_interface::PAGED ? (1 << disasm->page_address_bits()) - 1 : 0; - // round to the nearest display chunk - numbytes = ((numbytes + displaychunk - 1) / displaychunk) * displaychunk; - if (numbytes == 0) - numbytes = displaychunk; - numchunks = numbytes / displaychunk; - - // non-flipped case - if (!opts.flipped) - { - // output the address - printf("%08X: ", curpc); - - // output the raw bytes - if (!opts.norawbytes) - { - int firstchunks = (numchunks < maxchunks) ? numchunks : maxchunks; - int chunknum, bytenum; - for (chunknum = 0; chunknum < firstchunks; chunknum++) - { - for (bytenum = 0; bytenum < displaychunk; bytenum++) - printf("%02X", oprom[displayendian ? (displaychunk - 1 - bytenum) : bytenum]); - printf(" "); - oprom += displaychunk; - } - for ( ; chunknum < maxchunks; chunknum++) - printf("%*s ", displaychunk * 2, ""); - printf(" "); - } - - // output the disassembly - printf("%s\n", buffer.c_str()); - - // output additional raw bytes - if (!opts.norawbytes && numchunks > maxchunks) - { - for (numchunks -= maxchunks; numchunks > 0; numchunks -= maxchunks) - { - int firstchunks = (numchunks < maxchunks) ? numchunks : maxchunks; - int chunknum, bytenum; - printf(" "); - for (chunknum = 0; chunknum < firstchunks; chunknum++) - { - for (bytenum = 0; bytenum < displaychunk; bytenum++) - printf("%02X", oprom[displayendian ? (displaychunk - 1 - bytenum) : bytenum]); - printf(" "); - oprom += displaychunk; - } - printf("\n"); - } - } - } + // Next pc computation lambdas + std::function next_pc; + std::function next_pc_wrap; + if(flags & util::disasm_interface::NONLINEAR_PC) { + // lfsr pc is always paged + next_pc = [pc_mask, page_mask, dis = disasm.get()](offs_t pc, offs_t size) { + offs_t lpc = dis->pc_real_to_linear(pc); + offs_t lpce = lpc + size; + if((lpc ^ lpce) & ~page_mask) + lpce = (lpc | page_mask) + 1; + lpce &= pc_mask; + return dis->pc_linear_to_real(lpce); + }; + next_pc_wrap = [pc_mask, page_mask, dis = disasm.get()](offs_t pc, offs_t size) { + offs_t lpc = dis->pc_real_to_linear(pc); + offs_t lpce = (lpc & ~page_mask) | ((lpc + size) & page_mask); + return dis->pc_linear_to_real(lpce); + }; - // flipped case - else - { - // output the disassembly and address - printf("\t%-40s ; %08X", buffer.c_str(), curpc); - - // output the raw bytes - if (!opts.norawbytes) - { - int chunknum, bytenum; - printf(": "); - for (chunknum = 0; chunknum < numchunks; chunknum++) - { - for (bytenum = 0; bytenum < displaychunk; bytenum++) - printf("%02X", oprom[displayendian ? (displaychunk - 1 - bytenum) : bytenum]); - printf(" "); - oprom += displaychunk; - } - } - printf("\n"); - } + } else if(flags & util::disasm_interface::PAGED) { + next_pc = [pc_mask, page_mask](offs_t pc, offs_t size) { + offs_t pce = pc + size; + if((pc ^ pce) & ~page_mask) + pce = (pc | page_mask) + 1; + pce &= pc_mask; + return pce; + }; + next_pc_wrap = [pc_mask, page_mask](offs_t pc, offs_t size) { + offs_t pce = (pc & ~page_mask) | ((pc + size) & page_mask); + return pce; + }; - // advance - curpc += pcdelta; - } + } else { + next_pc = [pc_mask](offs_t pc, offs_t size) { + return (pc + size) & pc_mask; + }; + next_pc_wrap = [pc_mask](offs_t pc, offs_t size) { + return (pc + size) & pc_mask; + }; } - catch (emu_fatalerror &fatal) - { - fprintf(stderr, "%s\n", fatal.string()); - result = 1; - if (fatal.exitcode() != 0) - result = fatal.exitcode(); + + // Compute the shift amount from pc delta to granularity-sized elements + u32 granularity_shift = 31 - count_leading_zeros(disasm->opcode_alignment()); + + // Number of pc steps to disassemble + u32 count = pclength; + + if((count > opts.count) && (opts.count != 0)) + count = opts.count; + + // pc to string conversion + std::function pc_to_string; + int aw = 32 - count_leading_zeros(pc_mask); + bool is_octal = false; // Parameter? Per-cpu config? + if((flags & util::disasm_interface::PAGED2LEVEL) == util::disasm_interface::PAGED2LEVEL) { + int bits1 = disasm->page_address_bits(); + int bits2 = disasm->page2_address_bits(); + int bits3 = aw - bits1 - bits2; + offs_t sm1 = (1 << bits1) - 1; + int sh2 = bits1; + offs_t sm2 = (1 << bits2) - 1; + int sh3 = bits1+bits2; + + if(is_octal) { + int nc1 = (bits1+2)/3; + int nc2 = (bits2+2)/3; + int nc3 = (bits3+2)/3; + pc_to_string = [nc1, nc2, nc3, sm1, sm2, sh2, sh3](offs_t pc) -> std::string { + return util::string_format("%0*o:%0*o:%0*o", + nc3, pc >> sh3, + nc2, (pc >> sh2) & sm2, + nc1, pc & sm1); + }; + } else { + int nc1 = (bits1+3)/4; + int nc2 = (bits2+3)/4; + int nc3 = (bits3+3)/4; + pc_to_string = [nc1, nc2, nc3, sm1, sm2, sh2, sh3](offs_t pc) -> std::string { + return util::string_format("%0*x:%0*x:%0*x", + nc3, pc >> sh3, + nc2, (pc >> sh2) & sm2, + nc1, pc & sm1); + }; + } + + } else if(flags & util::disasm_interface::PAGED) { + int bits1 = disasm->page_address_bits(); + int bits2 = aw - bits1; + offs_t sm1 = (1 << bits1) - 1; + int sh2 = bits1; + + if(is_octal) { + int nc1 = (bits1+2)/3; + int nc2 = (bits2+2)/3; + pc_to_string = [nc1, nc2, sm1, sh2](offs_t pc) -> std::string { + return util::string_format("%0*o:%0*o", + nc2, pc >> sh2, + nc1, pc & sm1); + }; + } else { + int nc1 = (bits1+3)/4; + int nc2 = (bits2+3)/4; + pc_to_string = [nc1, nc2, sm1, sh2](offs_t pc) -> std::string { + return util::string_format("%0*x:%0*x", + nc2, pc >> sh2, + nc1, pc & sm1); + }; + } + + } else { + int bits1 = aw; + + if(is_octal) { + int nc1 = (bits1+2)/3; + pc_to_string = [nc1](offs_t pc) -> std::string { + return util::string_format("%0*o", + nc1, pc); + }; + } else { + int nc1 = (bits1+3)/4; + pc_to_string = [nc1](offs_t pc) -> std::string { + return util::string_format("%0*x", + nc1, pc); + }; + } } - catch (emu_exception &) - { - fprintf(stderr, "Caught unhandled emulator exception\n"); - result = 1; + + // Lower/upper optional transform + std::function tf; + if(opts.lower) + tf = [](const std::string &str) -> std::string { + std::string result = str; + std::transform(result.begin(), result.end(), result.begin(), [](char c) { return tolower(c); }); + return result; + }; + else if(opts.upper) + tf = [](const std::string &str) -> std::string { + std::string result = str; + std::transform(result.begin(), result.end(), result.begin(), [](char c) { return toupper(c); }); + return result; + }; + else + tf = [](const std::string &str) -> std::string { + return str; + }; + + + // Do the disassembly + std::vector dasm_lines; + offs_t curpc = opts.basepc; + for(u32 i=0; i < count;) { + std::ostringstream stream; + offs_t result = disasm->disassemble(stream, curpc, *popcodes, *pparams); + offs_t len = result & util::disasm_interface::LENGTHMASK; + dasm_lines.emplace_back(dasm_line{ curpc, len, stream.str() }); + curpc = next_pc(curpc, len); + i += len; } - catch (tag_add_exception &aex) - { - fprintf(stderr, "Tag '%s' already exists in tagged map\n", aex.tag()); - result = 1; + + // Compute the extrema + offs_t max_len = 0; + size_t max_text = 0; + for(const auto &l : dasm_lines) { + if(max_len < l.size) + max_len = l.size; + size_t s = l.dasm.size(); + if(max_text < s) + max_text = s; } - catch (std::exception &ex) - { - fprintf(stderr, "Caught unhandled %s exception: %s\n", typeid(ex).name(), ex.what()); - result = 1; + + // Build the raw bytes generator and compute the field size + max_len >>= granularity_shift; + std::function dump_raw_bytes; + + switch(granularity) { + case 1: + dump_raw_bytes = [step = disasm->opcode_alignment(), next_pc, base_buffer](offs_t pc, offs_t size) -> std::string { + std::string result = ""; + for(offs_t i=0; i != size; i++) { + if(i) + result += ' '; + result += util::string_format("%02x", base_buffer.r8(pc)); + pc = next_pc(pc, step); + } + return result; + }; + max_len = (max_len * 3) - 1; + break; + + case 2: + dump_raw_bytes = [step = disasm->opcode_alignment(), next_pc, base_buffer](offs_t pc, offs_t size) -> std::string { + std::string result = ""; + for(offs_t i=0; i != size; i++) { + if(i) + result += ' '; + result += util::string_format("%04x", base_buffer.r16(pc)); + pc = next_pc(pc, step); + } + return result; + }; + max_len = (max_len * 5) - 1; + break; + + case 4: + dump_raw_bytes = [step = disasm->opcode_alignment(), next_pc, base_buffer](offs_t pc, offs_t size) -> std::string { + std::string result = ""; + for(offs_t i=0; i != size; i++) { + if(i) + result += ' '; + result += util::string_format("%08x", base_buffer.r32(pc)); + pc = next_pc(pc, step); + } + return result; + }; + max_len = (max_len * 9) - 1; + break; + + case 8: + dump_raw_bytes = [step = disasm->opcode_alignment(), next_pc, base_buffer](offs_t pc, offs_t size) -> std::string { + std::string result = ""; + for(offs_t i=0; i != size; i++) { + if(i) + result += ' '; + result += util::string_format("%016x", base_buffer.r64(pc)); + pc = next_pc(pc, step); + } + return result; + }; + max_len = (max_len * 17) - 1; + break; } - catch (...) - { - fprintf(stderr, "Caught unhandled exception\n"); - result = 1; + + if(opts.flipped) { + if(opts.norawbytes) + for(const auto &l : dasm_lines) + util::stream_format(std::cout, "%-*s ; %s\n", max_text, tf(l.dasm), tf(pc_to_string(l.pc))); + else + for(const auto &l : dasm_lines) + util::stream_format(std::cout, "%-*s ; %s: %s\n", max_text, tf(l.dasm), tf(pc_to_string(l.pc)), tf(dump_raw_bytes(l.pc, l.size >> granularity_shift))); + } else { + if(opts.norawbytes) + for(const auto &l : dasm_lines) + util::stream_format(std::cout, "%s: %s\n", tf(pc_to_string(l.pc)), tf(l.dasm)); + else + for(const auto &l : dasm_lines) + util::stream_format(std::cout, "%s: %-*s %s\n", tf(pc_to_string(l.pc)), max_len, tf(dump_raw_bytes(l.pc, l.size >> granularity_shift)), tf(l.dasm)); } free(data); - return result; + return 0; } -- cgit v1.2.3