|
|
1.1 root 1: //
2: // nono
3: // Copyright (C) 2022 nono project
4: // Licensed under nono-license.txt
5: //
6:
7: //
8: // HD64180 逆アセンブラ
9: //
10:
11: #include "hd64180disasm.h"
12: #include "debugger_memory.h"
1.1.1.5 ! root 13: #include "mystring.h"
1.1 root 14:
15: #define OP_DEF(name) void __CONCAT(hd64180disasm::op_,name)()
16: #define OP_FUNC(name) __CONCAT(op_,name)()
17:
18: // コンストラクタ
19: hd64180disasm::hd64180disasm()
20: {
21: }
22:
23: // デストラクタ
24: hd64180disasm::~hd64180disasm()
25: {
26: }
27:
28: // 逆アセンブルを実行
29: bool
30: hd64180disasm::Exec(DebuggerMemoryStream *mem_)
31: {
32: ExecInit(mem_);
33:
34: name.clear();
35: arg1.clear();
36: arg2.clear();
37:
1.1.1.2 root 38: ppc = mem->laddr.Addr();
1.1 root 39: ixiy = USE_HL;
40: ixd = (uint32)-1;
41: // 1バイト目処理
1.1.1.2 root 42: op = fetch1();
1.1 root 43: switch (op) {
44: #include "hd64180switch_00.inc"
45: default:
46: __unreachable();
47: }
48:
49: // 出力文字列(ダンプ)
50: dump = string_format("%02x ", bin[0]);
51: for (int i = 1; i < bin.size(); i++) {
52: dump += string_format("%02x ", bin[i]);
53: }
54: if (bin.size() < 5) {
55: dump += std::string(15 - bin.size() * 3, ' ');
56: }
57:
58: // 出力文字列(命令)
59: text = name;
60:
61: // arg2 だけがあるという状態は認めないが、
62: // ここでシフトしておけばいいか。
63: if (__predict_false(!arg2.empty() && arg1.empty())) {
64: arg1 = arg2;
65: arg2.clear();
66: }
67:
68: // arg1 があればインデントして追加
69: if (!arg1.empty()) {
1.1.1.2 root 70: uint len = text.length();
1.1 root 71: if (len < 8) {
72: text += std::string(8 - len, ' ');
73: } else {
74: text += ' ';
75: }
76:
77: text += arg1;
78: }
79:
80: // arg2 があればカンマで区切って追加
81: if (!arg2.empty()) {
82: text += ",";
83: text += arg2;
84: }
85:
86: return true;
87: }
88:
89: // バイトフェッチ
90: uint8
1.1.1.2 root 91: hd64180disasm::fetch1()
1.1 root 92: {
93: uint8 data = mem->Read(1);
94: bin.push_back(data);
95: return data;
96: }
97:
98: // ワードフェッチ
99: uint16
1.1.1.2 root 100: hd64180disasm::fetch2()
1.1 root 101: {
102: uint16 data;
103:
1.1.1.2 root 104: data = fetch1();
105: data |= fetch1() << 8;
1.1 root 106:
107: return data;
108: }
109:
110:
111: // ixiy に応じて HL/IX/IY のレジスタ名を返す。
112: std::string
113: hd64180disasm::HL()
114: {
1.1.1.4 root 115: static const char *hlname[] = {
1.1 root 116: "HL",
117: "IX",
118: "IY",
119: };
1.1.1.4 root 120: return hlname[(uint)ixiy];
1.1 root 121: }
122:
123: // (HL)/(IX+d)/(IY+d) を出力する。
124: std::string
125: hd64180disasm::HLin()
126: {
127: if (ixiy) {
128: // ixd を読むタイミングが DD CB の時だけ違う。
129: if ((int32)ixd < 0) {
1.1.1.2 root 130: ixd = fetch1();
1.1 root 131: }
132: if (ixd < 0x80) {
133: return string_format("(%s+%02XH)", HL().c_str(), ixd);
134: } else {
135: int v = -(int)(int8)ixd;
136: return string_format("(%s-%02XH)", HL().c_str(), v);
137: }
138: } else {
139: return "(HL)";
140: }
141: }
142:
143: #define op_ww (((op) >> 4) & 3)
144: #define op_zz (((op) >> 4) & 3)
145: #define op_fff (((op) >> 3) & 7)
146: #define op_bbb (((op) >> 3) & 7)
147: #define op_rrr (((op) >> 3) & 7)
148: #define op_sss ( (op) & 7)
149:
150: // ww のレジスタ名を返す。HL は必要に応じて IX, IY を出力する。
151: std::string
152: hd64180disasm::ww()
153: {
154: static const char * const wwnames[] = {
155: "BC",
156: "DE",
157: "HL?", // 参照されないはず
158: "SP",
159: };
160:
161: uint r = op_ww;
162: if (r == 2) {
163: return HL();
164: } else {
165: return std::string(wwnames[r]);
166: }
167: }
168:
169: // ww のレジスタ間接名 ("(BC)"形式) を返す。
170: // (HL) は必要に応じて (IX+d)、(IY+d) を出力する。
171: std::string
172: hd64180disasm::wwin()
173: {
174: uint r = op_ww;
175: if (r == 2) {
176: return HLin();
177: } else {
178: return "(" + ww() + ")";
179: }
180: }
181:
182: // zz レジスタの "BC", "DE", "HL" を返す。
183: // "AF" は独立してるのでここでは扱わない。
184: std::string
185: hd64180disasm::zz()
186: {
187: static const char * const zznames[] = {
188: "BC",
189: "DE",
190: // HL は参照されないはず
191: };
192:
193: uint r = op_zz;
194: if (r == 2) {
195: return HL();
196: } else {
197: return std::string(zznames[r]);
198: }
199: }
200:
201: // rrr (!=%110) のレジスタ名を返す。
202: std::string
203: hd64180disasm::rrr()
204: {
205: return rrrsss(op_rrr);
206: }
207:
208: // sss (!=%110) のレジスタ名を返す。
209: std::string
210: hd64180disasm::sss()
211: {
212: return rrrsss(op_sss);
213: }
214:
215: // rrr/sss (!=%110) のレジスタ名を返す。
216: std::string
217: hd64180disasm::rrrsss(uint r)
218: {
219: static const char rrrnames[] = "BCDEHL?A";
220:
221: if (__predict_true(ixiy == USE_HL)) {
222: return std::string(1, rrrnames[r]);
223: } else {
224: switch (r) {
225: case 4: return HL() + "H";
226: case 5: return HL() + "L";
227: default: return std::string(1, rrrnames[r]);
228: }
229: }
230: }
231:
232: std::string
233: hd64180disasm::fff() const
234: {
1.1.1.4 root 235: static const char *fffname[] = {
1.1 root 236: "NZ",
237: "Z",
238: "NC",
239: "C",
240: "PO",
241: "PE",
242: "P",
243: "M",
244: };
245: uint r = op_fff;
1.1.1.4 root 246: return fffname[r];
1.1 root 247: }
248:
249: std::string
250: hd64180disasm::bbb() const
251: {
252: uint b = op_bbb;
253: return std::string(1, '0' + b);
254: }
255:
256: std::string
257: hd64180disasm::imm8()
258: {
1.1.1.2 root 259: uint8 imm = fetch1();
1.1 root 260: if (imm < 0xa0) {
261: return string_format("%02XH", imm);
262: } else {
263: return string_format("0%02XH", imm);
264: }
265: }
266:
267: std::string
268: hd64180disasm::imm16()
269: {
1.1.1.2 root 270: uint16 imm = fetch2();
1.1 root 271: if (imm < 0xa000) {
272: return string_format("%04XH", imm);
273: } else {
274: return string_format("0%04XH", imm);
275: }
276: }
277:
278: std::string
279: hd64180disasm::disp8()
280: {
1.1.1.2 root 281: int8 disp = (int8)fetch1();
1.1 root 282: // 外部的な表記はこの命令位置 + 2 となっているが、実際には
283: // disp をフェッチした後の PC が起点になっているということのはず。
1.1.1.2 root 284: uint32 pc = mem->laddr.Addr();
1.1 root 285: uint32 addr = pc + disp;
286: if (addr < 0xa000) {
287: return string_format("%04XH", addr);
288: } else {
289: return string_format("0%04XH", addr);
290: }
291: }
292:
293: // 不当命令
294: OP_DEF(illegal)
295: {
296: name = "<illegal instruction>";
297: }
298:
299: // エミュレータ的未実装
300: OP_DEF(undef)
301: {
302: name = "<not implemented?>";
303: }
304:
1.1.1.3 root 305: // 00000000: 01R: NOP
1.1 root 306: OP_DEF(nop)
307: {
308: name = "NOP";
309: }
310:
1.1.1.3 root 311: // 00ww0001: 01R: LD ww,nn
312: // DD:00100001: 01R: LD IX,nn
1.1 root 313: OP_DEF(ld_ww_nn)
314: {
315: name = "LD";
316: arg1 = ww();
317: arg2 = imm16();
318: }
319:
1.1.1.3 root 320: // 00ww0010: 01R: LD (ww),A
1.1 root 321: OP_DEF(ld_wwin_a)
322: {
323: name = "LD";
324: arg1 = wwin();
325: arg2 = "A";
326: }
327:
1.1.1.3 root 328: // 00ww0011: 01R: INC ww
329: // DD:00100011: 01R: INC IX
1.1 root 330: OP_DEF(inc_ww)
331: {
332: name = "INC";
333: arg1 = ww();
334: }
335:
1.1.1.3 root 336: // 00rrr100: 01R: INC r
1.1 root 337: OP_DEF(inc_r)
338: {
339: name = "INC";
340: arg1 = rrr();
341: }
342:
1.1.1.3 root 343: // 00rrr101: 01R: DEC r
1.1 root 344: OP_DEF(dec_r)
345: {
346: name = "DEC";
347: arg1 = rrr();
348: }
349:
1.1.1.3 root 350: // 00rrr110: 01R: LD r,n
1.1 root 351: OP_DEF(ld_r_n)
352: {
353: name = "LD";
354: arg1 = rrr();
355: arg2 = imm8();
356: }
357:
1.1.1.3 root 358: // 00000111: 01R: RLCA
1.1 root 359: OP_DEF(rlca)
360: {
361: name = "RLCA";
362: }
363:
1.1.1.3 root 364: // 00001000: 01R: EX AF,AF'
1.1 root 365: OP_DEF(ex_af_af)
366: {
367: name = "EX";
368: arg1 = "AF";
369: arg2 = "AF'";
370: }
371:
1.1.1.3 root 372: // 00ww1001: 01R: ADD HL,ww
373: // DD:00ww1001: 01R: ADD IX,ww
1.1 root 374: OP_DEF(add_hl_ww)
375: {
376: name = "ADD";
377: arg1 = HL();
378: arg2 = ww();
379: }
380:
1.1.1.3 root 381: // 00ww1010: 01R: LD A,(ww)
1.1 root 382: OP_DEF(ld_a_wwin)
383: {
384: name = "LD";
385: arg1 = "A";
386: arg2 = wwin();
387: }
388:
1.1.1.3 root 389: // 00ww1011: 01R: DEC ww
390: // DD:00101011: 01R: DEC IX
1.1 root 391: OP_DEF(dec_ww)
392: {
393: name = "DEC";
394: arg1 = ww();
395: }
396:
1.1.1.3 root 397: // 00001111: 01R: RRCA
1.1 root 398: OP_DEF(rrca)
399: {
400: name = "RRCA";
401: }
402:
1.1.1.3 root 403: // 00010000: 01R: DJNZ n
1.1 root 404: OP_DEF(djnz)
405: {
406: name = "DJNZ";
407: arg1 = disp8();
408: }
409:
1.1.1.3 root 410: // 00010111: 01R: RLA
1.1 root 411: OP_DEF(rla)
412: {
413: name = "RLA";
414: }
415:
1.1.1.3 root 416: // 00011000: 01R: JR n
1.1 root 417: OP_DEF(jr)
418: {
419: name = "JR";
420: arg1 = disp8();
421: }
422:
1.1.1.3 root 423: // 00011111: 01R: RRA
1.1 root 424: OP_DEF(rra)
425: {
426: name = "RRA";
427: }
428:
1.1.1.3 root 429: // 00100000: 01R: JR NZ,n
1.1 root 430: OP_DEF(jr_nz)
431: {
432: name = "JR";
433: arg1 = "NZ";
434: arg2 = disp8();
435: }
436:
1.1.1.3 root 437: // 00100010: 01R: LD (nn),HL
438: // DD:00100010: 01R: LD (nn),IX
1.1 root 439: OP_DEF(ld_nnin_hl)
440: {
441: name = "LD";
442: arg1 = "(" + imm16() + ")";
443: arg2 = HL();
444: }
445:
1.1.1.3 root 446: // 00100111: 01R: DAA
1.1 root 447: OP_DEF(daa)
448: {
449: name = "DAA";
450: }
451:
1.1.1.3 root 452: // 00101000: 01R: JR Z,n
1.1 root 453: OP_DEF(jr_z)
454: {
455: name = "JR";
456: arg1 = "Z";
457: arg2 = disp8();
458: }
459:
1.1.1.3 root 460: // 00101010: 01R: LD HL,(nn)
461: // DD:00101010: 01R: LD IX,(nn)
1.1 root 462: OP_DEF(ld_hl_nnin)
463: {
464: name = "LD";
465: arg1 = HL();
466: arg2 = "(" + imm16() + ")";
467: }
468:
1.1.1.3 root 469: // 00101111: 01R: CPL
1.1 root 470: OP_DEF(cpl)
471: {
472: name = "CPL";
473: }
474:
1.1.1.3 root 475: // 00110000: 01R: JR NC,n
1.1 root 476: OP_DEF(jr_nc)
477: {
478: name = "JR";
479: arg1 = "NC";
480: arg2 = disp8();
481: }
482:
1.1.1.3 root 483: // 00110010: 01R: LD (nn),A
1.1 root 484: OP_DEF(ld_nnin_a)
485: {
486: name = "LD";
487: arg1 = "(" + imm16() + ")";
488: arg2 = "A";
489: }
490:
1.1.1.3 root 491: // 00110100: 01R: INC (HL)
492: // DD:00110100: 01R: INC (IX+d)
1.1 root 493: OP_DEF(inc_hlin)
494: {
495: name = "INC";
496: arg1 = HLin();
497: }
498:
1.1.1.3 root 499: // 00110101: 01R: DEC (HL)
500: // DD:00110101: 01R: DEC (IX+d)
1.1 root 501: OP_DEF(dec_hlin)
502: {
503: name = "DEC";
504: arg1 = HLin();
505: }
506:
1.1.1.3 root 507: // 00110110: 01R: LD (HL),n
508: // DD:00110110: 01R: LD (IX+d),n
1.1 root 509: OP_DEF(ld_hlin_n)
510: {
511: name = "LD";
512: arg1 = HLin();
513: arg2 = imm8();
514: }
515:
1.1.1.3 root 516: // 00110111: 01R: SCF
1.1 root 517: OP_DEF(scf)
518: {
519: name = "SCF";
520: }
521:
1.1.1.3 root 522: // 00111000: 01R: JR C,n
1.1 root 523: OP_DEF(jr_c)
524: {
525: name = "JR";
526: arg1 = "C";
527: arg2 = disp8();
528: }
529:
1.1.1.3 root 530: // 00111010: 01R: LD A,(nn)
1.1 root 531: OP_DEF(ld_a_nnin)
532: {
533: name = "LD";
534: arg1 = "A";
535: arg2 = "(" + imm16() + ")";
536: }
537:
1.1.1.3 root 538: // 00111111: 01R: CCF
1.1 root 539: OP_DEF(ccf)
540: {
541: name = "CCF";
542: }
543:
1.1.1.3 root 544: // 01rrrsss: 01R: LD r,s
1.1 root 545: OP_DEF(ld_r_s)
546: {
547: name = "LD";
548: arg1 = rrr();
549: arg2 = sss();
550: }
551:
1.1.1.3 root 552: // 01rrr110: 01R: LD r,(HL)
553: // DD:01rrr110: 01R: LD r,(IX+d)
1.1 root 554: OP_DEF(ld_r_hlin)
555: {
556: name = "LD";
557: arg1 = rrr();
558: arg2 = HLin();
559: }
560:
1.1.1.3 root 561: // 01110sss: 01R: LD (HL),s
562: // DD:01110sss: 01R: LD (IX+d),s
1.1 root 563: OP_DEF(ld_hlin_s)
564: {
565: name = "LD";
566: arg1 = HLin();
567: arg2 = sss();
568: }
569:
1.1.1.3 root 570: // 01110110: 01R: HALT
1.1 root 571: OP_DEF(halt)
572: {
573: name = "HALT";
574: }
575:
1.1.1.3 root 576: // 10000rrr: 01R: ADD A,r
1.1 root 577: OP_DEF(add_a_r)
578: {
579: name = "ADD";
580: arg1 = "A";
581: arg2 = sss();
582: }
583:
1.1.1.3 root 584: // 10000110: 01R: ADD A,(HL)
585: // DD:10000110: 01R: ADD A,(IX+d)
1.1 root 586: OP_DEF(add_a_hlin)
587: {
588: name = "ADD";
589: arg1 = "A";
590: arg2 = HLin();
591: }
592:
1.1.1.3 root 593: // 10001rrr: 01R: ADC A,r
1.1 root 594: OP_DEF(adc_a_r)
595: {
596: name = "ADC";
597: arg1 = "A";
598: arg2 = sss();
599: }
600:
1.1.1.3 root 601: // 10001110: 01R: ADC A,(HL)
602: // DD:10001110: 01R: ADC A,(IX+d)
1.1 root 603: OP_DEF(adc_a_hlin)
604: {
605: name = "ADC";
606: arg1 = "A";
607: arg2 = HLin();
608: }
609:
1.1.1.3 root 610: // 10010rrr: 01R: SUB r
1.1 root 611: OP_DEF(sub_r)
612: {
613: name = "SUB";
614: arg1 = sss();
615: }
616:
1.1.1.3 root 617: // 10010110: 01R: SUB (HL)
618: // DD:10010110: 01R: SUB (IX+d)
1.1 root 619: OP_DEF(sub_hlin)
620: {
621: name = "SUB";
622: arg1 = HLin();
623: }
624:
1.1.1.3 root 625: // 10011rrr: 01R: SBC A,r
1.1 root 626: OP_DEF(sbc_a_r)
627: {
628: name = "SBC";
629: arg1 = "A";
630: arg2 = sss();
631: }
632:
1.1.1.3 root 633: // 10011110: 01R: SBC A,(HL)
634: // DD:10011110: 01R: SBC A,(IX+d)
1.1 root 635: OP_DEF(sbc_a_hlin)
636: {
637: name = "SBC";
638: arg1 = "A";
639: arg2 = HLin();
640: }
641:
1.1.1.3 root 642: // 10100rrr: 01R: AND r
1.1 root 643: OP_DEF(and_r)
644: {
645: name = "AND";
646: arg1 = sss();
647: }
648:
1.1.1.3 root 649: // 10100110: 01R: AND (HL)
650: // DD:10100110: 01R: AND (IX+d)
1.1 root 651: OP_DEF(and_hlin)
652: {
653: name = "AND";
654: arg1 = HLin();
655: }
656:
1.1.1.3 root 657: // 10101rrr: 01R: XOR r
1.1 root 658: OP_DEF(xor_r)
659: {
660: name = "XOR";
661: arg1 = sss();
662: }
663:
1.1.1.3 root 664: // 10101110: 01R: XOR (HL)
665: // DD:10101110: 01R: XOR (IX+d)
1.1 root 666: OP_DEF(xor_hlin)
667: {
668: name = "XOR";
669: arg1 = HLin();
670: }
671:
1.1.1.3 root 672: // 10110rrr: 01R: OR r
1.1 root 673: OP_DEF(or_r)
674: {
675: name = "OR";
676: arg1 = sss();
677: }
678:
1.1.1.3 root 679: // 10110110: 01R: OR (HL)
680: // DD:10110110: 01R: OR (IX+d)
1.1 root 681: OP_DEF(or_hlin)
682: {
683: name = "OR";
684: arg1 = HLin();
685: }
686:
1.1.1.3 root 687: // 10111rrr: 01R: CP r
1.1 root 688: OP_DEF(cp_r)
689: {
690: name = "CP";
691: arg1 = sss();
692: }
693:
1.1.1.3 root 694: // 10111110: 01R: CP (HL)
695: // DD:10111110: 01R: CP (IX+d)
1.1 root 696: OP_DEF(cp_hlin)
697: {
698: name = "CP";
699: arg1 = HLin();
700: }
701:
1.1.1.3 root 702: // 11fff000: 01R: RET f
1.1 root 703: OP_DEF(ret_f)
704: {
705: name = "RET";
706: arg1 = fff();
707: }
708:
1.1.1.3 root 709: // 11zz0001: 01R: POP zz
710: // DD:11100001: 01R: POP IX
1.1 root 711: OP_DEF(pop_zz)
712: {
713: name = "POP";
714: arg1 = zz();
715: }
716:
1.1.1.3 root 717: // 11fff010: 01R: JP f,nn
1.1 root 718: OP_DEF(jp_f_nn)
719: {
720: name = "JP";
721: arg1 = fff();
722: arg2 = imm16();
723: }
724:
1.1.1.3 root 725: // 11000011: 01R: JP nn
1.1 root 726: OP_DEF(jp_nn)
727: {
728: name = "JP";
729: arg1 = imm16();
730: }
731:
1.1.1.3 root 732: // 11fff100: 01R: CALL f,nn
1.1 root 733: OP_DEF(call_f_nn)
734: {
735: name = "CALL";
736: arg1 = fff();
737: arg2 = imm16();
738: }
739:
1.1.1.3 root 740: // 11zz0101: 01R: PUSH zz
741: // DD:11100101: 01R: PUSH IX
1.1 root 742: OP_DEF(push_zz)
743: {
744: name = "PUSH";
745: arg1 = zz();
746: }
747:
1.1.1.3 root 748: // 11000110: 01R: ADD A,n
1.1 root 749: OP_DEF(add_a_n)
750: {
751: name = "ADD";
752: arg1 = "A";
753: arg2 = imm8();
754: }
755:
1.1.1.3 root 756: // 11vvv111: 01R: RST v
1.1 root 757: OP_DEF(rst)
758: {
759: uint v = (op >> 3) & 7;
760: name = "RST";
761: arg1 = string_format("%02xH", v * 8);
762: }
763:
1.1.1.3 root 764: // 11001001: 01R: RET
1.1 root 765: OP_DEF(ret)
766: {
767: name = "RET";
768: }
769:
1.1.1.3 root 770: // 11001011: 01R: op_CB
1.1 root 771: OP_DEF(cb)
772: {
1.1.1.2 root 773: op = fetch1();
1.1 root 774: switch (op) {
775: #include "hd64180switch_cb.inc"
776: default:
777: OP_FUNC(illegal);
778: break;
779: }
780: }
781:
1.1.1.3 root 782: // 11001101: 01R: CALL nn
1.1 root 783: OP_DEF(call)
784: {
785: name = "CALL";
786: arg1 = imm16();
787: }
788:
1.1.1.3 root 789: // 11001110: 01R: ADC A,n
1.1 root 790: OP_DEF(adc_a_n)
791: {
792: name = "ADC";
793: arg1 = "A";
794: arg2 = imm8();
795: }
796:
1.1.1.3 root 797: // 11010011: 01R: OUT (n),A
1.1 root 798: OP_DEF(out_n_a)
799: {
800: name = "OUT";
801: arg1 = "(" + imm8() + ")";
802: arg2 = "A";
803: }
804:
1.1.1.3 root 805: // 11010110: 01R: SUB n
1.1 root 806: OP_DEF(sub_n)
807: {
808: name = "SUB";
809: arg1 = imm8();
810: }
811:
1.1.1.3 root 812: // 11011001: 01R: EXX
1.1 root 813: OP_DEF(exx)
814: {
815: name = "EXX";
816: }
817:
1.1.1.3 root 818: // 11011011: 01R: IN A,(n)
1.1 root 819: OP_DEF(in_a_n)
820: {
821: name = "IN";
822: arg1 = "A";
823: arg2 = "(" + imm8() + ")";
824: }
825:
826: // DD/FD の共通部
827: void
828: hd64180disasm::ops_ddfd(ixiy_t xy)
829: {
830: ixiy = xy;
831:
832: // 2バイト目をフェッチ
1.1.1.2 root 833: op = fetch1();
1.1 root 834: // で分岐
835: switch (op) {
836: #include "hd64180switch_dd.inc"
837: default:
838: OP_FUNC(illegal);
839: break;
840: }
841: }
842:
1.1.1.3 root 843: // 11011101: 01R: op_DD
1.1 root 844: OP_DEF(dd)
845: {
846: ops_ddfd(USE_IX);
847: }
848:
1.1.1.3 root 849: // 11011110: 01R: SBC A,n
1.1 root 850: OP_DEF(sbc_a_n)
851: {
852: name = "SBC";
853: arg1 = "A";
854: arg2 = imm8();
855: }
856:
1.1.1.3 root 857: // 11100011: 01R: EX (SP),HL
858: // DD:11100011: 01R: EX (SP),IX
1.1 root 859: OP_DEF(ex_sp_hl)
860: {
861: name = "EX";
862: arg1 = "(SP)";
863: arg2 = HL();
864: }
865:
1.1.1.3 root 866: // 11100110: 01R: AND n
1.1 root 867: OP_DEF(and_n)
868: {
869: name = "AND";
870: arg1 = imm8();
871: }
872:
1.1.1.3 root 873: // 11101001: 01R: JP (HL)
874: // DD:11101001: 01R: JP (IX)
1.1 root 875: OP_DEF(jp_hl)
876: {
877: // これは DD/FD の時に (IX+d)/(IY+d) ではなく (IX)/(IY) になる
878: name = "JP";
879: arg1 = "(" + HL() + ")";
880: }
881:
1.1.1.3 root 882: // 11101011: 01R: EX DE,HL
1.1 root 883: OP_DEF(ex_de_hl)
884: {
885: name = "EX";
886: arg1 = "DE";
887: arg2 = "HL";
888: }
889:
1.1.1.3 root 890: // 11101101: 01R: op_ED
1.1 root 891: OP_DEF(ed)
892: {
1.1.1.2 root 893: op = fetch1();
1.1 root 894: switch (op) {
895: #include "hd64180switch_ed.inc"
896: default:
897: OP_FUNC(illegal);
898: break;
899: }
900: }
901:
1.1.1.3 root 902: // 11101110: 01R: XOR n
1.1 root 903: OP_DEF(xor_n)
904: {
905: name = "XOR";
906: arg1 = imm8();
907: }
908:
1.1.1.3 root 909: // 11110001: 01R: POP AF
1.1 root 910: OP_DEF(pop_af)
911: {
912: name = "POP";
913: arg1 = "AF";
914: }
915:
1.1.1.3 root 916: // 11110011: 01R: DI
1.1 root 917: OP_DEF(di)
918: {
919: name = "DI";
920: }
921:
1.1.1.3 root 922: // 11110101: 01R: PUSH AF
1.1 root 923: OP_DEF(push_af)
924: {
925: name = "PUSH";
926: arg1 = "AF";
927: }
928:
1.1.1.3 root 929: // 11110110: 01R: OR n
1.1 root 930: OP_DEF(or_n)
931: {
932: name = "OR";
933: arg1 = imm8();
934: }
935:
1.1.1.3 root 936: // 11111001: 01R: LD SP,HL
937: // DD:11111001: 01R: LD SP,IX
1.1 root 938: OP_DEF(ld_sp_hl)
939: {
940: name = "LD";
941: arg1 = "SP";
942: arg2 = HL();
943: }
944:
1.1.1.3 root 945: // 11111011: 01R: EI
1.1 root 946: OP_DEF(ei)
947: {
948: name = "EI";
949: }
950:
1.1.1.3 root 951: // 11111101: 01R: op_FD
1.1 root 952: OP_DEF(fd)
953: {
954: ops_ddfd(USE_IY);
955: }
956:
1.1.1.3 root 957: // 11111110: 01R: CP n
1.1 root 958: OP_DEF(cp_n)
959: {
960: name = "CP";
961: arg1 = imm8();
962: }
963:
1.1.1.3 root 964: // CB:00000rrr: 01R: RLC r
1.1 root 965: OP_DEF(rlc_r)
966: {
967: name = "RLC";
968: arg1 = sss();
969: }
970:
1.1.1.3 root 971: // CB:00000110: 01R: RLC (HL)
972: // DD_CB:00000110: 01R: RLC (IX+d)
1.1 root 973: OP_DEF(rlc_hlin)
974: {
975: name = "RLC";
976: arg1 = HLin();
977: }
978:
1.1.1.3 root 979: // CB:00001rrr: 01R: RRC r
1.1 root 980: OP_DEF(rrc_r)
981: {
982: name = "RRC";
983: arg1 = sss();
984: }
985:
1.1.1.3 root 986: // CB:00001110: 01R: RRC (HL)
987: // DD_CB:00001110: 01R: RRC (IX+d)
1.1 root 988: OP_DEF(rrc_hlin)
989: {
990: name = "RRC";
991: arg1 = HLin();
992: }
993:
1.1.1.3 root 994: // CB:00010rrr: 01R: RL r
1.1 root 995: OP_DEF(rl_r)
996: {
997: name = "RL";
998: arg1 = sss();
999: }
1000:
1.1.1.3 root 1001: // CB:00010110: 01R: RL (HL)
1002: // DD_CB:00010110: 01R: RL (IX+d)
1.1 root 1003: OP_DEF(rl_hlin)
1004: {
1005: name = "RL";
1006: arg1 = HLin();
1007: }
1008:
1.1.1.3 root 1009: // CB:00011rrr: 01R: RR r
1.1 root 1010: OP_DEF(rr_r)
1011: {
1012: name = "RR";
1013: arg1 = sss();
1014: }
1015:
1.1.1.3 root 1016: // CB:00011110: 01R: RR (HL)
1017: // DD_CB:00011110: 01R: RR (IX+d)
1.1 root 1018: OP_DEF(rr_hlin)
1019: {
1020: name = "RR";
1021: arg1 = HLin();
1022: }
1023:
1.1.1.3 root 1024: // CB:00100rrr: 01R: SLA r
1.1 root 1025: OP_DEF(sla_r)
1026: {
1027: name = "SLA";
1028: arg1 = sss();
1029: }
1030:
1.1.1.3 root 1031: // CB:00100110: 01R: SLA (HL)
1032: // DD_CB:00100110: 01R: SLA (IX+d)
1.1 root 1033: OP_DEF(sla_hlin)
1034: {
1035: name = "SLA";
1036: arg1 = HLin();
1037: }
1038:
1.1.1.3 root 1039: // CB:00101rrr: 01R: SRA r
1.1 root 1040: OP_DEF(sra_r)
1041: {
1042: name = "SRA";
1043: arg1 = sss();
1044: }
1045:
1.1.1.3 root 1046: // CB:00101110: 01R: SRA (HL)
1047: // DD_CB:00101110: 01R: SRA (IX+d)
1.1 root 1048: OP_DEF(sra_hlin)
1049: {
1050: name = "SRA";
1051: arg1 = HLin();
1052: }
1053:
1.1.1.3 root 1054: // CB:00110rrr: Z--: SLL
1055: OP_DEF(sll_r)
1056: {
1057: name = "SLL";
1058: arg1 = sss();
1059: }
1060:
1061: // CB:00110110: Z--: SLL (HL)
1062: // DD_CB:00110110: Z--: SLL (IX+d)
1063: OP_DEF(sll_hlin)
1064: {
1065: name = "SLL";
1066: arg1 = HLin();
1067: }
1068:
1069: // CB:00111rrr: 01R: SRL r
1.1 root 1070: OP_DEF(srl_r)
1071: {
1072: name = "SRL";
1073: arg1 = sss();
1074: }
1075:
1.1.1.3 root 1076: // CB:00111110: 01R: SRL (HL)
1077: // DD_CB:00111110: 01R: SRL (IX+d)
1.1 root 1078: OP_DEF(srl_hlin)
1079: {
1080: name = "SRL";
1081: arg1 = HLin();
1082: }
1083:
1.1.1.3 root 1084: // CB:01bbbrrr: 01R: BIT b,r
1.1 root 1085: OP_DEF(bit_r)
1086: {
1087: name = "BIT";
1088: arg1 = bbb();
1089: arg2 = sss();
1090: }
1091:
1.1.1.3 root 1092: // CB:01bbb110: 01R: BIT b,(HL)
1093: // DD_CB:01bbb110: 01R: BIT b,(IX+d)
1.1 root 1094: OP_DEF(bit_hlin)
1095: {
1096: name = "BIT";
1097: arg1 = bbb();
1098: arg2 = HLin();
1099: }
1100:
1.1.1.3 root 1101: // CB:10bbbrrr: 01R: RES b,r
1.1 root 1102: OP_DEF(res_r)
1103: {
1104: name = "RES";
1105: arg1 = bbb();
1106: arg2 = sss();
1107: }
1108:
1.1.1.3 root 1109: // CB:10bbb110: 01R: RES b,(HL)
1110: // DD_CB:10bbb110: 01R: RES b,(IX+d)
1.1 root 1111: OP_DEF(res_hlin)
1112: {
1113: name = "RES";
1114: arg1 = bbb();
1115: arg2 = HLin();
1116: }
1117:
1.1.1.3 root 1118: // CB:11bbbrrr: 01R: SET b,r
1.1 root 1119: OP_DEF(set_r)
1120: {
1121: name = "SET";
1122: arg1 = bbb();
1123: arg2 = sss();
1124: }
1125:
1.1.1.3 root 1126: // CB:11bbb110: 01R: SET b,(HL)
1127: // DD_CB:11bbb110: 01R: SET b,(IX+d)
1.1 root 1128: OP_DEF(set_hlin)
1129: {
1130: name = "SET";
1131: arg1 = bbb();
1132: arg2 = HLin();
1133: }
1134:
1.1.1.3 root 1135: // ED:00rrr000: -1-: IN0 r,(n)
1.1 root 1136: OP_DEF(in0_r_n)
1137: {
1138: name = "IN0";
1139: arg1 = rrr();
1140: arg2 = "(" + imm8() + ")";
1141: }
1142:
1.1.1.3 root 1143: // ED:00rrr001: -1-: OUT0 (n),r
1.1 root 1144: OP_DEF(out0_n_r)
1145: {
1146: name = "OUT0";
1147: arg1 = "(" + imm8() + ")";
1148: arg2 = rrr();
1149: }
1150:
1.1.1.3 root 1151: // ED:00rrr100: -1-: TST r
1.1 root 1152: OP_DEF(tst_r)
1153: {
1154: name = "TST";
1155: arg1 = rrr();
1156: }
1157:
1.1.1.3 root 1158: // ED:00110000: -1-: IN0 F,(n)
1.1 root 1159: OP_DEF(in0_f_n)
1160: {
1161: name = "IN0";
1162: arg1 = "F";
1163: arg2 = "(" + imm8() + ")";
1164: }
1165:
1.1.1.3 root 1166: // ED:00110100: -1-: TST (HL)
1.1 root 1167: OP_DEF(tst_hlin)
1168: {
1169: name = "TST";
1170: arg1 = HLin();
1171: }
1172:
1.1.1.3 root 1173: // ED:01rrr000: 01R: IN r,(C)
1.1 root 1174: OP_DEF(in_r_c)
1175: {
1176: name = "IN";
1177: arg1 = rrr();
1178: arg2 = "(C)";
1179: }
1180:
1.1.1.3 root 1181: // ED:01rrr001: 01R: OUT (C),r
1.1 root 1182: OP_DEF(out_c_r)
1183: {
1184: name = "OUT";
1185: arg1 = "(C)";
1186: arg2 = rrr();
1187: }
1188:
1.1.1.3 root 1189: // ED:01ww0010: 01R: SBC HL,ww
1.1 root 1190: OP_DEF(sbc_hl_ww)
1191: {
1192: name = "SBC";
1193: arg1 = HL();
1194: arg2 = ww();
1195: }
1196:
1.1.1.3 root 1197: // ED:01ww0011: 01R: LD (nn),ww
1.1 root 1198: OP_DEF(ld_nnin_ww)
1199: {
1200: name = "LD";
1201: arg1 = "(" + imm16() + ")";
1202: arg2 = ww();
1203: }
1204:
1.1.1.3 root 1205: // ED:01000100: 01R: NEG
1.1 root 1206: OP_DEF(neg)
1207: {
1208: name = "NEG";
1209: }
1210:
1.1.1.3 root 1211: // ED:01000101: 01R: RETN
1.1 root 1212: OP_DEF(retn)
1213: {
1214: name = "RETN";
1215: }
1216:
1.1.1.3 root 1217: // ED:01000110: 01R: IM 0
1.1 root 1218: OP_DEF(im_0)
1219: {
1220: name = "IM";
1221: arg1 = "0";
1222: }
1223:
1.1.1.3 root 1224: // ED:01000111: 01R: LD I,A
1.1 root 1225: OP_DEF(ld_i_a)
1226: {
1227: name = "LD";
1228: arg1 = "I";
1229: arg2 = "A";
1230: }
1231:
1.1.1.3 root 1232: // ED:01ww1010: 01R: ADC HL,ww
1.1 root 1233: OP_DEF(adc_hl_ww)
1234: {
1235: name = "ADC";
1236: arg1 = HL();
1237: arg2 = ww();
1238: }
1239:
1.1.1.3 root 1240: // ED:01ww1011: 01R: LD ww,(nn)
1.1 root 1241: OP_DEF(ld_ww_nnin)
1242: {
1243: name = "LD";
1244: arg1 = ww();
1245: arg2 = "(" + imm16() + ")";
1246: }
1247:
1.1.1.3 root 1248: // ED:01ww1100: -1-: MLT ww
1.1 root 1249: OP_DEF(mlt)
1250: {
1251: name = "MLT";
1252: arg1 = ww();
1253: }
1254:
1.1.1.3 root 1255: // ED:01001101: 01R: RETI
1.1 root 1256: OP_DEF(reti)
1257: {
1258: name = "RETI";
1259: }
1260:
1.1.1.3 root 1261: // ED:01001111: 01R: LD R,A
1.1 root 1262: OP_DEF(ld_r_a)
1263: {
1264: name = "LD";
1265: arg1 = "R";
1266: arg2 = "A";
1267: }
1268:
1.1.1.3 root 1269: // ED:01010110: 01R: IM 1
1.1 root 1270: OP_DEF(im_1)
1271: {
1272: name = "IM";
1273: arg1 = "1";
1274: }
1275:
1.1.1.3 root 1276: // ED:01010111: 01R: LD A,I
1.1 root 1277: OP_DEF(ld_a_i)
1278: {
1279: name = "LD";
1280: arg1 = "A";
1281: arg2 = "I";
1282: }
1283:
1.1.1.3 root 1284: // ED:01011110: 01R: IM 2
1.1 root 1285: OP_DEF(im_2)
1286: {
1287: name = "IM";
1288: arg1 = "2";
1289: }
1290:
1.1.1.3 root 1291: // ED:01011111: 01R: LD A,R
1.1 root 1292: OP_DEF(ld_a_r)
1293: {
1294: name = "LD";
1295: arg1 = "A";
1296: arg2 = "R";
1297: }
1298:
1.1.1.3 root 1299: // ED:01100100: -1-: TST n
1.1 root 1300: OP_DEF(tst_n)
1301: {
1302: name = "TST";
1303: arg1 = imm8();
1304: }
1305:
1.1.1.3 root 1306: // ED:01100111: 01R: RRD
1.1 root 1307: OP_DEF(rrd)
1308: {
1309: name = "RRD";
1310: }
1311:
1.1.1.3 root 1312: // ED:01101111: 01R: RLD
1.1 root 1313: OP_DEF(rld)
1314: {
1315: name = "RLD";
1316: }
1317:
1.1.1.3 root 1318: // ED:01110000: 01R: IN F,(C)
1.1 root 1319: OP_DEF(in_f_c)
1320: {
1321: name = "IN";
1322: arg1 = "F";
1323: arg2 = "(C)";
1324: }
1325:
1.1.1.3 root 1326: // ED:01110100: -1-: TSTIO n
1.1 root 1327: OP_DEF(tstio_n)
1328: {
1329: name = "TSTIO";
1330: arg1 = imm8();
1331: }
1332:
1.1.1.3 root 1333: // ED:01110110: -1-: SLP
1.1 root 1334: OP_DEF(slp)
1335: {
1336: name = "SLP";
1337: }
1338:
1.1.1.3 root 1339: // ED:10000011: -1-: OTIM
1.1 root 1340: OP_DEF(otim)
1341: {
1342: name = "OTIM";
1343: }
1344:
1.1.1.3 root 1345: // ED:10001011: -1-: OTDM
1.1 root 1346: OP_DEF(otdm)
1347: {
1348: name = "OTDM";
1349: }
1350:
1.1.1.3 root 1351: // ED:10010011: -1-: OTIMR
1.1 root 1352: OP_DEF(otimr)
1353: {
1354: name = "OTIMR";
1355: }
1356:
1.1.1.3 root 1357: // ED:10011011: -1-: OTDMR
1.1 root 1358: OP_DEF(otdmr)
1359: {
1360: name = "OTDMR";
1361: }
1362:
1.1.1.3 root 1363: // ED:10100000: 01R: LDI
1.1 root 1364: OP_DEF(ldi)
1365: {
1366: name = "LDI";
1367: }
1368:
1.1.1.3 root 1369: // ED:10100001: 01R: CPI
1.1 root 1370: OP_DEF(cpi)
1371: {
1372: name = "CPI";
1373: }
1374:
1.1.1.3 root 1375: // ED:10100010: 01R: INI
1.1 root 1376: OP_DEF(ini)
1377: {
1378: name = "INI";
1379: }
1380:
1.1.1.3 root 1381: // ED:10100011: 01R: OUTI
1.1 root 1382: OP_DEF(outi)
1383: {
1384: name = "OUTI";
1385: }
1386:
1.1.1.3 root 1387: // ED:10101000: 01R: LDD
1.1 root 1388: OP_DEF(ldd)
1389: {
1390: name = "LDD";
1391: }
1392:
1.1.1.3 root 1393: // ED:10101001: 01R: CPD
1.1 root 1394: OP_DEF(cpd)
1395: {
1396: name = "CPD";
1397: }
1398:
1.1.1.3 root 1399: // ED:10101010: 01R: IND
1.1 root 1400: OP_DEF(ind)
1401: {
1402: name = "IND";
1403: }
1404:
1.1.1.3 root 1405: // ED:10101011: 01R: OUTD
1.1 root 1406: OP_DEF(outd)
1407: {
1408: name = "OUTD";
1409: }
1410:
1.1.1.3 root 1411: // ED:10110000: 01R: LDIR
1.1 root 1412: OP_DEF(ldir)
1413: {
1414: name = "LDIR";
1415: }
1416:
1.1.1.3 root 1417: // ED:10110001: 01R: CPIR
1.1 root 1418: OP_DEF(cpir)
1419: {
1420: name = "CPIR";
1421: }
1422:
1.1.1.3 root 1423: // ED:10110010: 01R: INIR
1.1 root 1424: OP_DEF(inir)
1425: {
1426: name = "INIR";
1427: }
1428:
1.1.1.3 root 1429: // ED:10110011: 01R: OTIR
1.1 root 1430: OP_DEF(otir)
1431: {
1432: name = "OTIR";
1433: }
1434:
1.1.1.3 root 1435: // ED:10111000: 01R: LDDR
1.1 root 1436: OP_DEF(lddr)
1437: {
1438: name = "LDDR";
1439: }
1440:
1.1.1.3 root 1441: // ED:10111001: 01R: CPDR
1.1 root 1442: OP_DEF(cpdr)
1443: {
1444: name = "CPDR";
1445: }
1446:
1.1.1.3 root 1447: // ED:10111010: 01R: INDR
1.1 root 1448: OP_DEF(indr)
1449: {
1450: name = "INDR";
1451: }
1452:
1.1.1.3 root 1453: // ED:10111011: 01R: OTDR
1.1 root 1454: OP_DEF(otdr)
1455: {
1456: name = "OTDR";
1457: }
1458:
1.1.1.3 root 1459: // ED:11rrr001: --R: MULUB A,r
1.1 root 1460: OP_DEF(mulub_a_r)
1461: {
1462: name = "MULUB";
1463: arg1 = "A";
1464: arg2 = rrr();
1465: }
1466:
1.1.1.3 root 1467: // ED:11000011: --R: MULUB HL,BC
1.1 root 1468: OP_DEF(mulub_hl_bc)
1469: {
1470: name = "MULUB";
1471: arg1 = "HL";
1472: arg2 = "BC";
1473: }
1474:
1.1.1.3 root 1475: // ED:11110011: --R: MULUB HL,SP
1.1 root 1476: OP_DEF(mulub_hl_sp)
1477: {
1478: name = "MULUB";
1479: arg1 = "HL";
1480: arg2 = "SP";
1481: }
1482:
1.1.1.3 root 1483: // ED:11111111: -N-: SYSCALL
1.1 root 1484: OP_DEF(syscall)
1485: {
1486: name = "SYSCALL";
1487: }
1488:
1.1.1.3 root 1489: // DD:00rrr100: Z-Z: INC ixr
1.1 root 1490: OP_DEF(inc_ixr)
1491: {
1492: OP_FUNC(inc_r);
1493: }
1494:
1.1.1.3 root 1495: // DD:00rrr101: Z-Z: DEC ixr
1.1 root 1496: OP_DEF(dec_ixr)
1497: {
1498: OP_FUNC(dec_r);
1499: }
1500:
1.1.1.3 root 1501: // DD:00rrr110: Z-Z: LD ixr,n
1502: OP_DEF(ld_ixr_n)
1503: {
1504: OP_FUNC(ld_r_n);
1505: }
1506:
1507: // DD:01rrrsss: Z-Z: LD r,ixs
1.1 root 1508: OP_DEF(ld_r_ixs)
1509: {
1510: OP_FUNC(ld_r_s);
1511: }
1512:
1.1.1.3 root 1513: // DD:10000rrr: Z-Z: ADD A,ixr
1.1 root 1514: OP_DEF(add_a_ixr)
1515: {
1516: OP_FUNC(add_a_r);
1517: }
1518:
1.1.1.3 root 1519: // DD:10001rrr: Z-Z: ADC A,ixr
1.1 root 1520: OP_DEF(adc_a_ixr)
1521: {
1522: OP_FUNC(adc_a_r);
1523: }
1524:
1.1.1.3 root 1525: // DD:10010rrr: Z-Z: SUB ixr
1.1 root 1526: OP_DEF(sub_ixr)
1527: {
1528: OP_FUNC(sub_r);
1529: }
1530:
1.1.1.3 root 1531: // DD:10011rrr: Z-Z: SBC A,ixr
1.1 root 1532: OP_DEF(sbc_a_ixr)
1533: {
1534: OP_FUNC(sbc_a_r);
1535: }
1536:
1.1.1.3 root 1537: // DD:10100rrr: Z-Z: AND ixr
1.1 root 1538: OP_DEF(and_ixr)
1539: {
1540: OP_FUNC(and_r);
1541: }
1542:
1.1.1.3 root 1543: // DD:10101rrr: Z-Z: XOR ixr
1.1 root 1544: OP_DEF(xor_ixr)
1545: {
1546: OP_FUNC(xor_r);
1547: }
1548:
1.1.1.3 root 1549: // DD:10110rrr: Z-Z: OR ixr
1.1 root 1550: OP_DEF(or_ixr)
1551: {
1552: OP_FUNC(or_r);
1553: }
1554:
1.1.1.3 root 1555: // DD:10111rrr: Z-Z: CP ixr
1.1 root 1556: OP_DEF(cp_ixr)
1557: {
1558: OP_FUNC(cp_r);
1559: }
1560:
1.1.1.3 root 1561: // DD:11001011: 01R: op_DD_CB
1.1 root 1562: OP_DEF(dd_cb)
1563: {
1564: // DD/FD CB の場合は 3バイト目が <d> で 4バイト目が命令語の順。
1565: // どうして…。
1.1.1.2 root 1566: ixd = fetch1();
1.1 root 1567:
1.1.1.2 root 1568: op = fetch1();
1.1 root 1569: switch (op) {
1570: #include "hd64180switch_dd_cb.inc"
1571: default:
1572: OP_FUNC(illegal);
1573: break;
1574: }
1575: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.