6 // (c) 2004, 2014 Underground Software
20 //NO MORE!!! extern V6809REGS mainCPU;//Hm.
22 static char op_mat1[256] = {
23 1, 0, 0, 1, 1, 0, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1,
24 0, 0, 5, 5, 0, 0, 4, 4, 0, 5, 8, 0, 8, 5, 6, 6,
25 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3,
26 7, 7, 7, 7, 6, 6, 6, 6, 0, 5, 5, 5, 8, 5, 5, 5,
27 5, 0, 0, 5, 5, 0, 5, 5, 5, 5, 5, 0, 5, 5, 0, 5,
28 5, 0, 0, 5, 5, 0, 5, 5, 5, 5, 5, 0, 5, 5, 0, 5,
29 7, 0, 0, 7, 7, 0, 7, 7, 7, 7, 7, 0, 7, 7, 7, 7,
30 2, 0, 0, 2, 2, 0, 2, 2, 2, 2, 2, 0, 2, 2, 2, 2,
31 8, 8, 8, 9, 8, 8, 8, 0, 8, 8, 8, 8, 9, 3, 9, 0,
32 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
33 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
34 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
35 8, 8, 8, 9, 8, 8, 8, 0, 8, 8, 8, 8, 9, 0, 9, 0,
36 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
37 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
38 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2
42 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
43 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
44 0, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4,
45 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5,
46 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
47 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
48 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
49 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
50 0, 0, 0, 9, 0, 0, 0, 0, 0, 0, 0, 0, 9, 0, 9, 0,
51 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1,
52 0, 0, 0, 7, 0, 0, 0, 0, 0, 0, 0, 0, 7, 0, 7, 7,
53 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, 2, 2,
54 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 9, 0,
55 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1,
56 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 7,
57 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 2
61 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
62 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
63 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
64 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5,
65 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
66 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
67 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
68 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
69 0, 0, 0, 9, 0, 0, 0, 0, 0, 0, 0, 0, 9, 0, 0, 0,
70 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0,
71 0, 0, 0, 7, 0, 0, 0, 0, 0, 0, 0, 0, 7, 0, 0, 0,
72 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0,
73 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
74 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
75 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
76 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
79 static char mnemonics[256][6] = {
80 "NEG ","??? ","??? ","COM ","LSR ","??? ","ROR ","ASR ",
81 "LSL ","ROL ","DEC ","??? ","INC ","TST ","JMP ","CLR ",
82 "PAGE1","PAGE2","NOP ","SYNC ","??? ","??? ","LBRA ","LBSR ",
83 "??? ","DAA ","ORCC ","??? ","ANDCC","SEX ","EXG ","TFR ",
84 "BRA ","BRN ","BHI ","BLS ","BHS ","BLO ","BNE ","BEQ ",
85 "BVC ","BVS ","BPL ","BMI ","BGE ","BLT ","BGT ","BLE ",
86 "LEAX ","LEAY ","LEAS ","LEAU ","PSHS ","PULS ","PSHU ","PULU ",
87 "??? ","RTS ","ABX ","RTI ","CWAI ","MUL ","RESET","SWI ",
88 "NEGA ","??? ","??? ","COMA ","LSRA ","??? ","RORA ","ASRA ",
89 "LSLA ","ROLA ","DECA ","??? ","INCA ","TSTA ","??? ","CLRA ",
90 "NEGB ","??? ","??? ","COMB ","LSRB ","??? ","RORB ","ASRB ",
91 "LSLB ","ROLB ","DECB ","??? ","INCB ","TSTB ","??? ","CLRB ",
92 "NEG ","??? ","??? ","COM ","LSR ","??? ","ROR ","ASR ",
93 "LSL ","ROL ","DEC ","??? ","INC ","TST ","JMP ","CLR ",
94 "NEG ","??? ","??? ","COM ","LSR ","??? ","ROR ","ASR ",
95 "LSL ","ROL ","DEC ","??? ","INC ","TST ","JMP ","CLR ",
96 "SUBA ","CMPA ","SCBA ","SUBD ","ANDA ","BITA ","LDA ","??? ",
97 "EORA ","ADCA ","ORA ","ADDA ","CMPX ","BSR ","LDX ","??? ",
98 "SUBA ","CMPA ","SBCA ","SUBD ","ANDA ","BITA ","LDA ","STA ",
99 "EORA ","ADCA ","ORA ","ADDA ","CMPX ","JSR ","LDX ","STX ",
100 "SUBA ","CMPA ","SBCA ","SUBD ","ANDA ","BITA ","LDA ","STA ",
101 "EORA ","ADCA ","ORA ","ADDA ","CMPX ","JSR ","LDX ","STX ",
102 "SUBA ","CMPA ","SBCA ","SUBD ","ANDA ","BITA ","LDA ","STA ",
103 "EORA ","ADCA ","ORA ","ADDA ","CMPX ","JSR ","LDX ","STX ",
104 "SUBB ","CMPB ","SCBB ","ADDD ","ANDB ","BITB ","LDB ","??? ",
105 "EORB ","ADCB ","ORB ","ADDB ","LDD ","??? ","LDU ","??? ",
106 "SUBB ","CMPB ","SBCB ","ADDD ","ANDB ","BITB ","LDB ","STB ",
107 "EORB ","ADCB ","ORB ","ADDB ","LDD ","STD ","LDU ","STU ",
108 "SUBB ","CMPB ","SBCB ","ADDD ","ANDB ","BITB ","LDB ","STB ",
109 "EORB ","ADCB ","ORB ","ADDB ","LDD ","STD ","LDU ","STU ",
110 "SUBB ","CMPB ","SBCB ","ADDD ","ANDB ","BITB ","LDB ","STB ",
111 "EORB ","ADCB ","ORB ","ADDB ","LDD ","STD ","LDU ","STU "
114 mnemonics2[256][6] = {
115 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
116 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
117 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
118 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
119 "??? ","LBRN ","LBHI ","LBLS ","LBHS ","LBLO ","LBNE ","LBEQ ",
120 "LBVC ","LBVS ","LBPL ","LBMI ","LBGE ","LBLT ","LBGT ","LBLE ",
121 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
122 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","SWI2 ",
123 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
124 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
125 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
126 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
127 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
128 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
129 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
130 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
131 "??? ","??? ","??? ","CMPD ","??? ","??? ","??? ","??? ",
132 "??? ","??? ","??? ","??? ","CMPY ","??? ","LDY ","??? ",
133 "??? ","??? ","??? ","CMPD ","??? ","??? ","??? ","??? ",
134 "??? ","??? ","??? ","??? ","CMPY ","??? ","LDY ","STY ",
135 "??? ","??? ","??? ","CMPD ","??? ","??? ","??? ","??? ",
136 "??? ","??? ","??? ","??? ","CMPY ","??? ","LDY ","STY ",
137 "??? ","??? ","??? ","CMPD ","??? ","??? ","??? ","??? ",
138 "??? ","??? ","??? ","??? ","CMPY ","??? ","LDY ","STY ",
139 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
140 "??? ","??? ","??? ","??? ","??? ","??? ","LDS ","??? ",
141 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
142 "??? ","??? ","??? ","??? ","??? ","??? ","LDS ","STS ",
143 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
144 "??? ","??? ","??? ","??? ","??? ","??? ","LDS ","STS ",
145 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
146 "??? ","??? ","??? ","??? ","??? ","??? ","LDS ","STS "
149 mnemonics3[256][6] = {
150 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
151 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
152 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
153 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
154 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
155 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
156 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
157 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","SWI3 ",
158 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
159 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
160 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
161 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
162 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
163 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
164 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
165 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
166 "??? ","??? ","??? ","CMPU ","??? ","??? ","??? ","??? ",
167 "??? ","??? ","??? ","??? ","CMPS ","??? ","??? ","??? ",
168 "??? ","??? ","??? ","CMPU ","??? ","??? ","??? ","??? ",
169 "??? ","??? ","??? ","??? ","CMPS ","??? ","??? ","??? ",
170 "??? ","??? ","??? ","CMPU ","??? ","??? ","??? ","??? ",
171 "??? ","??? ","??? ","??? ","CMPS ","??? ","??? ","??? ",
172 "??? ","??? ","??? ","CMPU ","??? ","??? ","??? ","??? ",
173 "??? ","??? ","??? ","??? ","CMPS ","??? ","??? ","??? ",
174 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
175 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
176 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
177 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
178 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
179 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
180 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? ",
181 "??? ","??? ","??? ","??? ","??? ","??? ","??? ","??? "
185 "D", "X", "Y", "U", "S", "PC", "??", "??",
186 "A", "B", "CC", "DP", "??", "??", "??", "??"
189 iregs[4][2] = {"X", "Y", "U", "S" };
192 // Display bytes in mem in hex
194 static void DisplayBytes(V6809REGS regs, uint16_t src, uint32_t dst)
196 WriteLog("%04X: ", src);
197 uint8_t cnt = 0; // Init counter...
200 dst += 0x10000; // That should fix the FFFF bug...
202 for(uint32_t i=src; i<dst; i++)
204 WriteLog("%02X ", regs.RdMem(i));
205 cnt++; // Bump counter...
208 for(int i=cnt; i<5; i++) // Pad the leftover spaces...
213 // Decode a 6809 instruction at 'addr'
215 //int Decode6809(uint16_t pc)
216 int Decode6809(V6809REGS regs)
218 char outbuf[80], mnem[6], tmp[30];
219 uint8_t opcode2, operand;
221 uint16_t addr = regs.pc, offset;
223 uint8_t opcode = regs.RdMem(addr++); // Get the opcode
224 uint8_t admode = op_mat1[opcode]; // addressing mode
225 strcpy(mnem, mnemonics[opcode]); // Copy page 1 opcode
227 if (opcode == 0x10) // Extended opcode?
229 opcode2 = regs.RdMem(addr++); // Then get next byte
230 admode = op_mat2[opcode2]; // And use it as index into 'op_mat2'
231 strcpy(mnem, mnemonics2[opcode2]); // Overwrite mnemonic
233 else if (opcode == 0x11) // Same as above...
235 opcode2 = regs.RdMem(addr++);
236 admode = op_mat3[opcode2];
237 strcpy(mnem, mnemonics3[opcode2]); // Overwrite mnemonic
240 switch (admode) // Decode it...
243 sprintf(outbuf, "???");
246 sprintf(outbuf, "%s $%02X", mnem, regs.RdMem(addr++));
249 // sprintf(outbuf, "%s $%04X", mnem, (regs.RdMem(addr++) << 8) | regs.RdMem(addr++));
250 offset = (regs.RdMem(addr) << 8) | regs.RdMem(addr + 1);
252 sprintf(outbuf, "%s $%04X", mnem, offset);
256 // sprintf(outbuf, "%s $%04X", mnem, ++addr + (int16_t)((int8_t)regs.RdMem(addr)));
257 offset = addr + 1 + (int16_t)(int8_t)regs.RdMem(addr);
259 sprintf(outbuf, "%s $%04X", mnem, offset);
261 case 4: // Long Relative
262 // sprintf(outbuf, "%s $%04X", mnem, addr + (int16_t)((regs.RdMem(addr++) << 8) | regs.RdMem(addr++)) + 2);
263 offset = addr + (int16_t)((regs.RdMem(addr) << 8) | regs.RdMem(addr + 1)) + 2;
265 sprintf(outbuf, "%s $%04X", mnem, offset);
268 sprintf(outbuf, "%s ", mnem);
270 case 6: // Txfr/exchg/push/pull
271 operand = regs.RdMem(addr++); // Get txfr/exg/push/pull byte
272 if ((opcode == 0x1E) || (opcode == 0x1F)) // Is it TXF/EXG?
273 sprintf(tmp, "%s,%s", tregs[operand >> 4], tregs[operand & 0x0F]);
277 if (operand & 0x01) strcat(tmp, "CC ");
278 if (operand & 0x02) strcat(tmp, "A ");
279 if (operand & 0x04) strcat(tmp, "B ");
280 if (operand & 0x08) strcat(tmp, "DP ");
281 if (operand & 0x10) strcat(tmp, "X ");
282 if (operand & 0x20) strcat(tmp, "Y ");
283 if (operand & 0x40) (((opcode == 0x34) || (opcode == 0x35)) ? strcat(tmp, "U ") : strcat(tmp, "S "));
284 if (operand & 0x80) strcat(tmp, "PC");
287 sprintf(outbuf, "%s %s", mnem, tmp);
289 case 7: // Indexed (the tough one!)
291 operand = regs.RdMem(addr++); // Get IDX byte
292 uint8_t reg = ((operand & 0x60) >> 5), idxind = ((operand & 0x10) >> 4),
293 lo_nyb = (operand & 0x0F), boff;
297 if (!(operand & 0x80)) // Hi bit set? Then decode 4 bit offset
298 sprintf(tmp, "(%d),%s", (idxind ? -(16-lo_nyb) : lo_nyb), iregs[reg]);
299 else // Add the ($nnnn,R) code dude...
305 case 1: sprintf(tmp, "(,%s++)", iregs[reg]); break;
306 case 3: sprintf(tmp, "(,--%s)", iregs[reg]); break;
307 case 4: sprintf(tmp, "(,%s)", iregs[reg]); break;
308 case 5: sprintf(tmp, "(B,%s)", iregs[reg]); break;
309 case 6: sprintf(tmp, "(A,%s)", iregs[reg]); break;
311 boff = regs.RdMem(addr++);
312 sprintf(tmp, "($%02X,%s)", boff, iregs[reg]);
315 woff = (regs.RdMem(addr) << 8) | regs.RdMem(addr + 1);
317 sprintf(tmp, "($%04X,%s)", woff, iregs[reg]);
319 case 11: sprintf(tmp, "(D,%s)", iregs[reg]); break;
321 boff = regs.RdMem(addr++);
322 sprintf(tmp, "($%02X,PC)", boff);
325 woff = (regs.RdMem(addr) << 8) | regs.RdMem(addr + 1);
327 sprintf(tmp, "($%04X,PC)", woff);
330 woff = (regs.RdMem(addr) << 8) | regs.RdMem(addr + 1);
332 sprintf(tmp, "[$%04X]", woff);
342 case 0: sprintf(tmp, ",%s+", iregs[reg]); break;
343 case 1: sprintf(tmp, ",%s++", iregs[reg]); break;
344 case 2: sprintf(tmp, ",-%s", iregs[reg]); break;
345 case 3: sprintf(tmp, ",--%s", iregs[reg]); break;
346 case 4: sprintf(tmp, ",%s", iregs[reg]); break;
347 case 5: sprintf(tmp, "(B),%s", iregs[reg]); break;
348 case 6: sprintf(tmp, "(A),%s", iregs[reg]); break;
350 boff = regs.RdMem(addr++);
351 sprintf(tmp, "($%02X),%s", boff, iregs[reg]);
354 woff = (regs.RdMem(addr) << 8) | regs.RdMem(addr + 1);
356 sprintf(tmp, "($%04X),%s", woff, iregs[reg]);
359 sprintf(tmp, "(D),%s", iregs[reg]);
362 boff = regs.RdMem(addr++);
363 sprintf(tmp, "($%02X),PC", boff);
366 woff = (regs.RdMem(addr) << 8) | regs.RdMem(addr + 1);
368 sprintf(tmp, "($%04X),PC", woff);
375 sprintf(outbuf, "%s %s", mnem, tmp);
379 sprintf(outbuf, "%s #$%02X", mnem, regs.RdMem(addr++));
381 case 9: // Long Immediate
382 // sprintf(outbuf, "%s #$%04X", mnem, (regs.RdMem(addr++) << 8) | regs.RdMem(addr++));
383 offset = (regs.RdMem(addr) << 8) | regs.RdMem(addr + 1);
385 sprintf(outbuf, "%s #$%04X", mnem, offset);
389 DisplayBytes(regs, regs.pc, addr); // Show bytes
390 WriteLog("%s", outbuf); // Display opcode & addressing, etc.
392 return addr - regs.pc;