summaryrefslogtreecommitdiffstatshomepage
path: root/src/devices/cpu/ks0164/ks0164d.cpp
blob: 2a357e9f70ee154e67d19dd63a5ce2cc2c59eee1 (plain) (blame)
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
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
// license:BSD-3-Clause
// copyright-holders:Olivier Galibert, David Carne

// KS0164 disassembler

#include "emu.h"
#include "ks0164d.h"

u32 ks0164_disassembler::opcode_alignment() const
{
	return 2;
}

const char *const ks0164_disassembler::regs[8] = {
	"r0", "r1", "r2", "r3", "sp", "psw", "pc", "zero"
};

s32 ks0164_disassembler::off10(u32 opcode)
{
	return opcode & 0x200 ? opcode | 0xfffffc00 : opcode & 0x3ff;
}

std::string ks0164_disassembler::off16(s16 dt)
{
	return dt < 0 ? util::string_format(" - %x", -dt) : dt ? util::string_format(" + %x", dt) : "";
}

#define P std::ostream &stream, u32 opcode, const data_buffer &opcodes, u32 pc
const ks0164_disassembler::instruction ks0164_disassembler::instructions[] {
	{ 0x0000, 0xfc00, [](P) -> u32 { util::stream_format(stream, "bne %04x", (pc + 2 + off10(opcode)) & 0xffff); return 2; } },
	{ 0x0400, 0xfc00, [](P) -> u32 { util::stream_format(stream, "beq %04x", (pc + 2 + off10(opcode)) & 0xffff); return 2; } },
	{ 0x0800, 0xfc00, [](P) -> u32 { util::stream_format(stream, "b?2 %04x", (pc + 2 + off10(opcode)) & 0xffff); return 2; } },
	{ 0x0c00, 0xfc00, [](P) -> u32 { util::stream_format(stream, "b?3 %04x", (pc + 2 + off10(opcode)) & 0xffff); return 2; } },
	{ 0x1000, 0xfc00, [](P) -> u32 { util::stream_format(stream, "b?4 %04x", (pc + 2 + off10(opcode)) & 0xffff); return 2; } },
	{ 0x1400, 0xfc00, [](P) -> u32 { util::stream_format(stream, "b?5 %04x", (pc + 2 + off10(opcode)) & 0xffff); return 2; } },
	{ 0x1800, 0xfc00, [](P) -> u32 { util::stream_format(stream, "b?6 %04x", (pc + 2 + off10(opcode)) & 0xffff); return 2; } },
	{ 0x1c00, 0xfc00, [](P) -> u32 { util::stream_format(stream, "b?7 %04x", (pc + 2 + off10(opcode)) & 0xffff); return 2; } },
	{ 0x2000, 0xfc00, [](P) -> u32 { util::stream_format(stream, "b?8 %04x", (pc + 2 + off10(opcode)) & 0xffff); return 2; } },
	{ 0x2400, 0xfc00, [](P) -> u32 { util::stream_format(stream, "b?9 %04x", (pc + 2 + off10(opcode)) & 0xffff); return 2; } },
	{ 0x2800, 0xfc00, [](P) -> u32 { util::stream_format(stream, "b?a %04x", (pc + 2 + off10(opcode)) & 0xffff); return 2; } },
	{ 0x2c00, 0xfc00, [](P) -> u32 { util::stream_format(stream, "b?b %04x", (pc + 2 + off10(opcode)) & 0xffff); return 2; } },
	{ 0x3000, 0xfc00, [](P) -> u32 { util::stream_format(stream, "b?c %04x", (pc + 2 + off10(opcode)) & 0xffff); return 2; } },
	{ 0x3400, 0xfc00, [](P) -> u32 { util::stream_format(stream, "b?d %04x", (pc + 2 + off10(opcode)) & 0xffff); return 2; } },
	{ 0x3800, 0xfc00, [](P) -> u32 { util::stream_format(stream, "blt %04x", (pc + 2 + off10(opcode)) & 0xffff); return 2; } },
	{ 0x3c00, 0xfc00, [](P) -> u32 { util::stream_format(stream, "bra %04x", (pc + 2 + off10(opcode)) & 0xffff); return 2; } },

	{ 0x4000, 0xf800, [](P) -> u32 { util::stream_format(stream, "%s.w += %02x",   regs[(opcode >> 8) & 7], opcode & 0xff); return 2; } },
	{ 0x4800, 0xf800, [](P) -> u32 { util::stream_format(stream, "%s.w -= %02x",   regs[(opcode >> 8) & 7], opcode & 0xff); return 2; } },
	{ 0x5000, 0xf800, [](P) -> u32 { util::stream_format(stream, "cmp %s.w, %02x", regs[(opcode >> 8) & 7], opcode & 0xff); return 2; } },
	{ 0x5800, 0xf800, [](P) -> u32 { util::stream_format(stream, "%s.w &= %02x",   regs[(opcode >> 8) & 7], opcode & 0xff); return 2; } },
	{ 0x6000, 0xf800, [](P) -> u32 { util::stream_format(stream, "%s.w |= %02x",   regs[(opcode >> 8) & 7], opcode & 0xff); return 2; } },
	{ 0x6800, 0xf800, [](P) -> u32 { util::stream_format(stream, "%s.w ?5 %02x",   regs[(opcode >> 8) & 7], opcode & 0xff); return 2; } },
	{ 0x7000, 0xf800, [](P) -> u32 { util::stream_format(stream, "%s.w = %02x",    regs[(opcode >> 8) & 7], opcode & 0xff); return 2; } },
	{ 0x7800, 0xf800, [](P) -> u32 { util::stream_format(stream, "%s.w ?7 %02x",   regs[(opcode >> 8) & 7], opcode & 0xff); return 2; } },

	{ 0x8004, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b += %s.b",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0x800c, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w += %s.w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0x8804, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b -= %s.b",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0x880c, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w -= %s.w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0x9004, 0xf88f, [](P) -> u32 { util::stream_format(stream, "cmp %s.b, %s.b", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0x900c, 0xf88f, [](P) -> u32 { util::stream_format(stream, "cmp %s.w, %s.w", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0x9804, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b &= %s.b",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0x980c, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w &= %s.w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xa004, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b |= %s.b",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xa00c, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w |= %s.w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xa804, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b ?5 %s.b",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xa80c, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w ?5 %s.w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xb004, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b = %s.b",    regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xb00c, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w = %s.w",    regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xb804, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b ?7 %s.b",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xb80c, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w ?7 %s.w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },

	{ 0x8075, 0xf8ff, [](P) -> u32 { u16 imm = opcodes.r16(pc+2); util::stream_format(stream, "%s.b += %02x",   regs[(opcode >> 8) & 7], imm); return 4; } },
	{ 0x807d, 0xf8ff, [](P) -> u32 { u16 imm = opcodes.r16(pc+2); util::stream_format(stream, "%s.w += %04x",   regs[(opcode >> 8) & 7], imm); return 4; } },
	{ 0x8875, 0xf8ff, [](P) -> u32 { u16 imm = opcodes.r16(pc+2); util::stream_format(stream, "%s.b -= %02x",   regs[(opcode >> 8) & 7], imm); return 4; } },
	{ 0x887d, 0xf8ff, [](P) -> u32 { u16 imm = opcodes.r16(pc+2); util::stream_format(stream, "%s.w -= %04x",   regs[(opcode >> 8) & 7], imm); return 4; } },
	{ 0x9075, 0xf8ff, [](P) -> u32 { u16 imm = opcodes.r16(pc+2); util::stream_format(stream, "cmp %s.b, %02x", regs[(opcode >> 8) & 7], imm); return 4; } },
	{ 0x907d, 0xf8ff, [](P) -> u32 { u16 imm = opcodes.r16(pc+2); util::stream_format(stream, "cmp %s.w, %04x", regs[(opcode >> 8) & 7], imm); return 4; } },
	{ 0x9875, 0xf8ff, [](P) -> u32 { u16 imm = opcodes.r16(pc+2); util::stream_format(stream, "%s.b &= %02x",   regs[(opcode >> 8) & 7], imm); return 4; } },
	{ 0x987d, 0xf8ff, [](P) -> u32 { u16 imm = opcodes.r16(pc+2); util::stream_format(stream, "%s.w &= %04x",   regs[(opcode >> 8) & 7], imm); return 4; } },
	{ 0xa075, 0xf8ff, [](P) -> u32 { u16 imm = opcodes.r16(pc+2); util::stream_format(stream, "%s.b |= %02x",   regs[(opcode >> 8) & 7], imm); return 4; } },
	{ 0xa07d, 0xf8ff, [](P) -> u32 { u16 imm = opcodes.r16(pc+2); util::stream_format(stream, "%s.w |= %04x",   regs[(opcode >> 8) & 7], imm); return 4; } },
	{ 0xa875, 0xf8ff, [](P) -> u32 { u16 imm = opcodes.r16(pc+2); util::stream_format(stream, "%s.b ?5 %02x",   regs[(opcode >> 8) & 7], imm); return 4; } },
	{ 0xa87d, 0xf8ff, [](P) -> u32 { u16 imm = opcodes.r16(pc+2); util::stream_format(stream, "%s.w ?5 %04x",   regs[(opcode >> 8) & 7], imm); return 4; } },
	{ 0xb075, 0xf8ff, [](P) -> u32 { u16 imm = opcodes.r16(pc+2); util::stream_format(stream, "%s.b = %02x",    regs[(opcode >> 8) & 7], imm); return 4; } },
	{ 0xb07d, 0xf8ff, [](P) -> u32 { u16 imm = opcodes.r16(pc+2); util::stream_format(stream, "%s.w = %04x",    regs[(opcode >> 8) & 7], imm); return 4; } },
	{ 0xb875, 0xf8ff, [](P) -> u32 { u16 imm = opcodes.r16(pc+2); util::stream_format(stream, "%s.b ?7 %02x",   regs[(opcode >> 8) & 7], imm); return 4; } },
	{ 0xb87d, 0xf8ff, [](P) -> u32 { u16 imm = opcodes.r16(pc+2); util::stream_format(stream, "%s.w ?7 %04x",   regs[(opcode >> 8) & 7], imm); return 4; } },

	{ 0x8006, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b += (%s).b",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0x800e, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w += (%s).w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0x8806, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b -= (%s).b",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0x880e, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w -= (%s).w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0x9006, 0xf88f, [](P) -> u32 { util::stream_format(stream, "cmp %s.b, (%s).b", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0x900e, 0xf88f, [](P) -> u32 { util::stream_format(stream, "cmp %s.w, (%s).w", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0x9806, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b &= (%s).b",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0x980e, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w &= (%s).w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xa006, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b |= (%s).b",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xa00e, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w |= (%s).w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xa806, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b ?5 (%s).b",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xa80e, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w ?5 (%s).w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xb006, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b = (%s).b",    regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xb00e, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w = (%s).w",    regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xb806, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b ?7 (%s).b",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xb80e, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w ?7 (%s).w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },

	{ 0x8077, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s.b += (%04x).b",   regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } },
	{ 0x807f, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s.w += (%04x).w",   regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } },
	{ 0x8877, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s.b -= (%04x).b",   regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } },
	{ 0x887f, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s.w -= (%04x).w",   regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } },
	{ 0x9077, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "cmp %s.b, (%04x).b", regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } },
	{ 0x907f, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "cmp %s.w, (%04x).w", regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } },
	{ 0x9877, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s.b &= (%04x).b",   regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } },
	{ 0x987f, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s.w &= (%04x).w",   regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } },
	{ 0xa077, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s.b |= (%04x).b",   regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } },
	{ 0xa07f, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s.w |= (%04x).w",   regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } },
	{ 0xa877, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s.b ?5 (%04x).b",   regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } },
	{ 0xa87f, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s.w ?5 (%04x).w",   regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } },
	{ 0xb077, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s.b = (%04x).b",    regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } },
	{ 0xb07f, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s.w = (%04x).w",    regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } },
	{ 0xb877, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s.b ?7 (%04x).b",   regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } },
	{ 0xb87f, 0xf8ff, [](P) -> u32 { util::stream_format(stream, "%s.w ?7 (%04x).w",   regs[(opcode >> 8) & 7], opcodes.r16(pc+2)); return 4; } },

	{ 0x8007, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b += (%s%s).b",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } },
	{ 0x800f, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w += (%s%s).w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } },
	{ 0x8807, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b -= (%s%s).b",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } },
	{ 0x880f, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w -= (%s%s).w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } },
	{ 0x9007, 0xf88f, [](P) -> u32 { util::stream_format(stream, "cmp %s.b, (%s%s).b", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } },
	{ 0x900f, 0xf88f, [](P) -> u32 { util::stream_format(stream, "cmp %s.w, (%s%s).w", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } },
	{ 0x9807, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b &= (%s%s).b",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } },
	{ 0x980f, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w &= (%s%s).w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } },
	{ 0xa007, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b |= (%s%s).b",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } },
	{ 0xa00f, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w |= (%s%s).w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } },
	{ 0xa807, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b ?5 (%s%s).b",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } },
	{ 0xa80f, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w ?5 (%s%s).w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } },
	{ 0xb007, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b = (%s%s).b",    regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } },
	{ 0xb00f, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w = (%s%s).w",    regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } },
	{ 0xb807, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.b ?7 (%s%s).b",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } },
	{ 0xb80f, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w ?7 (%s%s).w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7], off16(opcodes.r16(pc+2))); return 4; } },

	{ 0xc000, 0xf88f, [](P) -> u32 { util::stream_format(stream, "-(%s).w = %s.w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xc001, 0xffff, [](P) -> u32 { util::stream_format(stream, "push?"); return 2; } },
	{ 0xc003, 0xffff, [](P) -> u32 { util::stream_format(stream, "pop?"); return 2; } },
	{ 0xc008, 0xf88f, [](P) -> u32 { util::stream_format(stream, "(%s)+.w = %s.w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xc00a, 0xf88f, [](P) -> u32 { util::stream_format(stream, "%s.w = (%s)+.w",   regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },

	{ 0xc00c, 0xf80f, [](P) -> u32 { util::stream_format(stream, "%s.w <<= %x",   regs[(opcode >> 8) & 7], (opcode >> 4) & 0xf); return 2; } },
	{ 0xc80c, 0xf80f, [](P) -> u32 { util::stream_format(stream, "%s.w >>= %x",   regs[(opcode >> 8) & 7], (opcode >> 4) & 0xf); return 2; } },

	{ 0xd001, 0xffff, [](P) -> u32 { util::stream_format(stream, "jmp %04x", opcodes.r16(pc+2)); return 4; } },
	{ 0xd002, 0xffff, [](P) -> u32 { util::stream_format(stream, "jsr %04x", opcodes.r16(pc+2)); return 4; } },
	{ 0xd003, 0xffff, [](P) -> u32 { util::stream_format(stream, "rts"); return 2; } },
	{ 0xd004, 0xffff, [](P) -> u32 { util::stream_format(stream, "rti"); return 2; } },

	{ 0xe000, 0xf80f, [](P) -> u32 { util::stream_format(stream, "btst %s.b, %x",     regs[(opcode >> 8) & 7], (opcode >> 4) & 0xf); return 2; } },
	{ 0xe008, 0xf80f, [](P) -> u32 { util::stream_format(stream, "btst %s.w, %x",     regs[(opcode >> 8) & 7], (opcode >> 4) & 0xf); return 2; } },
	{ 0xe001, 0xf80f, [](P) -> u32 { util::stream_format(stream, "bset %s.b, %x",     regs[(opcode >> 8) & 7], (opcode >> 4) & 0xf); return 2; } },
	{ 0xe009, 0xf80f, [](P) -> u32 { util::stream_format(stream, "bset %s.w, %x",     regs[(opcode >> 8) & 7], (opcode >> 4) & 0xf); return 2; } },
	{ 0xe002, 0xf80f, [](P) -> u32 { util::stream_format(stream, "btst (%s).b, %x",   regs[(opcode >> 8) & 7], (opcode >> 4) & 0xf); return 2; } },
	{ 0xe00a, 0xf80f, [](P) -> u32 { util::stream_format(stream, "btst (%s).w, %x",   regs[(opcode >> 8) & 7], (opcode >> 4) & 0xf); return 2; } },
	{ 0xe703, 0xff0f, [](P) -> u32 { util::stream_format(stream, "btst (%04x).b, %x", opcodes.r16(pc+2), (opcode >> 4) & 0xf); return 4; } },
	{ 0xe70b, 0xff0f, [](P) -> u32 { util::stream_format(stream, "btst (%04x).w, %x", opcodes.r16(pc+2), (opcode >> 4) & 0xf); return 4; } },
	{ 0xe003, 0xf80f, [](P) -> u32 { util::stream_format(stream, "btst (%s%s).b, %x", regs[(opcode >> 8) & 7], off16(opcodes.r16(pc+2)), (opcode >> 4) & 0xf); return 4; } },
	{ 0xe00b, 0xf80f, [](P) -> u32 { util::stream_format(stream, "btst (%s%s).w, %x", regs[(opcode >> 8) & 7], off16(opcodes.r16(pc+2)), (opcode >> 4) & 0xf); return 4; } },
	{ 0xe004, 0xf80f, [](P) -> u32 { util::stream_format(stream, "bclr %s.b, %x",     regs[(opcode >> 8) & 7], (opcode >> 4) & 0xf); return 2; } },
	{ 0xe00c, 0xf80f, [](P) -> u32 { util::stream_format(stream, "bclr %s.w, %x",     regs[(opcode >> 8) & 7], (opcode >> 4) & 0xf); return 2; } },
	{ 0xe006, 0xf88f, [](P) -> u32 { util::stream_format(stream, "(%s).b = %s.b",     regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xe00e, 0xf88f, [](P) -> u32 { util::stream_format(stream, "(%s).w = %s.w",     regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]); return 2; } },
	{ 0xe707, 0xff8f, [](P) -> u32 { util::stream_format(stream, "(%04x).b = %s.b",   opcodes.r16(pc+2), regs[(opcode >> 4) & 7]); return 4; } },
	{ 0xe70f, 0xff8f, [](P) -> u32 { util::stream_format(stream, "(%04x).w = %s.w",   opcodes.r16(pc+2), regs[(opcode >> 4) & 7]); return 4; } },
	{ 0xe007, 0xf88f, [](P) -> u32 { util::stream_format(stream, "(%s%s).b = %s.b",   regs[(opcode >> 8) & 7], off16(opcodes.r16(pc+2)), regs[(opcode >> 4) & 7]); return 4; } },
	{ 0xe00f, 0xf88f, [](P) -> u32 { util::stream_format(stream, "(%s%s).w = %s.w",   regs[(opcode >> 8) & 7], off16(opcodes.r16(pc+2)), regs[(opcode >> 4) & 7]); return 4; } },


	{ 0x0000, 0x0000, [](P) -> u32 { util::stream_format(stream, "?%04x",   opcode); return 2; } },
};

#undef P

offs_t ks0164_disassembler::disassemble(std::ostream &stream, offs_t pc, const data_buffer &opcodes, const data_buffer &params)
{
	u32 opcode = opcodes.r16(pc);

	for(u32 i=0;; i++)
		if((opcode & instructions[i].mask) == instructions[i].value)
			return instructions[i].cb(stream, opcode, opcodes, pc);

	abort();

#if 0
	} else if((opcode & 0xf80f) == 0xc800) // c808?
		util::stream_format(stream, "store.w -(%s), %s", regs[(opcode >> 4) & 7], regs[(opcode >> 7) & 7]);

	else if(  (opcode & 0xf88f) == 0xc00a)
		util::stream_format(stream, "load.w %s, (%s)+ ?2", regs[(opcode >> 8) & 7], regs[(opcode >> 4) & 7]);

#endif
}