diff options
author | mrb0nk500 <b0nk@b0nk.xyz> | 2020-03-17 15:07:20 -0400 |
---|---|---|
committer | mrb0nk500 <b0nk@b0nk.xyz> | 2020-03-17 15:36:07 -0400 |
commit | 071edf621a6722f94027f37720a5a5f73d9696c0 (patch) | |
tree | 87761e6dca9e7cf47bf0b6f2d52e8e31623ac01a | |
parent | 917f864a6d1304d9f0c650c107a5fd6576690cb7 (diff) |
Revamped the opcode table, made the emulator more
efficient, and ported SuBEditor to C.
I revamped the opcode table to add another prefix bit
for the addressing mode, finally giving access to all
addresses, without wasting any bytes.
I made the stack based operations more efficient, by
sort of applying Duff's device to it.
And I ported SuBEditor to C, to make it easier for me
to figure out how to implement SuBAsm.
-rw-r--r-- | Makefile | 5 | ||||
-rw-r--r-- | asmmon.c | 647 | ||||
-rw-r--r-- | opcode.h | 1245 | ||||
-rw-r--r-- | programs/c-ports/annotated-dabbed.s | 38 | ||||
-rw-r--r-- | programs/c-ports/subasm.c | 33 | ||||
-rw-r--r-- | programs/c-ports/subeditor.c | 605 | ||||
-rw-r--r-- | programs/c-ports/subeditor.h | 36 | ||||
-rw-r--r-- | programs/subasm-2.s | 151 | ||||
-rw-r--r-- | programs/subeditor.s | 509 | ||||
-rw-r--r-- | sux.c | 780 | ||||
-rw-r--r-- | test/subroutine.s | 45 |
11 files changed, 2730 insertions, 1364 deletions
@@ -10,7 +10,10 @@ endif CFLAGS = $(PCC_CFLAGS) $(CFLAGS_EXTRA) OBJS = asmmon.o sux.o OBJ_NAME = cisc-0.2 +OBJ_NAME2 = subeditor all : clean $(OBJ_NAME) +subeditor : + $(CC) programs/c-ports/$(OBJ_NAME2).c $(CFLAGS) -lcurses -ltinfo -o $(OBJ_NAME2)-c cisc-0.2: $(OBJS) $(CC) $(OBJS) $(CFLAGS) -lpthread -lcurses -ltinfo -o $(OBJ_NAME) sux.o : @@ -18,7 +21,7 @@ sux.o : asmmon.o : $(CC) asmmon.c -c $(CFLAGS) -o asmmon.o clean : - rm -f $(OBJ_NAME) $(OBJS) + rm -f $(OBJ_NAME) $(OBJ_NAME2)-c $(OBJS) install : install -D -m755 $(OBJ_NAME) $(BIN_DIR)/$(OBJ_NAME) uninstall : @@ -213,98 +213,95 @@ void disasm(uint8_t prefix, uint8_t opcode, uint64_t value) { int asmmon(const char *fn) { /* mne IMM ZM ZMX ZMY IND INX INY ABS IMPL*/ SETOP( 0, "CPS", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); - SETOP( 1, "ADC", 0x01, 0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00); + SETOP( 1, "ADC", 0x01, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00); SETOP( 2, "AAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02); - SETOP( 3, "JMP", 0x00, 0xD0, 0x00, 0x00, 0x04, 0x14, 0x24, 0x10, 0x00); - SETOP( 4, "PHB", 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); - SETOP( 5, "PHP", 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); - SETOP( 6, "LDA", 0x09, 0x39, 0x59, 0x79, 0x99, 0xB9, 0xD9, 0x19, 0x00); - SETOP( 7, "LDY", 0x0A, 0x3A, 0x5A, 0x00, 0x7A, 0x9A, 0x00, 0x1A, 0x00); - SETOP( 8, "LDX", 0x0B, 0x3B, 0x00, 0x5B, 0x7B, 0x00, 0x9B, 0x1B, 0x00); - SETOP( 9, "TAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0C); - SETOP(10, "LDB", 0x0E, 0x3E, 0x5E, 0x7E, 0x9E, 0xBE, 0xDE, 0x1E, 0x00); - SETOP(11, "SBC", 0x11, 0x15, 0x00, 0x00, 0x00, 0x00, 0x00, 0x13, 0x00); - SETOP(12, "SAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x12); - SETOP(13, "PLB", 0x16, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); - SETOP(14, "PLP", 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); - SETOP(15, "TBA", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1C); - SETOP(16, "JSR", 0x00, 0x20, 0x00, 0x00, 0x34, 0x44, 0x54, 0x00, 0x00); - SETOP(17, "AND", 0x21, 0x25, 0x00, 0x00, 0x00, 0x00, 0x00, 0x23, 0x00); - SETOP(18, "ABA", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x22); - SETOP(19, "CPB", 0x26, 0x46, 0x00, 0x00, 0x56, 0x66, 0x76, 0x36, 0x00); - SETOP(20, "STT", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x28); - SETOP(21, "STA", 0x00, 0x49, 0x69, 0x89, 0xA9, 0xC9, 0xE9, 0x29, 0x00); - SETOP(22, "STY", 0x00, 0x4A, 0x6A, 0x00, 0x8A, 0xAA, 0x00, 0x2A, 0x00); - SETOP(23, "STX", 0x00, 0x4B, 0x00, 0x6B, 0x8B, 0x00, 0xAB, 0x2B, 0x00); - SETOP(24, "TAY", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x2C); - SETOP(25, "STB", 0x00, 0x4E, 0x6E, 0x8E, 0xAE, 0xCE, 0xEE, 0x2E, 0x00); - SETOP(26, "BPO", 0x00, 0x64, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00); - SETOP(27, "ORA", 0x31, 0x35, 0x00, 0x00, 0x00, 0x00, 0x00, 0x33, 0x00); - SETOP(28, "OAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x32); - SETOP(29, "SEI", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x38); - SETOP(30, "TYA", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3C); - SETOP(31, "BNG", 0x00, 0x74, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00); - SETOP(32, "XOR", 0x41, 0x45, 0x00, 0x00, 0x00, 0x00, 0x00, 0x43, 0x00); - SETOP(33, "XAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x42); - SETOP(34, "CLI", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x48); - SETOP(35, "TAX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x4C); - SETOP(36, "BCS", 0x00, 0x84, 0x00, 0x00, 0x00, 0x00, 0x00, 0x50, 0x00); - SETOP(37, "LSL", 0x51, 0x55, 0x00, 0x00, 0x00, 0x00, 0x00, 0x53, 0x00); - SETOP(38, "LLB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x52); - SETOP(39, "SEC", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x58); - SETOP(40, "TXA", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x5C); - SETOP(41, "BCC", 0x00, 0x94, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00); - SETOP(42, "LSR", 0x61, 0x65, 0x00, 0x00, 0x00, 0x00, 0x00, 0x63, 0x00); - SETOP(43, "LRB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x62); - SETOP(44, "CLC", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x68); - SETOP(45, "TYX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x6C); - SETOP(46, "BEQ", 0x00, 0xA4, 0x00, 0x00, 0x00, 0x00, 0x00, 0x70, 0x00); - SETOP(47, "ROL", 0x71, 0x75, 0x00, 0x00, 0x00, 0x00, 0x00, 0x73, 0x00); - SETOP(48, "RLB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x72); - SETOP(49, "SSP", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x78); - SETOP(50, "TXY", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x7C); - SETOP(51, "BNE", 0x00, 0xB4, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x00); - SETOP(52, "ROR", 0x81, 0x85, 0x00, 0x00, 0x00, 0x00, 0x00, 0x83, 0x00); - SETOP(53, "RRB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x82); - SETOP(54, "INY", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x86); - SETOP(55, "CSP", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x88); - SETOP(56, "TSX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x8C); - SETOP(57, "BVS", 0x00, 0xC4, 0x00, 0x00, 0x00, 0x00, 0x00, 0x90, 0x00); - SETOP(58, "MUL", 0x91, 0x95, 0x00, 0x00, 0x00, 0x00, 0x00, 0x93, 0x00); - SETOP(59, "MAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x92); - SETOP(60, "DEY", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x96); - SETOP(61, "SEV", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x98); - SETOP(62, "TXS", 0x9C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); - SETOP(63, "BVC", 0x00, 0xD4, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA0, 0x00); - SETOP(64, "DIV", 0xA1, 0xA5, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA3, 0x00); - SETOP(65, "DAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA2); - SETOP(66, "INX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA6); - SETOP(67, "CLV", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA8); - SETOP(68, "PHY", 0xAC, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); - SETOP(69, "RTS", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xB0); - SETOP(70, "CMP", 0xB1, 0xB5, 0x00, 0x00, 0xF1, 0xF3, 0xF5, 0xB3, 0x00); - SETOP(71, "CAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xB2); - SETOP(72, "DEX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xB6); - SETOP(73, "ENT", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xB8); - SETOP(74, "CPY", 0xBA, 0xDA, 0x00, 0x00, 0xEA, 0xFA, 0x00, 0xCA, 0x00); - SETOP(75, "CPX", 0xBB, 0xDB, 0x00, 0x00, 0xEB, 0x00, 0xFB, 0xCB, 0x00); - SETOP(76, "PLY", 0xBC, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); - SETOP(77, "RTI", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC0); - SETOP(78, "INC", 0x00, 0xC5, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC3, 0xC1); - SETOP(79, "IAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC2); - SETOP(80, "WAI", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC8); - SETOP(81, "PHX", 0xCC, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); - SETOP(82, "DEC", 0x00, 0xD5, 0x00, 0x00, 0x00, 0x00, 0x00, 0xD3, 0xD1); - SETOP(83, "DBA", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xD2); - SETOP(84, "PLX", 0xDC, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); - SETOP(85, "JSL", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE0, 0x00); - SETOP(86, "ASR", 0xE1, 0xE5, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE3, 0x00); - SETOP(87, "ARB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE2); - SETOP(88, "NOP", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE8); - SETOP(89, "PHA", 0xEC, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); - SETOP(90, "RTL", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xF0); - SETOP(91, "BRK", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xF8); - SETOP(92, "PLA", 0xFC, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); + SETOP( 3, "PHP", 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); + SETOP( 4, "CPB", 0x09, 0x2D, 0x00, 0x00, 0x55, 0xAD, 0xAC, 0x2C, 0x00); + SETOP( 5, "PHB", 0x0A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); + SETOP( 6, "DEC", 0x00, 0x0D, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0C, 0xE5); + SETOP( 7, "JMP", 0x00, 0x0E, 0x00, 0x00, 0xCE, 0x00, 0x00, 0x10, 0x00); + SETOP( 8, "SBC", 0x11, 0x16, 0x00, 0x00, 0x00, 0x00, 0x00, 0x14, 0x00); + SETOP( 9, "SAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x12); + SETOP(10, "ENT", 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); + SETOP(11, "CPY", 0x19, 0x3D, 0x00, 0x00, 0x85, 0x00, 0x00, 0x4C, 0x00); + SETOP(12, "PLB", 0x1A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); + SETOP(13, "INC", 0x00, 0x1D, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1C, 0xF5); + SETOP(14, "JSR", 0x00, 0x1E, 0x00, 0x00, 0xBE, 0x00, 0x00, 0x00, 0x00); + SETOP(15, "JSL", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x00); + SETOP(16, "AND", 0x21, 0x26, 0x00, 0x00, 0x00, 0x00, 0x00, 0x24, 0x00); + SETOP(17, "ABA", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x22); + SETOP(18, "PLP", 0x28, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); + SETOP(19, "CPX", 0x29, 0x4D, 0x00, 0x00, 0xB5, 0x00, 0x00, 0x3C, 0x00); + SETOP(20, "PHY", 0x2A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); + SETOP(21, "BPO", 0x00, 0x2E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00); + SETOP(22, "ORA", 0x31, 0x36, 0x00, 0x00, 0x00, 0x00, 0x00, 0x34, 0x00); + SETOP(23, "OAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x32); + SETOP(24, "STT", 0x38, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); + SETOP(25, "PLY", 0x3A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); + SETOP(26, "BNG", 0x00, 0x3E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00); + SETOP(27, "XOR", 0x41, 0x46, 0x00, 0x00, 0x00, 0x00, 0x00, 0x44, 0x00); + SETOP(28, "XAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x42); + SETOP(29, "PHA", 0x48, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); + SETOP(30, "PHX", 0x4A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); + SETOP(31, "BCS", 0x00, 0x4E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x50, 0x00); + SETOP(32, "LSL", 0x51, 0x56, 0x00, 0x00, 0x00, 0x00, 0x00, 0x54, 0x00); + SETOP(33, "LLB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x52); + SETOP(34, "CLC", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x58); + SETOP(35, "PLX", 0x5A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); + SETOP(36, "BCC", 0x00, 0x5E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00); + SETOP(37, "LSR", 0x61, 0x66, 0x00, 0x00, 0x00, 0x00, 0x00, 0x64, 0x00); + SETOP(38, "LRB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x62); + SETOP(39, "PLA", 0x68, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); + SETOP(40, "TAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x6A); + SETOP(41, "BEQ", 0x00, 0x6E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x70, 0x00); + SETOP(42, "ROL", 0x71, 0x76, 0x00, 0x00, 0x00, 0x00, 0x00, 0x74, 0x00); + SETOP(43, "RLB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x72); + SETOP(44, "SEC", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x78); + SETOP(45, "TBA", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x7A); + SETOP(46, "BNE", 0x00, 0x7E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x00); + SETOP(47, "ROR", 0x81, 0x86, 0x00, 0x00, 0x00, 0x00, 0x00, 0x84, 0x00); + SETOP(48, "RRB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x82); + SETOP(49, "DEY", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x88); + SETOP(50, "TAY", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x8A); + SETOP(51, "BVS", 0x00, 0x8E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x90, 0x00); + SETOP(52, "MUL", 0x91, 0x96, 0x00, 0x00, 0x00, 0x00, 0x00, 0x94, 0x00); + SETOP(53, "MAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x92); + SETOP(54, "CLI", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x98); + SETOP(55, "TYA", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x9A); + SETOP(56, "BVC", 0x00, 0x9E, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA0, 0x00); + SETOP(57, "DIV", 0xA1, 0xA6, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA4, 0x00); + SETOP(58, "DAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA2); + SETOP(59, "INY", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA8); + SETOP(60, "TAX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xAA); + SETOP(61, "RTS", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xAE); + SETOP(62, "RTL", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xB0); + SETOP(63, "CMP", 0xB1, 0xB6, 0x00, 0x00, 0x25, 0x7D, 0x7C, 0xB4, 0x00); + SETOP(64, "CAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xB2); + SETOP(65, "SEI", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xB8); + SETOP(66, "LDX", 0xB9, 0xBD, 0x00, 0xC9, 0x95, 0x00, 0x00, 0xBC, 0x00); + SETOP(67, "TXA", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xBA); + SETOP(68, "RTI", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC0); + SETOP(69, "LDA", 0xC1, 0xC6, 0x79, 0x39, 0x05, 0x5D, 0x5C, 0xC4, 0x00); + SETOP(70, "DEX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC5); + SETOP(71, "CLV", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC8); + SETOP(72, "TYX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xCA); + SETOP(73, "STA", 0x00, 0xCD, 0x89, 0x49, 0x15, 0x6D, 0x6C, 0xCC, 0x00); + SETOP(74, "TSX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xD0); + SETOP(75, "LDB", 0xD1, 0xD6, 0x99, 0x59, 0x35, 0x8D, 0x8C, 0xD4, 0x00); + SETOP(76, "INX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xD5); + SETOP(77, "WAI", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xD8); + SETOP(78, "TXY", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xDA); + SETOP(79, "STB", 0x00, 0xDD, 0xA9, 0x69, 0x45, 0x9D, 0x9C, 0xDC, 0x00); + SETOP(80, "TXS", 0xE0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); + SETOP(81, "LDY", 0xE1, 0xE6, 0xE9, 0x00, 0x65, 0x00, 0x00, 0xE4, 0x00); + SETOP(82, "BRK", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE8); + SETOP(83, "NOP", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xEA); + SETOP(84, "STY", 0x00, 0xED, 0xF9, 0x00, 0x75, 0x00, 0x00, 0xEC, 0x00); + SETOP(85, "DEB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xEE); + SETOP(86, "ASR", 0xF1, 0xF6, 0x00, 0x00, 0x00, 0x00, 0x00, 0xF4, 0x00); + SETOP(87, "ARB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xF2); + SETOP(88, "STX", 0x00, 0xFD, 0x00, 0xD9, 0xA5, 0x00, 0x00, 0xFC, 0x00); + SETOP(89, "INB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFE); FILE *fp; if (strcasecmp(fn, "stdin") != 0) { fp = fopen(fn, "r"); @@ -322,13 +319,16 @@ int asmmon(const char *fn) { char mode[3]; opent op; uint8_t addrmode = IMPL; + uint8_t addrtok = 0; uint64_t value = 0; char *oprand; + char *oprand2; char *cmd; char ir[2] = ""; /* Index register. */ int a = 0; int b = 0; char *tmp = malloc(sizeof(char *)*128); + char *tmp2; size_t size; prefix = 0; done = 0; @@ -348,8 +348,18 @@ int asmmon(const char *fn) { strtok_r(ins, ".", &postfix); if (oprand != NULL) { for (int i = 0; i < strlen(oprand); i++) { - if (oprand[i] == '(') - addrmode = IND; + switch (oprand[i]) { + case '(': + addrmode = IND; + break; + case '+': + addrtok = 1; + break; + case '-': + addrtok = 2; + + } + if (oprand[i] == '"') break; if (a && oprand[a] == ',') { @@ -467,9 +477,9 @@ int asmmon(const char *fn) { else if (start < 0xFFFFFFFFFFFFFFFF) printf("$%016llx: ", start); prefix = addr[start]; - if ((prefix & 0x07) == 0x07) { + if ((prefix & 0x03) == 0x03) { start+=1; - addrsize = (prefix & 8) >> 3; + addrsize = (prefix & 0x0C) >> 2; rs = (prefix & 0x30) >> 4; regsize = (1 << rs); } else { @@ -484,17 +494,17 @@ int asmmon(const char *fn) { break; case IMM: value = addr[start]; - if (regsize >= 2) - value |= addr[start+1] << 8; - if (regsize >= 4) { - value |= addr[start+2] << 16; - value |= addr[start+3] << 24; - } - if (regsize >= 8) { - value |= (uint64_t)addr[start+4] << 32; - value |= (uint64_t)addr[start+5] << 40; - value |= (uint64_t)addr[start+6] << 48; - value |= (uint64_t)addr[start+7] << 56; + switch (regsize) { + case 8: + value |= (uint64_t)addr[start+7] << 56; + value |= (uint64_t)addr[start+6] << 48; + value |= (uint64_t)addr[start+5] << 40; + value |= (uint64_t)addr[start+4] << 32; + case 4: + value |= addr[start+3] << 24; + value |= addr[start+2] << 16; + case 2: + value |= addr[start+1] << 8; } start += regsize; break; @@ -505,28 +515,61 @@ int asmmon(const char *fn) { case INDX: case INDY: value = addr[start]; - if (addrsize) { - value |= addr[start+1] << 8; - value |= addr[start+2] << 16; - value |= addr[start+3] << 24; - start+=4; - } else { - start+=1; + switch (addrsize) { + case 0: + start+=1; + break; + case 1: + value |= addr[start+1] << 8; + value |= addr[start+2] << 16; + start+=3; + break; + case 2: + value |= addr[start+1] << 8; + value |= addr[start+2] << 16; + value |= addr[start+3] << 24; + value |= (uint64_t)addr[start+4] << 32; + value |= (uint64_t)addr[start+5] << 40; + start+=6; + break; + case 3: + value |= addr[start+1] << 8; + value |= addr[start+2] << 16; + value |= addr[start+3] << 24; + start+=4; + break; } break; case ABS: value = addr[start]; value |= addr[start+1] << 8; - if (addrsize) { - value |= (uint64_t)addr[start+2] << 16; - value |= (uint64_t)addr[start+3] << 24; - value |= (uint64_t)addr[start+4] << 32; - value |= (uint64_t)addr[start+5] << 40; - value |= (uint64_t)addr[start+6] << 48; - value |= (uint64_t)addr[start+7] << 56; - start+=8; - } else { - start+=2; + switch (addrsize) { + case 0: + start+=2; + break; + case 1: + value |= addr[start+2] << 16; + value |= addr[start+3] << 24; + value |= (uint64_t)addr[start+4] << 32; + start+=5; + break; + case 2: + value |= addr[start+2] << 16; + value |= addr[start+3] << 24; + value |= (uint64_t)addr[start+4] << 32; + value |= (uint64_t)addr[start+5] << 40; + value |= (uint64_t)addr[start+6] << 48; + start+=7; + break; + case 3: + value |= addr[start+2] << 16; + value |= addr[start+3] << 24; + value |= (uint64_t)addr[start+4] << 32; + value |= (uint64_t)addr[start+5] << 40; + value |= (uint64_t)addr[start+6] << 48; + value |= (uint64_t)addr[start+7] << 56; + start+=8; + break; } break; } @@ -578,9 +621,14 @@ int asmmon(const char *fn) { sprintf(oprand, "%llx", value); break; } - if (oprand[i] == '"' && !strcasecmp(ins, ".byte")) { - qstr = 1; - continue; + if (!strcasecmp(ins, ".byte")) { + if (oprand[i] == '"') { + qstr = 1; + continue; + } else if (oprand[i] == '\'') { + qstr = 2; + continue; + } } if (oprand[i] == '$') { qstr = 0; @@ -597,7 +645,7 @@ int asmmon(const char *fn) { switch (oprand[i]) { case 0: puts("oof, unterminated string."); - qstr = 2; + qstr = 4; break; case '"': value = '\0'; @@ -642,6 +690,55 @@ int asmmon(const char *fn) { break; } addr[address++] = (uint8_t)value & 0xFF; + } else if (qstr == 2) { + switch (oprand[i]) { + case 0: + puts("oof, unterminated string."); + qstr = 4; + break; + case '\'': + c = '\0'; + tmpstr[slen++] = '\0'; + qstr = 3; + break; + case '\\': + switch (oprand[i+1]) { + case 'n': + value = '\n'; + c = '\n'; + tmpstr[slen++] = '\\'; + tmpstr[slen++] = 'n'; + break; + case 't': + value = '\t'; + c = '\t'; + tmpstr[slen++] = '\\'; + tmpstr[slen++] = 't'; + break; + case 'r': + value = '\r'; + c = '\r'; + tmpstr[slen++] = '\\'; + tmpstr[slen++] = 'r'; + break; + case '0': + break; + default: + value = oprand[i]; + tmpstr[slen++] = '\\'; + tmpstr[slen++] = oprand[i]; + break; + } + i++; + break; + default: + value = oprand[i]; + c = oprand[i]; + tmpstr[slen++] = c; + break; + } + if (qstr != 3) + addr[address++] = (uint8_t)value & 0xFF; } } if (!strcasecmp(ins, ".byte") && !qstr) @@ -695,13 +792,19 @@ int asmmon(const char *fn) { done |= 32; } else if (oprand != NULL && !strcasecmp(ins, "TXS")) - prefix = 0x17; + prefix = 0x13; if (!(done & 2) && oprand != NULL) { mode[0] = oprand[0]; mode[1] = oprand[1]; - if (oprand[0] == '#' || oprand[0] == '$' || (oprand[0] == '(' && (oprand[1] == '$' || oprand[1] == '%'))) { + strtok_r(oprand, "+-", &oprand2); + if (ir[0] == 'x' || ir[0] == 'y') + oprand2 = strtok_r(oprand2, ",)", &tmp2); + uint8_t isimm = oprand[0] == '#'; + /* This flag is used for checking if there is a secondary token. */ + uint8_t issectok = (oprand[1] == '$' || oprand[1] == '%' || isdigit(oprand[1])); + if (oprand[0] == '$' || (isimm && issectok) || (oprand[0] == '(' && issectok)) { oprand = strtok(oprand, "#($%"); - if (mode[0] == '#') { + if (isimm) { addrmode = IMM; done |= 32; if (mode[1] == '$') @@ -717,19 +820,27 @@ int asmmon(const char *fn) { value = strtoull(oprand, NULL, 2); else value = strtoull(oprand, NULL, 10); - if (value & 0xFFFFFF00 && (ir[0] == 'x' || ir[0] == 'y')) - prefix |= 0xF; if (mode[0] != '(') { - if (value & 0xFFFF0000 || (value <= 0xFF) || - (value & 0xFF00 && address <= 0xFFFF && (ir[0] == 'x' || ir[0] == 'y'))) { + if ((value & 0xFF0000 || value & 0xFFFF00000000 || value & 0xFFFF0000 || !(value & 0xFF00))) addrmode = ZM; - if (value & 0xFFFFFF00) - prefix |= 0xF; - } else if (value & 0xFFFFFFFF00000000 || (value & 0xFF00 && address <= 0xFFFF)) { + else if (value & 0xFF00000000 || value & 0xFF000000000000 || value & 0xFF00000000000000 || (value & 0xFF00)) addrmode = ABS; - if (value & 0xFFFFFFFF00000000) - prefix |= 0xF; - } + } + if (addrmode == ZM || addrmode == IND) { + if (value & 0xFFFF00) + prefix |= 0x7; + else if (value & 0xFFFF00000000) + prefix |= 0xB; + else if (value & 0xFFFF000000) + prefix |= 0xF; + } + if (addrmode == ABS) { + if (value & 0xFF00000000) + prefix |= 0x7; + else if (value & 0xFF000000000000) + prefix |= 0xB; + else if (value & 0xFF00000000000000) + prefix |= 0xF; } if ((addrmode == 2 || addrmode == 6) && ir != NULL) { switch (ir[0]) { @@ -752,8 +863,13 @@ int asmmon(const char *fn) { } } } else { - if (mode[0] == '(') + if (mode[0] == '(') { oprand = strtok(oprand, "#($%"); + } else if (isimm) { + oprand = strtok(oprand, "#"); + addrmode = IMM; + done |= 32; + } for (int i = 0; i < strlen(oprand); i++) { if (oprand[i] == ';') { done |= 16; @@ -761,37 +877,47 @@ int asmmon(const char *fn) { } if ((isalnum(oprand[i]) || oprand[i] == '_') && oprand[i] != '"') { value = use_label(oprand, address); - if (value & 0xFFFFFF00 && (ir[0] == 'x' || ir[0] == 'y')) - prefix |= 0xF; - if (mode[0] != '(') { - if (value & 0xFFFF0000 || (value <= 0xFF) || - (value <= 0xFFFF && address <= 0xFFFF && (ir[0] == 'x' || ir[0] == 'y'))) { - addrmode = ZM; - if (value & 0xFFFFFF00) + if (!isimm) { + if (mode[0] != '(') { + if ((value & 0xFF0000 || value & 0xFFFF00000000 || value & 0xFFFF0000 || !(value & 0xFF00))) + addrmode = ZM; + else if (value & 0xFF00000000 || value & 0xFF000000000000 || value & 0xFF00000000000000 || (value & 0xFF00)) + addrmode = ABS; + } + if (addrmode == ZM || addrmode == IND) { + if (value & 0xFFFF00) + prefix |= 0x7; + else if (value & 0xFFFF00000000) + prefix |= 0xB; + else if (value & 0xFFFF000000) prefix |= 0xF; - } else if (value & 0xFFFFFFFF00000000 || (value & 0xFF00 && address <= 0xFFFF)) { - addrmode = ABS; - if (value & 0xFFFFFFFF00000000) + } + if (addrmode == ABS) { + if (value & 0xFF00000000) + prefix |= 0x7; + else if (value & 0xFF000000000000) + prefix |= 0xB; + else if (value & 0xFF00000000000000) prefix |= 0xF; } - } - if ((addrmode == ZM || addrmode == IND) && ir != NULL && a) { - switch (ir[0]) { - case 'x': - if (addrmode == ZM) - addrmode = ZMX; - else if (addrmode == IND) - addrmode = INDX; - break; - case 'y': - if (addrmode == ZM) - addrmode = ZMY; - else if (addrmode == IND) - addrmode = INDY; - break; - default: - done |= 32; - break; + if ((addrmode == ZM || addrmode == IND) && ir != NULL && a) { + switch (ir[0]) { + case 'x': + if (addrmode == ZM) + addrmode = ZMX; + else if (addrmode == IND) + addrmode = INDX; + break; + case 'y': + if (addrmode == ZM) + addrmode = ZMY; + else if (addrmode == IND) + addrmode = INDY; + break; + default: + done |= 32; + break; + } } } sprintf(oprand, "%llx", value); @@ -799,6 +925,25 @@ int asmmon(const char *fn) { } } } + if (oprand2 != NULL && (addrtok == 1 || addrtok == 2)) { + uint64_t val2 = 0; + mode[0] = oprand2[0]; + oprand2 = strtok(oprand2, "$%"); + if (mode[0] == '$') + val2 = strtoull(oprand2, NULL, 16); + else if (mode[0] == '%') + val2 = strtoull(oprand2, NULL, 2); + else + val2 = strtoull(oprand2, NULL, 10); + switch (addrtok) { + case 1: + value += val2; + break; + case 2: + value -= val2; + break; + } + } } if (ins != NULL && !(done & 6)) { uint8_t i; @@ -861,11 +1006,11 @@ int asmmon(const char *fn) { } if (postfix != NULL && !(done & 8)) { if (!strcasecmp(postfix, "w") || !strcasecmp(postfix, "2")) { - prefix |= 0x17; + prefix |= 0x13; } else if (!strcasecmp(postfix, "d") || !strcasecmp(postfix, "4")) { - prefix |= 0x27; + prefix |= 0x23; } else if (!strcasecmp(postfix, "q") || !strcasecmp(postfix, "8")) { - prefix |= 0x37; + prefix |= 0x33; } else if (!prefix) { done |=8; } @@ -873,6 +1018,7 @@ int asmmon(const char *fn) { done |=8; } uint8_t r; + uint8_t r2; if (!(done & 8)) { r = prefix; addr[address] = prefix; @@ -880,6 +1026,7 @@ int asmmon(const char *fn) { } else { r = 0; } + r2 = 1 << ((prefix & 0x30) >> 4); switch (addrmode) { case IMPL: if (op.impl || op.impl == CPS) { @@ -921,18 +1068,21 @@ int asmmon(const char *fn) { break; default: addr[address] = value & 0xFF; - if (r & 0x10) + if (r & 0x10) { addr[address+1] = value >> 8; - if (r & 0x20) + } + if (r & 0x20) { addr[address+2] = value >> 16; addr[address+3] = value >> 24; - if (r & 0x30) + } + if (r & 0x30) { addr[address+4] = value >> 32; addr[address+5] = value >> 40; addr[address+6] = value >> 48; addr[address+7] = value >> 56; + } - address+=(1 << ((r & 0x30) >> 4)); + address+=r2; break; } break; @@ -944,14 +1094,20 @@ int asmmon(const char *fn) { if (op.zm) { addr[address++] = op.zm; addr[address] = value & 0xFF; - if ((r & 8) == 8) { - addr[address+1] = value >> 8; - addr[address+2] = value >> 16; - addr[address+3] = value >> 24; - address+=4; - } else { - address+=1; + switch ((r & 0x0C) >> 2) { + case 2: + addr[address+5] = (uint64_t)value >> 40; + addr[address+4] = (uint64_t)value >> 32; + address += 2; + case 3: + addr[address+3] = value >> 24; + address += 1; + case 1: + addr[address+2] = value >> 16; + addr[address+1] = value >> 8; + address += 2; } + address += 1; break; } else { fprintf(stderr, "oof, %s does not use Zero Matrix.\n", op.mnemonic); @@ -961,14 +1117,20 @@ int asmmon(const char *fn) { if (op.zmx) { addr[address++] = op.zmx; addr[address] = value & 0xFF; - if ((r & 8) == 8) { - addr[address+1] = value >> 8; - addr[address+2] = value >> 16; - addr[address+3] = value >> 24; - address+=4; - } else { - address+=1; + switch ((r & 0x0C) >> 2) { + case 2: + addr[address+5] = (uint64_t)value >> 40; + addr[address+4] = (uint64_t)value >> 32; + address += 2; + case 3: + addr[address+3] = value >> 24; + address += 1; + case 1: + addr[address+2] = value >> 16; + addr[address+1] = value >> 8; + address += 2; } + address += 1; break; } else { fprintf(stderr, "oof, %s does not use Zero Matrix, indexed with x.\n", op.mnemonic); @@ -978,14 +1140,20 @@ int asmmon(const char *fn) { if (op.zmy) { addr[address++] = op.zmy; addr[address] = value & 0xFF; - if ((r & 8) == 8) { - addr[address+1] = value >> 8; - addr[address+2] = value >> 16; - addr[address+3] = value >> 24; - address+=4; - } else { - address+=1; + switch ((r & 0x0C) >> 2) { + case 2: + addr[address+5] = (uint64_t)value >> 40; + addr[address+4] = (uint64_t)value >> 32; + address += 2; + case 3: + addr[address+3] = value >> 24; + address += 1; + case 1: + addr[address+2] = value >> 16; + addr[address+1] = value >> 8; + address += 2; } + address += 1; break; } else { fprintf(stderr, "oof, %s does not use Zero Matrix, indexed with y.\n", op.mnemonic); @@ -996,17 +1164,21 @@ int asmmon(const char *fn) { addr[address++] = op.abs; addr[address] = value & 0xFF; addr[address+1] = value >> 8; - if ((r & 8) == 8) { - addr[address+2] = value >> 16; - addr[address+3] = value >> 24; - addr[address+4] = value >> 32; - addr[address+5] = value >> 40; - addr[address+6] = value >> 48; - addr[address+7] = value >> 56; - address+=8; - } else { - address+=2; + switch ((r & 0x0C) >> 2) { + case 3: + addr[address+7] = value >> 56; + address += 1; + case 2: + addr[address+6] = (uint64_t)value >> 48; + addr[address+5] = (uint64_t)value >> 40; + address += 2; + case 1: + addr[address+4] = (uint64_t)value >> 32; + addr[address+3] = value >> 24; + addr[address+2] = value >> 16; + address += 3; } + address += 2; break; } else { fprintf(stderr, "oof, %s cannot be an absolute dictator.\n", op.mnemonic); @@ -1016,14 +1188,20 @@ int asmmon(const char *fn) { if (op.ind) { addr[address++] = op.ind; addr[address] = value & 0xFF; - if ((r & 8) == 8) { - addr[address+1] = value >> 8; - addr[address+2] = value >> 16; - addr[address+3] = value >> 24; - address+=4; - } else { - address+=1; + switch ((r & 0x0C) >> 2) { + case 2: + addr[address+5] = (uint64_t)value >> 40; + addr[address+4] = (uint64_t)value >> 32; + address += 2; + case 3: + addr[address+3] = value >> 24; + address += 1; + case 1: + addr[address+2] = value >> 16; + addr[address+1] = value >> 8; + address += 2; } + address += 1; break; } else { fprintf(stderr, "oof, %s cannot use pointers.\n", op.mnemonic); @@ -1033,14 +1211,20 @@ int asmmon(const char *fn) { if (op.inx) { addr[address++] = op.inx; addr[address] = value & 0xFF; - if ((r & 8) == 8) { - addr[address+1] = value >> 8; - addr[address+2] = value >> 16; - addr[address+3] = value >> 24; - address+=4; - } else { - address+=1; + switch ((r & 0x0C) >> 2) { + case 2: + addr[address+5] = (uint64_t)value >> 40; + addr[address+4] = (uint64_t)value >> 32; + address += 2; + case 3: + addr[address+3] = value >> 24; + address += 1; + case 1: + addr[address+2] = value >> 16; + addr[address+1] = value >> 8; + address += 2; } + address += 1; break; } else { fprintf(stderr, "oof, %s does not use Indexed Indirect.\n", op.mnemonic); @@ -1050,14 +1234,20 @@ int asmmon(const char *fn) { if (op.iny) { addr[address++] = op.iny; addr[address] = value & 0xFF; - if ((r & 8) == 8) { - addr[address+1] = value >> 8; - addr[address+2] = value >> 16; - addr[address+3] = value >> 24; - address+=4; - } else { - address+=1; + switch ((r & 0x0C) >> 2) { + case 2: + addr[address+5] = (uint64_t)value >> 40; + addr[address+4] = (uint64_t)value >> 32; + address += 2; + case 3: + addr[address+3] = value >> 24; + address += 1; + case 1: + addr[address+2] = value >> 16; + addr[address+1] = value >> 8; + address += 2; } + address += 1; break; } else { fprintf(stderr, "oof, %s does not use Indirect Indexed.\n", op.mnemonic); @@ -1067,6 +1257,7 @@ int asmmon(const char *fn) { #if debug if (!(done & 6)) { printf("instruction: %s, ", ins); + printf("addrmode: %s, ", adrmode[addrmode]); #if (!__GLIBC__) || (__TINYC__) printf("Postfix: %s, ", (postfix != NULL) ? postfix : "none"); #else @@ -4,101 +4,193 @@ #include <unistd.h> #define OPNAME(opcode) [opcode] = #opcode /* Get name of Opcode, for disassembly. */ -#define CPS 0x00 /* Clear Processor Status. */ -#define ADC 0x01 /* ADd with Carry. */ -#define AAB 0x02 /* Add Accumulator with carry by B register. */ -#define PHB 0x06 /* PusH B register to stack. */ -#define PHP 0x08 /* PusH Processor status to stack. */ -#define LDA 0x09 /* LoaD Accumulator. */ -#define LDY 0x0A /* LoaD Y register. */ -#define LDX 0x0B /* LoaD X register. */ -#define TAB 0x0C /* Transfer Accumulator to B. */ -#define LDB 0x0E /* LoaD B register. */ -#define JMP 0x10 /* JuMP to memory location. */ -#define SBC 0x11 /* SuBtract with Carry. */ -#define SAB 0x12 /* Subtract Accumulator with carry by B register. */ -#define PLB 0x16 /* PuLl B register to stack. */ -#define PLP 0x18 /* PuLl Processor status from stack. */ -#define TBA 0x1C /* Transfer B to Accumulator. */ -#define JSR 0x20 /* Jump to SubRoutine. */ -#define AND 0x21 /* bitwise AND with accumulator. */ -#define ABA 0x22 /* bitwise And with Accumulator, and B register. */ -#define CPB 0x26 /* ComPare B register. */ -#define STT 0x28 /* STart Threads. */ -#define STA 0x29 /* STore Accumulator. */ -#define STY 0x2A /* STore Y register. */ -#define STX 0x2B /* STore X register. */ -#define TAY 0x2C /* Transfer Accumulator to Y. */ -#define STB 0x2E /* STore B register. */ -#define BPO 0x30 /* Branch if POsitive. */ -#define ORA 0x31 /* bitwise OR with Accumulator. */ -#define OAB 0x32 /* bitwise Or with Accumulator, and B register. */ -#define SEI 0x38 /* SEt Interupt flag. */ -#define TYA 0x3C /* Transfer Y to Accumulator. */ -#define BNG 0x40 /* Branch if NeGative. */ -#define XOR 0x41 /* bitwise XOR with accumulator. */ -#define XAB 0x42 /* bitwise Xor with Accumulator, and B register. */ -#define CLI 0x48 /* CLear Interupt flag. */ -#define TAX 0x4C /* Transfer Accumulator to X. */ -#define BCS 0x50 /* Branch if Carry Set. */ -#define LSL 0x51 /* Logical Shift Left. */ -#define LLB 0x52 /* Logical shift Left accumulator by B. */ -#define SEC 0x58 /* SEt Carry flag. */ -#define TXA 0x5C /* Transfer X to Accumulator. */ -#define BCC 0x60 /* Branch if Carry Clear. */ -#define LSR 0x61 /* Logical Shift Right. */ -#define LRB 0x62 /* Logical shift Right accumulator by B. */ -#define CLC 0x68 /* CLear Carry flag. */ -#define TYX 0x6C /* Transfer Y to X. */ -#define BEQ 0x70 /* Branch if EQual. */ -#define ROL 0x71 /* ROtate Left. */ -#define RLB 0x72 /* Rotate Left accumulator by B. */ -#define SSP 0x78 /* Set Stack Protection flag. */ -#define TXY 0x7C /* Transfer X to Y. */ -#define BNE 0x80 /* Branch if Not Equal. */ -#define ROR 0x81 /* ROtate Right. */ -#define RRB 0x82 /* Rotate Right accumulator by B. */ -#define INY 0x86 /* INcrement Y register. */ -#define CSP 0x88 /* Clear Stack Protection flag. */ -#define TSX 0x8C /* Transfer Stack pointer to X. */ -#define BVS 0x90 /* Branch if oVerflow Set. */ -#define MUL 0x91 /* MULtiply accumulator. */ -#define MAB 0x92 /* Multiply Accumulator by B. */ -#define DEY 0x96 /* DEcrement Y register. */ -#define SEV 0x98 /* SEt oVerflow flag. */ -#define TXS 0x9C /* Transfer X to Stack pointer. */ -#define BVC 0xA0 /* Branch if oVerflow Clear. */ -#define DIV 0xA1 /* DIVide with accumulator. */ -#define DAB 0xA2 /* Divide Accumulator by B. */ -#define INX 0xA6 /* INcrement X register. */ -#define CLV 0xA8 /* CLear oVerflow flag. */ -#define PHY 0xAC /* PusH Y register to stack. */ -#define RTS 0xB0 /* ReTurn from Subroutine. */ -#define CMP 0xB1 /* CoMPare accumulator. */ -#define CAB 0xB2 /* Compare Accumulator, and B. */ -#define DEX 0xB6 /* DEcrement X register. */ -#define ENT 0xB8 /* ENd Threads. */ -#define CPY 0xBA /* ComPare Y register. */ -#define CPX 0xBB /* ComPare X register. */ -#define PLY 0xBC /* PuLl Y register from stack. */ -#define RTI 0xC0 /* ReTurn from Interrupt. */ -#define INC 0xC1 /* INCrement accumulator. */ -#define IAB 0xC2 /* Increment Accumulator, and B register. */ -#define WAI 0xC8 /* WAit for Interrupt. */ -#define PHX 0xCC /* PusH X register to stack. */ -#define DEC 0xD1 /* DECrement accumulator. */ -#define DBA 0xD2 /* Decrement Accumulator, and B register. */ -#define PLX 0xDC /* PuLl X register from stack. */ -#define JSL 0xE0 /* Jump to Subroutine Long. */ -#define ASR 0xE1 /* Arithmetic Shift Right. */ -#define ARB 0xE2 /* Arithmetic shift Right accumulator by B. */ -#define NOP 0xE8 /* No OPeration. */ -#define PHA 0xEC /* PusH Accumulator to stack. */ -#define RTL 0xF0 /* ReTurn from subroutine Long. */ -#define BRK 0xF8 /* BReaK. */ -#define PLA 0xFC /* PuLl Accumulator from stack. */ +#define CPS 0x00 /* Clear Processor Status. */ +#define ADC 0x01 /* ADd with Carry. */ +#define AAB 0x02 /* Add Accumulator with carry by B register. */ +#define ADC_AB 0x04 /* ADC Absolute. */ +#define LDA_IN 0x05 /* LDA Indirect. */ +#define ADC_Z 0x06 /* ADC Zero Matrix. */ +#define PHP 0x08 /* PusH Processor status to stack. */ +#define CPB 0x09 /* ComPare B register. */ +#define PHB 0x0A /* PusH B register to stack. */ +#define DEC_AB 0x0C /* DEC Absolute. */ +#define DEC_Z 0x0D /* DEC Zero Matrix. */ +#define JMP_Z 0x0E /* JuMP to memory location. */ +#define JMP 0x10 /* JMP Absolute. */ +#define SBC 0x11 /* SuBtract with Carry. */ +#define SAB 0x12 /* Subtract Accumulator with carry by B register. */ +#define SBC_AB 0x14 /* SBC Absolute. */ +#define STA_IN 0x15 /* STA Indirect. */ +#define SBC_Z 0x16 /* SBC Zero Matrix. */ +#define ENT 0x18 /* ENd Threads. */ +#define CPY 0x19 /* ComPare Y register. */ +#define PLB 0x1A /* PuLl B register to stack. */ +#define INC_AB 0x1C /* INC Absolute. */ +#define INC_Z 0x1D /* INC Zero Matrix. */ +#define JSR 0x1E /* Jump to SubRoutine. */ +#define JSL 0x20 /* Jump to Subroutine Long. */ +#define AND 0x21 /* bitwise AND with accumulator. */ +#define ABA 0x22 /* bitwise And with Accumulator, and B register. */ +#define AND_AB 0x24 /* AND Absolute. */ +#define CMP_IN 0x25 /* CMP Indirect. */ +#define AND_Z 0x26 /* AND Zero Matrix. */ +#define PLP 0x28 /* PuLl Processor status from stack. */ +#define CPX 0x29 /* ComPare X register. */ +#define PHY 0x2A /* PusH Y register to stack. */ +#define CPB_AB 0x2C /* CPB Absolute. */ +#define CPB_Z 0x2D /* CPB Zero Matrix. */ +#define BPO_Z 0x2E /* Branch if POsitive. */ +#define BPO 0x30 /* BPO Absolute. */ +#define ORA 0x31 /* bitwise OR with Accumulator. */ +#define OAB 0x32 /* bitwise Or with Accumulator, and B register. */ +#define ORA_AB 0x34 /* ORA Absolute. */ +#define LDB_IN 0x35 /* LDB Indirect. */ +#define ORA_Z 0x36 /* ORA Zero Matrix. */ +#define STT 0x38 /* STart Threads. */ +#define LDA_ZY 0x39 /* LDA Zero Matrix, indexed with Y. */ +#define PLY 0x3A /* PuLl Y register from stack. */ +#define CPX_AB 0x3C /* CPX Absolute. */ +#define CPY_Z 0x3D /* CPY Zero Matrix. */ +#define BNG_Z 0x3E /* Branch if NeGative. */ +#define BNG 0x40 /* BNG Absolute. */ +#define XOR 0x41 /* bitwise XOR with accumulator. */ +#define XAB 0x42 /* bitwise Xor with Accumulator, and B register. */ +#define XOR_AB 0x44 /* XOR Absolute. */ +#define STB_IN 0x45 /* STB Indirect. */ +#define XOR_Z 0x46 /* XOR Zero Matrix. */ +#define PHA 0x48 /* PusH Accumulator to stack. */ +#define STA_ZY 0x49 /* STA Zero Matrix, indexed with Y. */ +#define PHX 0x4A /* PusH X register to stack. */ +#define CPY_AB 0x4C /* CPY Absolute. */ +#define CPX_Z 0x4D /* CPX Zero Matrix. */ +#define BCS_Z 0x4E /* Branch if Carry Set. */ +#define BCS 0x50 /* BCS Absolute. */ +#define LSL 0x51 /* Logical Shift Left. */ +#define LLB 0x52 /* Logical shift Left accumulator by B. */ +#define LSL_AB 0x54 /* LSL Absolute. */ +#define CPB_IN 0x55 /* CPB Indirect. */ +#define LSL_Z 0x56 /* LSL Zero Matrix. */ +#define CLC 0x58 /* CLear Carry flag. */ +#define LDB_ZY 0x59 /* LDB Zero Matrix, indexed with Y. */ +#define PLX 0x5A /* PuLl X register from stack. */ +#define LDA_IY 0x5C /* LDA Indirect Indexed. */ +#define LDA_IX 0x5D /* LDA Indexed Indirect. */ +#define BCC_Z 0x5E /* Branch if Carry Clear. */ +#define BCC 0x60 /* BCC Absolute. */ +#define LSR 0x61 /* Logical Shift Right. */ +#define LRB 0x62 /* Logical shift Right accumulator by B. */ +#define LSR_AB 0x64 /* LSR Absolute. */ +#define LDY_IN 0x65 /* LDY Indirect. */ +#define LSR_Z 0x66 /* LSR Zero Matrix. */ +#define PLA 0x68 /* PuLl Accumulator from stack. */ +#define STB_ZY 0x69 /* STB Zero Matrix, indexed with Y. */ +#define TAB 0x6A /* Transfer Accumulator to B. */ +#define STA_IY 0x6C /* STA Indirect Indexed. */ +#define STA_IX 0x6D /* STA Indexed Indirect. */ +#define BEQ_Z 0x6E /* Branch if EQual. */ +#define BEQ 0x70 /* BEQ Absolute. */ +#define ROL 0x71 /* ROtate Left. */ +#define RLB 0x72 /* Rotate Left accumulator by B. */ +#define ROL_AB 0x74 /* ROL Absolute. */ +#define STY_IN 0x75 /* STY Indirect. */ +#define ROL_Z 0x76 /* ROL Zero Matrix. */ +#define SEC 0x78 /* SEt Carry flag. */ +#define LDA_ZX 0x79 /* LDA Zero Matrix, indexed with X. */ +#define TBA 0x7A /* Transfer B to Accumulator. */ +#define CMP_IY 0x7C /* CMP Indirect Indexed. */ +#define CMP_IX 0x7D /* CMP Indexed Indirect. */ +#define BNE_Z 0x7E /* Branch if Not Equal. */ +#define BNE 0x80 /* BNE Absolute. */ +#define ROR 0x81 /* ROtate Right. */ +#define RRB 0x82 /* Rotate Right accumulator by B. */ +#define ROR_AB 0x84 /* ROR Absolute. */ +#define CPY_IN 0x85 /* CPY Indirect. */ +#define ROR_Z 0x86 /* ROR Zero Matrix. */ +#define DEY 0x88 /* DEcrement Y register. */ +#define STA_ZX 0x89 /* STA Zero Matrix, indexed with X. */ +#define TAY 0x8A /* Transfer Accumulator to Y. */ +#define LDB_IY 0x8C /* LDB Indirect Indexed. */ +#define LDB_IX 0x8D /* LDB Indexed Indirect. */ +#define BVS_Z 0x8E /* Branch if oVerflow Set. */ +#define BVS 0x90 /* BVS Absolute. */ +#define MUL 0x91 /* MULtiply accumulator. */ +#define MAB 0x92 /* Multiply Accumulator by B. */ +#define MUL_AB 0x94 /* MUL Absolute. */ +#define LDX_IN 0x95 /* LDX Indirect. */ +#define MUL_Z 0x96 /* MUL Zero Matrix. */ +#define CLI 0x98 /* CLear Interupt flag. */ +#define LDB_ZX 0x99 /* LDB Zero Matrix, indexed with X. */ +#define TYA 0x9A /* Transfer Y to Accumulator. */ +#define STB_IY 0x9C /* STB Indirect Indexed. */ +#define STB_IX 0x9D /* STB Indexed Indirect. */ +#define BVC_Z 0x9E /* Branch if oVerflow Clear. */ +#define BVC 0xA0 /* BVC Absolute. */ +#define DIV 0xA1 /* DIVide with accumulator. */ +#define DAB 0xA2 /* Divide Accumulator by B. */ +#define DIV_AB 0xA4 /* DIV Absolute. */ +#define STX_IN 0xA5 /* STX Indirect. */ +#define DIV_Z 0xA6 /* DIV Zero Matrix. */ +#define INY 0xA8 /* INcrement Y register. */ +#define STB_ZX 0xA9 /* STB Zero Matrix, indexed with X. */ +#define TAX 0xAA /* Transfer Accumulator to X. */ +#define CPB_IY 0xAC /* CPB Indirect Indexed. */ +#define CPB_IX 0xAD /* CPB Indexed Indirect. */ +#define RTS 0xAE /* ReTurn from Subroutine. */ +#define RTL 0xB0 /* ReTurn from subroutine Long. */ +#define CMP 0xB1 /* CoMPare accumulator. */ +#define CAB 0xB2 /* Compare Accumulator, and B. */ +#define CMP_AB 0xB4 /* CMP Absolute. */ +#define CPX_IN 0xB5 /* CPX Indirect. */ +#define CMP_Z 0xB6 /* CMP Zero Matrix. */ +#define SEI 0xB8 /* SEt Interupt flag. */ +#define LDX 0xB9 /* LoaD X register. */ +#define TXA 0xBA /* Transfer X to Accumulator. */ +#define LDX_AB 0xBC /* LDX Absolute. */ +#define LDX_Z 0xBD /* LDX Zero Matrix. */ +#define JSR_IN 0xBE /* JSR Indirect. */ +#define RTI 0xC0 /* ReTurn from Interrupt. */ +#define LDA 0xC1 /* LoaD Accumulator. */ +#define LDA_AB 0xC4 /* LDA Absolute. */ +#define DEX 0xC5 /* DEcrement X register. */ +#define LDA_Z 0xC6 /* LDA Zero Matrix. */ +#define CLV 0xC8 /* CLear oVerflow flag. */ +#define LDX_ZY 0xC9 /* LDX Zero Matrix, indexed with Y. */ +#define TYX 0xCA /* Transfer Y to X. */ +#define STA 0xCC /* STA Absolute. */ +#define STA_Z 0xCD /* STore Accumulator. */ +#define JMP_IN 0xCE /* JMP Indirect. */ +#define TSX 0xD0 /* Transfer Stack pointer to X. */ +#define LDB 0xD1 /* LoaD B register. */ +#define LDB_AB 0xD4 /* LDB Absolute. */ +#define INX 0xD5 /* INcrement X register. */ +#define LDB_Z 0xD6 /* LDB Zero Matrix. */ +#define WAI 0xD8 /* WAit for Interrupt. */ +#define STX_ZY 0xD9 /* STX Zero Matrix, indexed with Y. */ +#define TXY 0xDA /* Transfer X to Y. */ +#define STB 0xDC /* STB Absolute. */ +#define STB_Z 0xDD /* STore B register. */ +#define TXS 0xE0 /* Transfer X to Stack pointer. */ +#define LDY 0xE1 /* LoaD Y register. */ +#define LDY_AB 0xE4 /* LDY Absolute. */ +#define DEC 0xE5 /* DECrement accumulator. */ +#define LDY_Z 0xE6 /* LDY Zero Matrix. */ +#define BRK 0xE8 /* BReaK. */ +#define LDY_ZX 0xE9 /* LDY Zero Matrix, indexed with X. */ +#define NOP 0xEA /* No OPeration. */ +#define STY 0xEC /* STY Absolute. */ +#define STY_Z 0xED /* STore Y register. */ +#define DEB 0xEE /* Decrement B register. */ +#define ASR 0xF1 /* Arithmetic Shift Right. */ +#define ARB 0xF2 /* Arithmetic shift Right accumulator by B. */ +#define ASR_AB 0xF4 /* ASR Absolute. */ +#define INC 0xF5 /* INCrement accumulator. */ +#define ASR_Z 0xF6 /* ASR Zero Matrix. */ +#define STY_ZX 0xF9 /* STY Zero Matrix, indexed with X. */ +#define STX 0xFC /* STX Absolute. */ +#define STX_Z 0xFD /* STore X register. */ +#define INB 0xFE /* Increment B register. */ -#define OPNUM 93 +#define OPNUM 90 #define C ((uint64_t)1 << 0) #define Z ((uint64_t)1 << 1) @@ -139,599 +231,578 @@ typedef struct { opent opcodes[OPNUM]; enum {IMPL, IMM, ZM, ZMX, ZMY, ABS, IND, INDX, INDY}; +static const char *adrmode[9] = { + [0] = "IMPL", + [1] = "IMM", + [2] = "ZM", + [3] = "ZMX", + [4] = "ZMY", + [5] = "ABS", + [6] = "IND", + [7] = "INDX", + [8] = "INDY" +}; static const uint8_t optype[0x100] = { [0x00] = IMPL, [0x01] = IMM, [0x02] = IMPL, - [0x03] = ABS, - [0x04] = IND, - [0x05] = ZM, - [0x06] = IMM, + [0x04] = ABS, + [0x05] = IND, + [0x06] = ZM, [0x08] = IMM, [0x09] = IMM, [0x0A] = IMM, - [0x0B] = IMM, - [0x0C] = IMPL, - [0x0E] = IMM, + [0x0C] = ABS, + [0x0D] = ZM, + [0x0E] = ZM, [0x10] = ABS, [0x11] = IMM, [0x12] = IMPL, - [0x13] = ABS, - [0x14] = INDX, - [0x15] = ZM, - [0x16] = IMM, + [0x14] = ABS, + [0x15] = IND, + [0x16] = ZM, [0x18] = IMM, - [0x19] = ABS, - [0x1A] = ABS, - [0x1B] = ABS, - [0x1C] = IMPL, - [0x1E] = ABS, - [0x20] = ZM, + [0x19] = IMM, + [0x1A] = IMM, + [0x1C] = ABS, + [0x1D] = ZM, + [0x1E] = ZM, + [0x20] = ABS, [0x21] = IMM, [0x22] = IMPL, - [0x23] = ABS, - [0x24] = INDY, - [0x25] = ZM, - [0x26] = IMM, - [0x28] = IMPL, - [0x29] = ABS, - [0x2A] = ABS, - [0x2B] = ABS, - [0x2C] = IMPL, - [0x2E] = ABS, + [0x24] = ABS, + [0x25] = IND, + [0x26] = ZM, + [0x28] = IMM, + [0x29] = IMM, + [0x2A] = IMM, + [0x2C] = ABS, + [0x2D] = ZM, + [0x2E] = ZM, [0x30] = ABS, [0x31] = IMM, [0x32] = IMPL, - [0x33] = ABS, - [0x34] = IND, - [0x35] = ZM, - [0x36] = ABS, - [0x38] = IMPL, - [0x39] = ZM, - [0x3A] = ZM, - [0x3B] = ZM, - [0x3C] = IMPL, + [0x34] = ABS, + [0x35] = IND, + [0x36] = ZM, + [0x38] = IMM, + [0x39] = ZMY, + [0x3A] = IMM, + [0x3C] = ABS, + [0x3D] = ZM, [0x3E] = ZM, [0x40] = ABS, [0x41] = IMM, [0x42] = IMPL, - [0x43] = ABS, - [0x44] = INDX, - [0x45] = ZM, + [0x44] = ABS, + [0x45] = IND, [0x46] = ZM, - [0x48] = IMPL, - [0x49] = ZM, - [0x4A] = ZM, - [0x4B] = ZM, - [0x4C] = IMPL, + [0x48] = IMM, + [0x49] = ZMY, + [0x4A] = IMM, + [0x4C] = ABS, + [0x4D] = ZM, [0x4E] = ZM, [0x50] = ABS, [0x51] = IMM, [0x52] = IMPL, - [0x53] = ABS, - [0x54] = INDY, - [0x55] = ZM, - [0x56] = IND, + [0x54] = ABS, + [0x55] = IND, + [0x56] = ZM, [0x58] = IMPL, - [0x59] = ZMX, - [0x5A] = ZMX, - [0x5B] = ZMY, - [0x5C] = IMPL, - [0x5E] = ZMX, + [0x59] = ZMY, + [0x5A] = IMM, + [0x5C] = INDY, + [0x5D] = INDX, + [0x5E] = ZM, [0x60] = ABS, [0x61] = IMM, [0x62] = IMPL, - [0x63] = ABS, - [0x64] = ZM, - [0x65] = ZM, - [0x66] = INDX, - [0x68] = IMPL, - [0x69] = ZMX, - [0x6A] = ZMX, - [0x6B] = ZMY, - [0x6C] = IMPL, - [0x6E] = ZMX, + [0x64] = ABS, + [0x65] = IND, + [0x66] = ZM, + [0x68] = IMM, + [0x69] = ZMY, + [0x6A] = IMPL, + [0x6C] = INDY, + [0x6D] = INDX, + [0x6E] = ZM, [0x70] = ABS, [0x71] = IMM, [0x72] = IMPL, - [0x73] = ABS, - [0x74] = ZM, - [0x75] = ZM, - [0x76] = INDY, + [0x74] = ABS, + [0x75] = IND, + [0x76] = ZM, [0x78] = IMPL, - [0x79] = ZMY, - [0x7A] = IND, - [0x7B] = IND, - [0x7C] = IMPL, - [0x7E] = ZMY, + [0x79] = ZMX, + [0x7A] = IMPL, + [0x7C] = INDY, + [0x7D] = INDX, + [0x7E] = ZM, [0x80] = ABS, [0x81] = IMM, [0x82] = IMPL, - [0x83] = ABS, - [0x84] = ZM, - [0x85] = ZM, - [0x86] = IMPL, + [0x84] = ABS, + [0x85] = IND, + [0x86] = ZM, [0x88] = IMPL, - [0x89] = ZMY, - [0x8A] = IND, - [0x8B] = IND, - [0x8C] = IMPL, - [0x8E] = ZMY, + [0x89] = ZMX, + [0x8A] = IMPL, + [0x8C] = INDY, + [0x8D] = INDX, + [0x8E] = ZM, [0x90] = ABS, [0x91] = IMM, [0x92] = IMPL, - [0x93] = ABS, - [0x94] = ZM, - [0x95] = ZM, - [0x96] = IMPL, + [0x94] = ABS, + [0x95] = IND, + [0x96] = ZM, [0x98] = IMPL, - [0x99] = IND, - [0x9A] = INDX, - [0x9B] = INDY, - [0x9C] = IMM, - [0x9E] = IND, + [0x99] = ZMX, + [0x9A] = IMPL, + [0x9C] = INDY, + [0x9D] = INDX, + [0x9E] = ZM, [0xA0] = ABS, [0xA1] = IMM, [0xA2] = IMPL, - [0xA3] = ABS, - [0xA4] = ZM, - [0xA5] = ZM, - [0xA6] = IMPL, + [0xA4] = ABS, + [0xA5] = IND, + [0xA6] = ZM, [0xA8] = IMPL, - [0xA9] = IND, - [0xAA] = INDX, - [0xAB] = INDY, - [0xAC] = IMM, - [0xAE] = IND, + [0xA9] = ZMX, + [0xAA] = IMPL, + [0xAC] = INDY, + [0xAD] = INDX, + [0xAE] = IMPL, [0xB0] = IMPL, [0xB1] = IMM, [0xB2] = IMPL, - [0xB3] = ABS, - [0xB4] = ZM, - [0xB5] = ZM, - [0xB6] = IMPL, + [0xB4] = ABS, + [0xB5] = IND, + [0xB6] = ZM, [0xB8] = IMPL, - [0xB9] = INDX, - [0xBA] = IMM, - [0xBB] = IMM, - [0xBC] = IMM, - [0xBE] = INDX, + [0xB9] = IMM, + [0xBA] = IMPL, + [0xBC] = ABS, + [0xBD] = ZM, + [0xBE] = IND, [0xC0] = IMPL, - [0xC1] = IMPL, - [0xC2] = IMPL, - [0xC3] = ABS, - [0xC4] = ZM, - [0xC5] = ZM, + [0xC1] = IMM, + [0xC4] = ABS, + [0xC5] = IMPL, + [0xC6] = ZM, [0xC8] = IMPL, - [0xC9] = INDX, - [0xCA] = ABS, - [0xCB] = ABS, - [0xCC] = IMM, - [0xCE] = INDX, - [0xD0] = ZM, - [0xD1] = IMPL, - [0xD2] = IMPL, - [0xD3] = ABS, - [0xD4] = ZM, - [0xD5] = ZM, - [0xD9] = INDY, - [0xDA] = ZM, - [0xDB] = ZM, - [0xDC] = IMM, - [0xDE] = INDY, - [0xE0] = ABS, + [0xC9] = ZMY, + [0xCA] = IMPL, + [0xCC] = ABS, + [0xCD] = ZM, + [0xCE] = IND, + [0xD0] = IMPL, + [0xD1] = IMM, + [0xD4] = ABS, + [0xD5] = IMPL, + [0xD6] = ZM, + [0xD8] = IMPL, + [0xD9] = ZMY, + [0xDA] = IMPL, + [0xDC] = ABS, + [0xDD] = ZM, + [0xE0] = IMM, [0xE1] = IMM, - [0xE2] = IMPL, - [0xE3] = ABS, - [0xE5] = ZM, + [0xE4] = ABS, + [0xE5] = IMPL, + [0xE6] = ZM, [0xE8] = IMPL, - [0xE9] = INDY, - [0xEA] = IND, - [0xEB] = IND, - [0xEC] = IMM, - [0xEE] = INDY, - [0xF0] = IMPL, - [0xF1] = IND, - [0xF3] = INDX, - [0xF5] = INDY, - [0xF8] = IMPL, - [0xFA] = INDX, - [0xFB] = INDY, - [0xFC] = IMM + [0xE9] = ZMX, + [0xEA] = IMPL, + [0xEC] = ABS, + [0xED] = ZM, + [0xEE] = IMPL, + [0xF1] = IMM, + [0xF2] = IMPL, + [0xF4] = ABS, + [0xF5] = IMPL, + [0xF6] = ZM, + [0xF9] = ZMX, + [0xFC] = ABS, + [0xFD] = ZM, + [0xFE] = IMPL }; static const char *mne[OPNUM] = { [ 0] = "CPS", [ 1] = "ADC", [ 2] = "AAB", - [ 3] = "JMP", - [ 4] = "PHB", - [ 5] = "PHP", - [ 6] = "LDA", - [ 7] = "LDY", - [ 8] = "LDX", - [ 9] = "TAB", - [10] = "LDB", - [11] = "SBC", - [12] = "SAB", - [13] = "PLB", - [14] = "PLP", - [15] = "TBA", - [16] = "JSR", - [17] = "AND", - [18] = "ABA", - [19] = "CPB", - [20] = "STT", - [21] = "STA", - [22] = "STY", - [23] = "STX", - [24] = "TAY", - [25] = "STB", - [26] = "BPO", - [27] = "ORA", - [28] = "OAB", - [29] = "SEI", - [30] = "TYA", - [31] = "BNG", - [32] = "XOR", - [33] = "XAB", - [34] = "CLI", - [35] = "TAX", - [36] = "BCS", - [37] = "LSL", - [38] = "LLB", - [39] = "SEC", - [40] = "TXA", - [41] = "BCC", - [42] = "LSR", - [43] = "LRB", - [44] = "CLC", - [45] = "TYX", - [46] = "BEQ", - [47] = "ROL", - [48] = "RLB", - [49] = "SSP", - [50] = "TXY", - [51] = "BNE", - [52] = "ROR", - [53] = "RRB", - [54] = "INY", - [55] = "CSP", - [56] = "TSX", - [57] = "BVS", - [58] = "MUL", - [59] = "MAB", - [60] = "DEY", - [61] = "SEV", - [62] = "TXS", - [63] = "BVC", - [64] = "DIV", - [65] = "DAB", - [66] = "INX", - [67] = "CLV", - [68] = "PHY", - [69] = "RTS", - [70] = "CMP", - [71] = "CAB", - [72] = "DEX", - [73] = "ENT", - [74] = "CPY", - [75] = "CPX", - [76] = "PLY", - [77] = "RTI", - [78] = "INC", - [79] = "IAB", - [80] = "WAI", - [81] = "PHX", - [82] = "DEC", - [83] = "DBA", - [84] = "PLX", - [85] = "JSL", + [ 3] = "PHP", + [ 4] = "CPB", + [ 5] = "PHB", + [ 6] = "DEC", + [ 7] = "JMP", + [ 8] = "SBC", + [ 9] = "SAB", + [10] = "ENT", + [11] = "CPY", + [12] = "PLB", + [13] = "INC", + [14] = "JSR", + [15] = "JSL", + [16] = "AND", + [17] = "ABA", + [18] = "PLP", + [19] = "CPX", + [20] = "PHY", + [21] = "BPO", + [22] = "ORA", + [23] = "OAB", + [24] = "STT", + [25] = "PLY", + [26] = "BNG", + [27] = "XOR", + [28] = "XAB", + [29] = "PHA", + [30] = "PHX", + [31] = "BCS", + [32] = "LSL", + [33] = "LLB", + [34] = "CLC", + [35] = "PLX", + [36] = "BCC", + [37] = "LSR", + [38] = "LRB", + [39] = "PLA", + [40] = "TAB", + [41] = "BEQ", + [42] = "ROL", + [43] = "RLB", + [44] = "SEC", + [45] = "TBA", + [46] = "BNE", + [47] = "ROR", + [48] = "RRB", + [49] = "DEY", + [50] = "TAY", + [51] = "BVS", + [52] = "MUL", + [53] = "MAB", + [54] = "CLI", + [55] = "TYA", + [56] = "BVC", + [57] = "DIV", + [58] = "DAB", + [59] = "INY", + [60] = "TAX", + [61] = "RTS", + [62] = "RTL", + [63] = "CMP", + [64] = "CAB", + [65] = "SEI", + [66] = "LDX", + [67] = "TXA", + [68] = "RTI", + [69] = "LDA", + [70] = "DEX", + [71] = "CLV", + [72] = "TYX", + [73] = "STA", + [74] = "TSX", + [75] = "LDB", + [76] = "INX", + [77] = "WAI", + [78] = "TXY", + [79] = "STB", + [80] = "TXS", + [81] = "LDY", + [82] = "BRK", + [83] = "NOP", + [84] = "STY", + [85] = "DEB", [86] = "ASR", [87] = "ARB", - [88] = "NOP", - [89] = "PHA", - [90] = "RTL", - [91] = "BRK", - [92] = "PLA" + [88] = "STX", + [89] = "INB" }; static const char *instdesc[OPNUM] = { [ 0] = "Clears the Processor Status register.", [ 1] = "ADd accumulator, with operand, Carry if needed.", [ 2] = "Add Accumulator, with B, carry if needed.", - [ 3] = "JuMP to the address specified.", - [ 4] = "PusH the number of bytes specified, from the B register to the stack.", - [ 5] = "PusH the number of bytes specified, from the Processor status register to the stack.", - [ 6] = "LoaD the value from the operand, to the Accumulator.", - [ 7] = "LoaD the value from the operand, to the Y register.", - [ 8] = "LoaD the value from the operand, to the X register.", - [ 9] = "Transfer the value from the Accumulator, to the B register.", - [10] = "LoaD the value from the operand, to the B register.", - [11] = "SuBtract accumulator, with operand, Carry if needed", - [12] = "Subtract Accumulator, with B, carry if needed.", - [13] = "PuLl the number of bytes specified, from the stack, to the B register.", - [14] = "PuLl the number of bytes specified, from the stack, to the Processor status register.", - [15] = "Transfer the value from the Y register, to the Accumulator.", - [16] = "Jump to a SubRoutine.", - [17] = "Bitwise AND accumulator, with operand.", - [18] = "Bitwise AND Accumulator, with B.", - [19] = "ComPare the B register, with operand.", - [20] = "STart a Thread.", - [21] = "STore the value from the Accumulator, in memory.", - [22] = "STore the value from the Y register, in memory.", - [23] = "STore the value from the X register, in memory.", - [24] = "Transfer the value from the Accumulator, to the Y register.", - [25] = "STore the value from the B register, in memory.", - [26] = "Branch if POsitive.", - [27] = "Bitwise OR Accumulator, with operand.", - [28] = "Bitwise OR Accumulator, with B.", - [29] = "SEt the Interrupt flag.", - [30] = "Transfer the value from the Y register, to the Accumulator.", - [31] = "Branch if NeGative.", - [32] = "Bitwise XOR Accumulator, with operand.", - [33] = "Bitwise XOR Accumulator, with B.", - [34] = "CLear the Interrupt flag.", - [35] = "Transfer the value from the Accumulator, to the X register.", - [36] = "Branch if the Carry flag is Set.", - [37] = "Logical Shift Left accumulator, with operand.", - [38] = "Logical Shift Left accumulator, with B.", - [39] = "SEt the Carry flag.", - [40] = "Transfer the value from the X register, to the Accumulator.", - [41] = "Branch if the Carry flag has been Cleared.", - [42] = "Logical Shift Right accumulator, with operand.", - [43] = "Logical Shift Right accumulator, with B.", - [44] = "CLear the Carry flag.", - [45] = "Transfer the value from the Y register, to the X register.", - [46] = "Branch if EQual (the zero flag has been set).", - [47] = "ROtate Left accumulator, with operand.", - [48] = "Rotate Left accumulator, with B.", - [49] = "Set the Stack Protection flag.", - [50] = "Transfer the value from the X register, to the Y register.", - [51] = "Branch if Not Equal (the zero flag has been cleared).", - [52] = "ROtate Right accumulator, with operand.", - [53] = "Rotate Right accumulator, with B.", - [54] = "INcrement the Y register.", - [55] = "Clear the Stack Protection flag.", - [56] = "Transfer the value from the Stack pointer, to the X register.", - [57] = "Branch if the oVerflow flag is Set.", - [58] = "MULtiply accumulator, with operand.", - [59] = "Multiply Accumulator, with B.", - [60] = "DEcrement the Y register.", - [61] = "SEt the oVerflow flag.", - [62] = "Transfer the value from the X register, to the Stack pointer.", - [63] = "Branch if the oVerflow flag has been Cleared.", - [64] = "DIVide accumulator, with operand, and put the remainder into the B register.", - [65] = "Divide Accumulator, with B, and put the remainder into the X register.", - [66] = "INcrement the X register.", - [67] = "CLear the oVerflow flag.", - [68] = "PusH the number of bytes specified, from the Y register to the stack.", - [69] = "ReTurn from a Subroutine.", - [70] = "CoMPare acumulator, with operand.", - [71] = "Compare Accumulator, with B.", - [72] = "DEcrement the X register.", - [73] = "ENd a Thread.", - [74] = "ComPare the Y register, with operand.", - [75] = "ComPare the X register, with operand.", - [76] = "PuLl the number of bytes specified, from the stack, to the Y register.", - [77] = "ReTurn from an Interrupt.", - [78] = "INCrement accumulator, or memory.", - [79] = "Increment Accumulator, and B.", - [80] = "WAIt for an interrupt.", - [81] = "PusH the number of bytes specified, from the X register to the stack.", - [82] = "DECrement accumulator, or memory.", - [83] = "Decrement Accumulator, and B.", - [84] = "PuLl the number of bytes specified, from the stack, to the X register.", - [85] = "Jump to a Subroutine, Long address.", + [ 3] = "PusH the number of bytes specified, from the Processor status register to the stack.", + [ 4] = "ComPare the B register, with operand.", + [ 5] = "PusH the number of bytes specified, from the B register to the stack.", + [ 6] = "DECrement accumulator, or memory.", + [ 7] = "JuMP to the address specified.", + [ 8] = "SuBtract accumulator, with operand, Carry if needed", + [ 9] = "Subtract Accumulator, with B, carry if needed.", + [10] = "ENd a Thread.", + [11] = "ComPare the Y register, with operand.", + [12] = "PuLl the number of bytes specified, from the stack, to the B register.", + [13] = "INCrement accumulator, or memory.", + [14] = "Jump to a SubRoutine.", + [15] = "Jump to a Subroutine, Long address.", + [16] = "Bitwise AND accumulator, with operand.", + [17] = "Bitwise AND Accumulator, with B.", + [18] = "PuLl the number of bytes specified, from the stack, to the Processor status register.", + [19] = "ComPare the X register, with operand.", + [20] = "PusH the number of bytes specified, from the Y register to the stack.", + [21] = "Branch if POsitive.", + [22] = "Bitwise OR Accumulator, with operand.", + [23] = "Bitwise OR Accumulator, with B.", + [24] = "STart a Thread.", + [25] = "PuLl the number of bytes specified, from the stack, to the Y register.", + [26] = "Branch if NeGative.", + [27] = "Bitwise XOR Accumulator, with operand.", + [28] = "Bitwise XOR Accumulator, with B.", + [29] = "PusH the number of bytes specified, from the Accumulator to the stack.", + [30] = "PusH the number of bytes specified, from the X register to the stack.", + [31] = "Branch if the Carry flag is Set.", + [32] = "Logical Shift Left accumulator, with operand.", + [33] = "Logical Shift Left accumulator, with B.", + [34] = "CLear the Carry flag.", + [35] = "PuLl the number of bytes specified, from the stack, to the X register.", + [36] = "Branch if the Carry flag has been Cleared.", + [37] = "Logical Shift Right accumulator, with operand.", + [38] = "Logical Shift Right accumulator, with B.", + [39] = "PuLl the number of bytes specified, from the stack, to the Accumulator.", + [40] = "Transfer the value from the Accumulator, to the B register.", + [41] = "Branch if EQual (the zero flag has been set).", + [42] = "ROtate Left accumulator, with operand.", + [43] = "Rotate Left accumulator, with B.", + [44] = "SEt the Carry flag.", + [45] = "Transfer the value from the Y register, to the Accumulator.", + [46] = "Branch if Not Equal (the zero flag has been cleared)", + [47] = "ROtate Right accumulator, with operand.", + [48] = "Rotate Right accumulator, with B.", + [49] = "DEcrement the Y register.", + [50] = "Transfer the value from the Accumulator, to the Y register.", + [51] = "Branch if the oVerflow flag is Set.", + [52] = "MULtiply accumulator, with operand.", + [53] = "Multiply Accumulator, with B.", + [54] = "CLear the Interrupt flag.", + [55] = "Transfer the value from the Y register, to the Accumulator.", + [56] = "Branch if the oVerflow flag has been Cleared.", + [57] = "DIVide accumulator, with operand, and put the remainder into the B register.", + [58] = "Divide Accumulator, with B, and put the remainder into the X register.", + [59] = "INcrement the Y register.", + [60] = "Transfer the value from the Accumulator, to the X register.", + [61] = "ReTurn from a Subroutine.", + [62] = "ReTurn from subroutine, Long address.", + [63] = "CoMPare acumulator, with operand.", + [64] = "Compare Accumulator, with B.", + [65] = "SEt the Interrupt flag.", + [66] = "LoaD the value from the operand, to the X register.", + [67] = "Transfer the value from the X register, to the Accumulator.", + [68] = "ReTurn from an Interrupt.", + [69] = "LoaD the value from the operand, to the Accumulator.", + [70] = "DEcrement the X register.", + [71] = "CLear the oVerflow flag.", + [72] = "Transfer the value from the Y register, to the X register.", + [73] = "STore the value from the Accumulator, in memory.", + [74] = "Transfer the value from the Stack pointer, to the X register.", + [75] = "LoaD the value from the operand, to the B register.", + [76] = "INcrement the X register.", + [77] = "WAIt for an interrupt", + [78] = "Transfer the value from the X register, to the Y register.", + [79] = "STore the value from the B register, in memory.", + [80] = "Transfer the value from the X register, to the Stack pointer.", + [81] = "LoaD the value from the operand, to the Y register.", + [82] = "BReaKpoint", + [83] = "NO oPeration", + [84] = "STore the value from the Y register, in memory.", + [85] = "DEcrement the B register.", [86] = "Arithmetic Shift Right accumulator, with operand.", [87] = "Arithmetic shift Right accumulator, with B.", - [88] = "NO oPeration.", - [89] = "PusH the number of bytes specified, from the Accumulator to the stack.", - [90] = "ReTurn from subroutine, Long address.", - [91] = "BReaKpoint.", - [92] = "PuLl the number of bytes specified, from the stack, to the Accumulator." + [88] = "STore the value from the X register, in memory.", + [89] = "INcrement the B register." }; static const char *opname[0x100] = { [0x00] = "CPS", [0x01] = "ADC #", [0x02] = "AAB", - [0x03] = "ADC a", - [0x04] = "JMP (ind)", - [0x05] = "ADC zm", - [0x06] = "PHB", - [0x08] = "PHP", - [0x09] = "LDA #", - [0x0A] = "LDY #", - [0x0B] = "LDX #", - [0x0C] = "TAB", - [0x0E] = "LDB #", + [0x04] = "ADC a", + [0x05] = "LDA ind", + [0x06] = "ADC zm", + [0x08] = "PHP #", + [0x09] = "CPB #", + [0x0A] = "PHB #", + [0x0C] = "DEC a", + [0x0D] = "DEC zm", + [0x0E] = "JMP zm", [0x10] = "JMP a", [0x11] = "SBC #", [0x12] = "SAB", - [0x13] = "SBC a", - [0x14] = "JMP (ind, x)", - [0x15] = "SBC zm", - [0x16] = "PLB", - [0x18] = "PLP", - [0x19] = "LDA a", - [0x1A] = "LDY a", - [0x1B] = "LDX a", - [0x1C] = "TBA", - [0x1E] = "LDB a", - [0x20] = "JSR", + [0x14] = "SBC a", + [0x15] = "STA ind", + [0x16] = "SBC zm", + [0x18] = "ENT #", + [0x19] = "CPY #", + [0x1A] = "PLB #", + [0x1C] = "INC a", + [0x1D] = "INC zm", + [0x1E] = "JSR zm", + [0x20] = "JSL a", [0x21] = "AND #", [0x22] = "ABA", - [0x23] = "AND a", - [0x24] = "JMP (ind), y", - [0x25] = "AND zm", - [0x26] = "CPB #", - [0x28] = "STT", - [0x29] = "STA a", - [0x2A] = "STY a", - [0x2B] = "STX a", - [0x2C] = "TAY", - [0x2E] = "STB a", - [0x30] = "BPO", + [0x24] = "AND a", + [0x25] = "CMP ind", + [0x26] = "AND zm", + [0x28] = "PLP #", + [0x29] = "CPX #", + [0x2A] = "PHY #", + [0x2C] = "CPB a", + [0x2D] = "CPB zm", + [0x2E] = "BPO zm", + [0x30] = "BPO a", [0x31] = "ORA #", [0x32] = "OAB", - [0x33] = "ORA a", - [0x34] = "JSR (ind)", - [0x35] = "ORA zm", - [0x36] = "CPB a", - [0x38] = "SEI", - [0x39] = "LDA zm", - [0x3A] = "LDY zm", - [0x3B] = "LDX zm", - [0x3C] = "TYA", - [0x3E] = "LDB zm", - [0x40] = "BNG", + [0x34] = "ORA a", + [0x35] = "LDB ind", + [0x36] = "ORA zm", + [0x38] = "STT #", + [0x39] = "LDA zmy", + [0x3A] = "PLY #", + [0x3C] = "CPX a", + [0x3D] = "CPY zm", + [0x3E] = "BNG zm", + [0x40] = "BNG a", [0x41] = "XOR #", [0x42] = "XAB", - [0x43] = "XOR a", - [0x44] = "JSR (ind, x)", - [0x45] = "XOR zm", - [0x46] = "CPB zm", - [0x48] = "CLI", - [0x49] = "STA zm", - [0x4A] = "STY zm", - [0x4B] = "STX zm", - [0x4C] = "TAX", - [0x4E] = "STB zm", - [0x50] = "BCS", + [0x44] = "XOR a", + [0x45] = "STB ind", + [0x46] = "XOR zm", + [0x48] = "PHA #", + [0x49] = "STA zmy", + [0x4A] = "PHX #", + [0x4C] = "CPY a", + [0x4D] = "CPX zm", + [0x4E] = "BCS zm", + [0x50] = "BCS a", [0x51] = "LSL #", [0x52] = "LLB", - [0x53] = "LSL a", - [0x54] = "JSR (ind), y", - [0x55] = "LSL zm", - [0x56] = "CPB (ind)", - [0x58] = "SEC", - [0x59] = "LDA zm, x", - [0x5A] = "LDY zm, x", - [0x5B] = "LDX zm, y", - [0x5C] = "TXA", - [0x5E] = "LDB zm, x", - [0x60] = "BCC", + [0x54] = "LSL a", + [0x55] = "CPB ind", + [0x56] = "LSL zm", + [0x58] = "CLC", + [0x59] = "LDB zmy", + [0x5A] = "PLX #", + [0x5C] = "LDA iny", + [0x5D] = "LDA inx", + [0x5E] = "BCC zm", + [0x60] = "BCC a", [0x61] = "LSR #", [0x62] = "LRB", - [0x63] = "LSR a", - [0x64] = "BPO zm", - [0x65] = "LSR zm", - [0x66] = "CPB (ind, x)", - [0x68] = "CLC", - [0x69] = "STA zm, x", - [0x6A] = "STY zm, x", - [0x6B] = "STX zm, y", - [0x6C] = "TYX", - [0x6E] = "STB zm, x", - [0x70] = "BEQ", + [0x64] = "LSR a", + [0x65] = "LDY ind", + [0x66] = "LSR zm", + [0x68] = "PLA #", + [0x69] = "STB zmy", + [0x6A] = "TAB", + [0x6C] = "STA iny", + [0x6D] = "STA inx", + [0x6E] = "BEQ zm", + [0x70] = "BEQ a", [0x71] = "ROL #", [0x72] = "RLB", - [0x73] = "ROL a", - [0x74] = "BNG zm", - [0x75] = "ROL zm", - [0x76] = "CPB (ind), y", - [0x78] = "SSP", - [0x79] = "LDA zm, y", - [0x7A] = "LDY (ind)", - [0x7B] = "LDX (ind)", - [0x7C] = "TXY", - [0x7E] = "LDB zm, y", - [0x80] = "BNE", + [0x74] = "ROL a", + [0x75] = "STY ind", + [0x76] = "ROL zm", + [0x78] = "SEC", + [0x79] = "LDA zmx", + [0x7A] = "TBA", + [0x7C] = "CMP iny", + [0x7D] = "CMP inx", + [0x7E] = "BNE zm", + [0x80] = "BNE a", [0x81] = "ROR #", [0x82] = "RRB", - [0x83] = "ROR a", - [0x84] = "BCS zm", - [0x85] = "ROR zm", - [0x86] = "INY", - [0x88] = "CSP", - [0x89] = "STA zm, y", - [0x8A] = "STY (ind)", - [0x8B] = "STX (ind)", - [0x8C] = "TSX", - [0x8E] = "STB zm, y", - [0x90] = "BVS", + [0x84] = "ROR a", + [0x85] = "CPY ind", + [0x86] = "ROR zm", + [0x88] = "DEY", + [0x89] = "STA zmx", + [0x8A] = "TAY", + [0x8C] = "LDB iny", + [0x8D] = "LDB inx", + [0x8E] = "BVS zm", + [0x90] = "BVS a", [0x91] = "MUL #", [0x92] = "MAB", - [0x93] = "MUL a", - [0x94] = "BCC zm", - [0x95] = "MUL zm", - [0x96] = "DEY", - [0x98] = "SEV", - [0x99] = "LDA (ind)", - [0x9A] = "LDY (ind, x)", - [0x9B] = "LDX (ind), y", - [0x9C] = "TXS", - [0x9E] = "LDB (ind)", - [0xA0] = "BVC", + [0x94] = "MUL a", + [0x95] = "LDX ind", + [0x96] = "MUL zm", + [0x98] = "CLI", + [0x99] = "LDB zmx", + [0x9A] = "TYA", + [0x9C] = "STB iny", + [0x9D] = "STB inx", + [0x9E] = "BVC zm", + [0xA0] = "BVC a", [0xA1] = "DIV #", [0xA2] = "DAB", - [0xA3] = "DIV a", - [0xA4] = "BEQ zm", - [0xA5] = "DIV zm", - [0xA6] = "INX", - [0xA8] = "CLV", - [0xA9] = "STA (ind)", - [0xAA] = "STY (ind, x)", - [0xAB] = "STX (ind), y", - [0xAC] = "PHY", - [0xAE] = "STB (ind)", - [0xB0] = "RTS", + [0xA4] = "DIV a", + [0xA5] = "STX ind", + [0xA6] = "DIV zm", + [0xA8] = "INY", + [0xA9] = "STB zmx", + [0xAA] = "TAX", + [0xAC] = "CPB iny", + [0xAD] = "CPB inx", + [0xAE] = "RTS", + [0xB0] = "RTL", [0xB1] = "CMP #", [0xB2] = "CAB", - [0xB3] = "CMP a", - [0xB4] = "BNE zm", - [0xB5] = "CMP zm", - [0xB6] = "DEX", - [0xB8] = "ENT", - [0xB9] = "LDA (ind, x)", - [0xBA] = "CPY #", - [0xBB] = "CPX #", - [0xBC] = "PLY", - [0xBE] = "LDB (ind, x)", + [0xB4] = "CMP a", + [0xB5] = "CPX ind", + [0xB6] = "CMP zm", + [0xB8] = "SEI", + [0xB9] = "LDX #", + [0xBA] = "TXA", + [0xBC] = "LDX a", + [0xBD] = "LDX zm", + [0xBE] = "JSR ind", [0xC0] = "RTI", - [0xC1] = "INC A", - [0xC2] = "IAB", - [0xC3] = "INC a", - [0xC4] = "BVS zm", - [0xC5] = "INC zm", - [0xC8] = "WAI", - [0xC9] = "STA (ind, x)", - [0xCA] = "CPY a", - [0xCB] = "CPX a", - [0xCC] = "PHX", - [0xCE] = "STB (ind, x)", - [0xD0] = "JMP zm", - [0xD1] = "DEC A", - [0xD2] = "DBA", - [0xD3] = "DEC a", - [0xD4] = "BVC zm", - [0xD5] = "DEC zm", - [0xD9] = "LDA (ind), y", - [0xDA] = "CPY zm", - [0xDB] = "CPX zm", - [0xDC] = "PLX", - [0xDE] = "LDB (ind), y", - [0xE0] = "JSL", - [0xE1] = "ASR #", - [0xE2] = "ARB", - [0xE3] = "ASR a", - [0xE5] = "ASR zm", - [0xE8] = "NOP", - [0xE9] = "STA (ind), y", - [0xEA] = "CPY (ind)", - [0xEB] = "CPX (ind)", - [0xEC] = "PHA", - [0xEE] = "STB (ind), y", - [0xF0] = "RTL", - [0xF1] = "CMP (ind)", - [0xF3] = "CMP (ind, x)", - [0xF5] = "CMP (ind), y", - [0xF8] = "BRK", - [0xFA] = "CPY (ind, x)", - [0xFB] = "CPX (ind), y", - [0xFC] = "PLA" + [0xC1] = "LDA #", + [0xC4] = "LDA a", + [0xC5] = "DEX", + [0xC6] = "LDA zm", + [0xC8] = "CLV", + [0xC9] = "LDX zmy", + [0xCA] = "TYX", + [0xCC] = "STA a", + [0xCD] = "STA zm", + [0xCE] = "JMP ind", + [0xD0] = "TSX", + [0xD1] = "LDB #", + [0xD4] = "LDB a", + [0xD5] = "INX", + [0xD6] = "LDB zm", + [0xD8] = "WAI", + [0xD9] = "STX zmy", + [0xDA] = "TXY", + [0xDC] = "STB a", + [0xDD] = "STB zm", + [0xE0] = "TXS #", + [0xE1] = "LDY #", + [0xE4] = "LDY a", + [0xE5] = "DEC A", + [0xE6] = "LDY zm", + [0xE8] = "BRK", + [0xE9] = "LDY zmx", + [0xEA] = "NOP", + [0xEC] = "STY a", + [0xED] = "STY zm", + [0xEE] = "DEB", + [0xF1] = "ASR #", + [0xF2] = "ARB", + [0xF4] = "ASR a", + [0xF5] = "INC A", + [0xF6] = "ASR zm", + [0xF9] = "STY zmx", + [0xFC] = "STX a", + [0xFD] = "STX zm", + [0xFE] = "INB" }; extern int asmmon(); diff --git a/programs/c-ports/annotated-dabbed.s b/programs/c-ports/annotated-dabbed.s new file mode 100644 index 0000000..fca6e81 --- /dev/null +++ b/programs/c-ports/annotated-dabbed.s @@ -0,0 +1,38 @@ +dabbed: ; 472: uint8_t dabbed() { + ldb #0 ; + lda.w #tok ; + sta.q ptr2 ; + tba ; +dab_st: ; + phy #2 ; + txy ; 475: while (!done) { + lda (ptr6), y ; 476: if (!cmd_buf[i]) { + beq dab_pend ; 477: done = 1; + cmp (ptr2), y ; 478: } else if (cmd_buf[i] == tok[i]) { + beq chk_str ; 479: + jmp dab_pend ; 484: } else { + ; 485: done = 1; + ; 486: } +chk_str: ; + ply #2 ; + inx ; 479: i++; + cpx #3 ; + bne dab_st ; + ldx #0 ; 480: if (i == 3) { +pnt_msg: ; + lda.w #msg ; + ldx #0 ; + stx.q ptr ; + jsl print_str ; 481: print_str(msg); + jmp dab_peqnd ; 482: break; + ; 483: } +dab_pend: ; + ply #2 ; + lda #1 ; 477/485: done = 1; + jmp dab_end ; +dab_peqnd: ; + lda #0 ; done = 0; + jmp dab_end ; +dab_end: ; 487: } + rtl ; 488: return done; + ; 489: } diff --git a/programs/c-ports/subasm.c b/programs/c-ports/subasm.c new file mode 100644 index 0000000..a996e3a --- /dev/null +++ b/programs/c-ports/subasm.c @@ -0,0 +1,33 @@ +#include "subeditor.h" +int16_t str_cmp(const char *s0, uint16_t i, const char *s1, uint16_t j) { + for (; s0[i] == s1[j]; i++, j++); + return i-j; +} + +void tokenize(char *str) { + uint16_t i = 0; + uint16_t skip = 0; + uint8_t done = 0; + while (!done) { + if (!cmd_buf[i]) { + done = 1; + } else { + switch (cmd_buf[i]) { + case '.': + if (skip = str_cmp(cmd_buf, i+1, "org", 0) > 0) { + f = TOK_ORG; + i += skip; + } else if (skip = str_cmp(cmd_buf, i+1, "byte", 0) > 0) { + f = TOK_BYTE; + i+=skip; + } + break; + } + } + } +} + +void subasm() { + uint64_t address = 0; + tokenize(cmd_buf); +} diff --git a/programs/c-ports/subeditor.c b/programs/c-ports/subeditor.c new file mode 100644 index 0000000..2d748b9 --- /dev/null +++ b/programs/c-ports/subeditor.c @@ -0,0 +1,605 @@ +#include <curses.h> +#include "subeditor.h" +#define clr_bitabl() {\ + bitabl[0x00] = 0;\ + bitabl[0x01] = 0;\ + bitabl[0x02] = 0;\ + bitabl[0x03] = 0;\ + bitabl[0x04] = 0;\ + bitabl[0x05] = 0;\ + bitabl[0x06] = 0;\ + bitabl[0x07] = 0;\ + bitabl[0x08] = 0;\ + bitabl[0x09] = 0;\ + bitabl[0x0A] = 0;\ + bitabl[0x0B] = 0;\ + bitabl[0x0C] = 0;\ + bitabl[0x0D] = 0;\ + bitabl[0x0E] = 0;\ + bitabl[0x0F] = 0;\ +} + +WINDOW *scr; + +const char *tok = "dab"; +const char *msg = "oof, you divided a, and b on me.\n"; +const char *string = "Please, type something.\n"; +const char *string2 = "You typed, "; + +const uint8_t bits[8] = { + 0x80, + 0x40, + 0x20, + 0x10, + 0x08, + 0x04, + 0x02, + 0x01 +}; + +char *buffer; +char *cmd_buf; + +uint8_t scr_row = 0; +uint8_t scr_col = 0; +uint8_t scr_trow = 0; +uint8_t scr_tcol = 0; +uint16_t scr_ptr = 0; + +uint8_t byte = 0; +uint8_t mask = 0; + +uint8_t a = 0; +uint8_t b = 0; +uint8_t c = 0; +uint8_t d = 0; +uint8_t e = 0; +uint8_t f = 0; + +uint8_t bitmask = 0; +uint8_t bitabl[16]; + +uint8_t scr_str = 0; +uint8_t scr_end = 23; +uint8_t wrapped = 0; + +void clr_buf() { + uint16_t i = 0; + for (; i < 0x2000;) { + buffer[i+0x00] = 0; + buffer[i+0x01] = 0; + buffer[i+0x02] = 0; + buffer[i+0x03] = 0; + buffer[i+0x04] = 0; + buffer[i+0x05] = 0; + buffer[i+0x06] = 0; + buffer[i+0x07] = 0; + buffer[i+0x08] = 0; + buffer[i+0x09] = 0; + buffer[i+0x0A] = 0; + buffer[i+0x0B] = 0; + buffer[i+0x0C] = 0; + buffer[i+0x0D] = 0; + buffer[i+0x0E] = 0; + buffer[i+0x0F] = 0; + buffer[i+0x10] = 0; + buffer[i+0x11] = 0; + buffer[i+0x12] = 0; + buffer[i+0x13] = 0; + buffer[i+0x14] = 0; + buffer[i+0x15] = 0; + buffer[i+0x16] = 0; + buffer[i+0x17] = 0; + buffer[i+0x18] = 0; + buffer[i+0x19] = 0; + buffer[i+0x1A] = 0; + buffer[i+0x1B] = 0; + buffer[i+0x1C] = 0; + buffer[i+0x1D] = 0; + buffer[i+0x1E] = 0; + buffer[i+0x1F] = 0; + i+=0x20; + } +} + +void clr_cbuf() { + uint16_t i = 0; + for (; i < 0x400;) { + cmd_buf[i+0x00] = 0; + cmd_buf[i+0x01] = 0; + cmd_buf[i+0x02] = 0; + cmd_buf[i+0x03] = 0; + cmd_buf[i+0x04] = 0; + cmd_buf[i+0x05] = 0; + cmd_buf[i+0x06] = 0; + cmd_buf[i+0x07] = 0; + cmd_buf[i+0x08] = 0; + cmd_buf[i+0x09] = 0; + cmd_buf[i+0x0A] = 0; + cmd_buf[i+0x0B] = 0; + cmd_buf[i+0x0C] = 0; + cmd_buf[i+0x0D] = 0; + cmd_buf[i+0x0E] = 0; + cmd_buf[i+0x0F] = 0; + cmd_buf[i+0x10] = 0; + cmd_buf[i+0x11] = 0; + cmd_buf[i+0x12] = 0; + cmd_buf[i+0x13] = 0; + cmd_buf[i+0x14] = 0; + cmd_buf[i+0x15] = 0; + cmd_buf[i+0x16] = 0; + cmd_buf[i+0x17] = 0; + cmd_buf[i+0x18] = 0; + cmd_buf[i+0x19] = 0; + cmd_buf[i+0x1A] = 0; + cmd_buf[i+0x1B] = 0; + cmd_buf[i+0x1C] = 0; + cmd_buf[i+0x1D] = 0; + cmd_buf[i+0x1E] = 0; + cmd_buf[i+0x1F] = 0; + i+=0x20; + } +} + +void update_pos() { + scr_ptr = (scr_row+scr_str)*80; + scr_ptr += scr_col; + #if !debug + wmove(scr, scr_row, scr_col); + #endif +} + +void rdrw_row() { + uint8_t i = 0; + uint16_t ptr; + scr_col = 0; + update_pos(); + ptr = scr_ptr; + for (;i < 80;i++) { + if (buffer[ptr+i]) { + #if !debug + waddch(scr, buffer[ptr+i]); + #endif + } + scr_col++; + if (!buffer[ptr+i]) { + update_pos(); + } + } + scr_col = 0; +} + +void scrl_down() { + scr_str++; + scr_end++; + #if !debug + wscrl(scr, 1); + #endif + rdrw_row(); + update_pos(); + wrapped = 0; +} + +void scrl_up() { + scr_str--; + scr_end--; + #if !debug + wscrl(scr, -1); + #endif + scr_trow = scr_row; + scr_tcol = scr_col; + rdrw_row(); + scr_row = scr_trow; + scr_col = scr_tcol; + update_pos(); + wrapped = 0; +} + +void bitpos(uint8_t row) { + uint8_t bit; + bitmask = row; + bit = row & 7; + mask = bits[bit]; + byte = bitmask >> 3; + #if debug + mvwprintw(scr, 2, 0, "bit: $%02X, row: $%02X, byte: $%02X, mask: $%02X, bitmask: $%02X\r", bit, row, byte, mask, bitmask); + #endif +} + +void clrbit (uint8_t row) { + uint8_t tmp; + uint8_t invmsk; + bitpos(row); + invmsk = ~mask; + tmp = (invmsk & (bitabl[byte])); + bitabl[byte] = tmp; +} + +void setbit (uint8_t row) { + uint8_t tmp; + bitpos(row); + tmp = (mask | (bitabl[byte])); + bitabl[byte] = tmp; +} + +uint8_t getbit() { + if (scr_str) { + bitpos(scr_row+scr_str); + } else { + bitpos(scr_row); + } + return (mask & bitabl[byte]); +} + +void findst() { + while (getbit()) { + scr_row--; + if ((int8_t)scr_row < 0) { + scr_row++; + } + } +} + +void print_char(char ch) { + uint8_t is_wrap = 0; + uint8_t is_scroll = 0; + uint8_t is_esc = 0; + uint8_t done = 0; + a = ch; + switch (ch) { + case 0x1B: + if (wgetch(scr) == 0x1B) { + is_esc = 1; + } + ch = wgetch(scr); + if (!ch) + break; + switch (ch) { + case 'A': + if (!scr_row) { + if (scr_str) { + scrl_up(); + update_pos(); + break; + } else { + break; + } + } + scr_row--; + update_pos(); + break; + case 'B': + if (scr_row == 23) { + scr_trow = scr_row; + scr_tcol = scr_col; + scrl_down(); + scr_row = scr_trow; + scr_col = scr_tcol; + update_pos(); + break; + } + scr_row++; + update_pos(); + break; + case 'C': + if (scr_col >= 79) { + ++scr_row; + if (getbit()) { + scr_col = 0; + if (scr_row >= 23) { + if (scr_str) { + wrapped = 1; + scrl_down(); + } + is_wrap = 0; + done = 1; + } else { + is_wrap = 1; + done = 1; + } + } else { + is_wrap = 0; + done = 1; + } + } else { + scr_col++; + is_wrap = 1; + done = 1; + } + if (!is_wrap) { + --scr_row; + is_wrap = 0; + } + if (done) { + update_pos(); + done = 0; + } + wrapped = 0; + break; + case 'D': + /* isleft. */ + if (!scr_col) { + /* isleft_wrp. */ + if (getbit()) { + /* wrap_dec. */ + if (scr_row) { + wrapped = 1; + scr_row--; + } + /* wrap_dec1. */ + scr_col = 79; + if (!scr_row) { + /* isleft_scrl. */ + if (wrapped) { + done = 1; + } else if (!scr_str) { + done = 0; + } else { + scrl_up(); + done = 0; + } + } else { + done = 1; + } + } else { + done = 0; + } + } else { + scr_col--; + done = 1; + } + if (done) { + update_pos(); + done = 0; + } + break; + } + break; + case '\n': + buffer[scr_ptr] = 0; + scr_col = 0; + if (scr_row == 23) { + scrl_down(); + } else { + scr_row++; + update_pos(); + } + a = '\n'; + wrefresh(scr); + break; + case 0x0C: + scr_end = 23; + scr_str = 0; + clr_bitabl(); + clr_buf(); + clr_cbuf(); + scr_row = 0; + scr_col = 0; + update_pos(); + werase(scr); + break; + case 19: + break; + case 18: + break; + case '\b': + case 0x7F: + if (!scr_col) { + if (getbit()) { + if (!scr_row) { + if (scr_str) { + scrl_up(); + scr_row++; + } else { + break; + } + } + clrbit(scr_row+scr_str); + scr_row--; + scr_col = 80; + update_pos(); + } else { + break; + } + } + scr_col--; + update_pos(); + buffer[scr_ptr] = 0; + #if !debug + wdelch(scr); + #endif + break; + default: + a = ch; + buffer[scr_ptr] = ch; + scr_col++; + #if !debug + waddch(scr, ch); + #endif + if (scr_col >= 80) { + if (scr_row >= 23) { + is_scroll = 1; + scrl_down(); + } else { + is_scroll = 0; + scr_row++; + } + scr_col = 0; + setbit(scr_row+scr_str); + update_pos(); + } + update_pos(); + break; + } +} + +uint8_t getkey(char ch) { + e = 0; + if (ch == '\n') { + uint16_t i = 0; + uint16_t ptr; + e = scr_row; + findst(scr_row); + ptr = (scr_row+scr_str)*80; + for (;buffer[ptr+i] != '\0';i++) { + cmd_buf[i] = buffer[ptr+i]; + } + } + if (e) { + scr_row = e; + } + print_char(ch); + wrefresh(scr); + if (a == '\n') { + return 0; + } else { + return 1; + } +} + +void print_str(const char *str) { + uint16_t i = 0; + for (;str[i] != '\0'; i++) { + print_char(str[i]); + } +} + +uint8_t dabbed() { + uint8_t i = 0; + uint8_t done = 0; + while (!done) { + if (!cmd_buf[i]) { + done = 1; + } else if (cmd_buf[i] == tok[i]) { + i++; + if (i == 3) { + print_str(msg); + break; + } + } else { + done = 1; + } + } + return done; +} + +int main() { + if(!scr) + scr = initscr(); + nodelay(stdscr, 0); + crmode(); + noecho(); + nl(); + curs_set(1); + werase(scr); + scrollok(scr, 1); + wrefresh(scr); + start_color(); + use_default_colors(); + init_pair(1, COLOR_WHITE, -1); + attron(COLOR_PAIR(1) | A_BOLD); + wmove(scr, 0, 0); + buffer = malloc(0x2000); + cmd_buf = malloc(0x400); + clr_bitabl(); + clr_buf(); + uint8_t end = 0; + uint8_t next = 1; + char ch; + while (!end) { + if (next) { + clr_cbuf(); + print_str(string); + next = 0; + } + #if debug + uint8_t ln = 0; + mvwprintw(scr, ln++, 0, "scr_row: $%02X, scr_col: $%02X\r", scr_row, scr_col); + mvwprintw(scr, ln++, 0, "scr_str: $%02X, scr_end: $%02X, scr_ptr: $%04X\r", scr_str, scr_end, scr_ptr); + ln+=2; + mvwprintw(scr, ln++, 0, "buffer:\r"); + for (uint16_t i = 0; i < 120; i+=5) { + mvwprintw(scr, ln++, 0, "%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x" + "%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x" + "%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x" + "%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x" + "%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x, i: $%02X\r" + , buffer[(0x00)+(i*0x10)], buffer[(0x01)+(i*0x10)], buffer[(0x02)+(i*0x10)], buffer[(0x03)+(i*0x10)] + , buffer[(0x04)+(i*0x10)], buffer[(0x05)+(i*0x10)], buffer[(0x06)+(i*0x10)], buffer[(0x07)+(i*0x10)] + , buffer[(0x08)+(i*0x10)], buffer[(0x09)+(i*0x10)], buffer[(0x0A)+(i*0x10)], buffer[(0x0B)+(i*0x10)] + , buffer[(0x0C)+(i*0x10)], buffer[(0x0D)+(i*0x10)], buffer[(0x0E)+(i*0x10)], buffer[(0x0F)+(i*0x10)] + , buffer[(0x10)+(i*0x10)], buffer[(0x11)+(i*0x10)], buffer[(0x12)+(i*0x10)], buffer[(0x13)+(i*0x10)] + , buffer[(0x14)+(i*0x10)], buffer[(0x15)+(i*0x10)], buffer[(0x16)+(i*0x10)], buffer[(0x17)+(i*0x10)] + , buffer[(0x18)+(i*0x10)], buffer[(0x19)+(i*0x10)], buffer[(0x1A)+(i*0x10)], buffer[(0x1B)+(i*0x10)] + , buffer[(0x1C)+(i*0x10)], buffer[(0x1D)+(i*0x10)], buffer[(0x1E)+(i*0x10)], buffer[(0x1F)+(i*0x10)] + , buffer[(0x20)+(i*0x10)], buffer[(0x21)+(i*0x10)], buffer[(0x22)+(i*0x10)], buffer[(0x23)+(i*0x10)] + , buffer[(0x24)+(i*0x10)], buffer[(0x25)+(i*0x10)], buffer[(0x26)+(i*0x10)], buffer[(0x27)+(i*0x10)] + , buffer[(0x28)+(i*0x10)], buffer[(0x29)+(i*0x10)], buffer[(0x2A)+(i*0x10)], buffer[(0x2B)+(i*0x10)] + , buffer[(0x2C)+(i*0x10)], buffer[(0x2D)+(i*0x10)], buffer[(0x2E)+(i*0x10)], buffer[(0x2F)+(i*0x10)] + , buffer[(0x30)+(i*0x10)], buffer[(0x31)+(i*0x10)], buffer[(0x32)+(i*0x10)], buffer[(0x33)+(i*0x10)] + , buffer[(0x34)+(i*0x10)], buffer[(0x35)+(i*0x10)], buffer[(0x36)+(i*0x10)], buffer[(0x37)+(i*0x10)] + , buffer[(0x38)+(i*0x10)], buffer[(0x39)+(i*0x10)], buffer[(0x3A)+(i*0x10)], buffer[(0x3B)+(i*0x10)] + , buffer[(0x3C)+(i*0x10)], buffer[(0x3D)+(i*0x10)], buffer[(0x3E)+(i*0x10)], buffer[(0x3F)+(i*0x10)] + , buffer[(0x40)+(i*0x10)], buffer[(0x41)+(i*0x10)], buffer[(0x42)+(i*0x10)], buffer[(0x43)+(i*0x10)] + , buffer[(0x44)+(i*0x10)], buffer[(0x45)+(i*0x10)], buffer[(0x46)+(i*0x10)], buffer[(0x47)+(i*0x10)] + , buffer[(0x48)+(i*0x10)], buffer[(0x49)+(i*0x10)], buffer[(0x4A)+(i*0x10)], buffer[(0x4B)+(i*0x10)] + , buffer[(0x4C)+(i*0x10)], buffer[(0x4D)+(i*0x10)], buffer[(0x4E)+(i*0x10)], buffer[(0x4F)+(i*0x10)] + , i); + } + mvwprintw(scr, ln++, 0, "cmd_buf:\r"); + for (uint16_t i = 0; i < 12; i+=5) { + mvwprintw(scr, ln++, 0, "%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x" + "%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x" + "%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x" + "%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x" + "%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x, i: $%02X\r" + , cmd_buf[(0x00)+(i*0x10)], cmd_buf[(0x01)+(i*0x10)], cmd_buf[(0x02)+(i*0x10)], cmd_buf[(0x03)+(i*0x10)] + , cmd_buf[(0x04)+(i*0x10)], cmd_buf[(0x05)+(i*0x10)], cmd_buf[(0x06)+(i*0x10)], cmd_buf[(0x07)+(i*0x10)] + , cmd_buf[(0x08)+(i*0x10)], cmd_buf[(0x09)+(i*0x10)], cmd_buf[(0x0A)+(i*0x10)], cmd_buf[(0x0B)+(i*0x10)] + , cmd_buf[(0x0C)+(i*0x10)], cmd_buf[(0x0D)+(i*0x10)], cmd_buf[(0x0E)+(i*0x10)], cmd_buf[(0x0F)+(i*0x10)] + , cmd_buf[(0x10)+(i*0x10)], cmd_buf[(0x11)+(i*0x10)], cmd_buf[(0x12)+(i*0x10)], cmd_buf[(0x13)+(i*0x10)] + , cmd_buf[(0x14)+(i*0x10)], cmd_buf[(0x15)+(i*0x10)], cmd_buf[(0x16)+(i*0x10)], cmd_buf[(0x17)+(i*0x10)] + , cmd_buf[(0x18)+(i*0x10)], cmd_buf[(0x19)+(i*0x10)], cmd_buf[(0x1A)+(i*0x10)], cmd_buf[(0x1B)+(i*0x10)] + , cmd_buf[(0x1C)+(i*0x10)], cmd_buf[(0x1D)+(i*0x10)], cmd_buf[(0x1E)+(i*0x10)], cmd_buf[(0x1F)+(i*0x10)] + , cmd_buf[(0x20)+(i*0x10)], cmd_buf[(0x21)+(i*0x10)], cmd_buf[(0x22)+(i*0x10)], cmd_buf[(0x23)+(i*0x10)] + , cmd_buf[(0x24)+(i*0x10)], cmd_buf[(0x25)+(i*0x10)], cmd_buf[(0x26)+(i*0x10)], cmd_buf[(0x27)+(i*0x10)] + , cmd_buf[(0x28)+(i*0x10)], cmd_buf[(0x29)+(i*0x10)], cmd_buf[(0x2A)+(i*0x10)], cmd_buf[(0x2B)+(i*0x10)] + , cmd_buf[(0x2C)+(i*0x10)], cmd_buf[(0x2D)+(i*0x10)], cmd_buf[(0x2E)+(i*0x10)], cmd_buf[(0x2F)+(i*0x10)] + , cmd_buf[(0x30)+(i*0x10)], cmd_buf[(0x31)+(i*0x10)], cmd_buf[(0x32)+(i*0x10)], cmd_buf[(0x33)+(i*0x10)] + , cmd_buf[(0x34)+(i*0x10)], cmd_buf[(0x35)+(i*0x10)], cmd_buf[(0x36)+(i*0x10)], cmd_buf[(0x37)+(i*0x10)] + , cmd_buf[(0x38)+(i*0x10)], cmd_buf[(0x39)+(i*0x10)], cmd_buf[(0x3A)+(i*0x10)], cmd_buf[(0x3B)+(i*0x10)] + , cmd_buf[(0x3C)+(i*0x10)], cmd_buf[(0x3D)+(i*0x10)], cmd_buf[(0x3E)+(i*0x10)], cmd_buf[(0x3F)+(i*0x10)] + , cmd_buf[(0x40)+(i*0x10)], cmd_buf[(0x41)+(i*0x10)], cmd_buf[(0x42)+(i*0x10)], cmd_buf[(0x43)+(i*0x10)] + , cmd_buf[(0x44)+(i*0x10)], cmd_buf[(0x45)+(i*0x10)], cmd_buf[(0x46)+(i*0x10)], cmd_buf[(0x47)+(i*0x10)] + , cmd_buf[(0x48)+(i*0x10)], cmd_buf[(0x49)+(i*0x10)], cmd_buf[(0x4A)+(i*0x10)], cmd_buf[(0x4B)+(i*0x10)] + , cmd_buf[(0x4C)+(i*0x10)], cmd_buf[(0x4D)+(i*0x10)], cmd_buf[(0x4E)+(i*0x10)], cmd_buf[(0x4F)+(i*0x10)] + , i); + } + mvwprintw(scr, ln++, 0, "bitabl:\r"); + mvwprintw(scr, ln++, 0, "%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x\r" + , bitabl[0x00], bitabl[0x01], bitabl[0x02], bitabl[0x03] + , bitabl[0x04], bitabl[0x05], bitabl[0x06], bitabl[0x07] + , bitabl[0x08], bitabl[0x09], bitabl[0x0A], bitabl[0x0B] + , bitabl[0x0C], bitabl[0x0D], bitabl[0x0E], bitabl[0x0F]); + + wrefresh(scr); + #endif + ch = wgetch(scr); + if (ch == 0x11) { + end = 1; + continue; + } + if (!getkey(ch)) { + if (dabbed()) { + print_str(string2); + print_str(cmd_buf); + print_char('\n'); + } + next = 1; + } + } + endwin(); + free(buffer); + free(cmd_buf); + return 0; +} diff --git a/programs/c-ports/subeditor.h b/programs/c-ports/subeditor.h new file mode 100644 index 0000000..f20088d --- /dev/null +++ b/programs/c-ports/subeditor.h @@ -0,0 +1,36 @@ +#include <stdlib.h> +#include <stdint.h> +#include <stdio.h> +#include <string.h> + +#define debug 0 + +extern char *buffer; +extern char *cmd_buf; + +extern uint8_t scr_row = 0; +extern uint8_t scr_col = 0; +extern uint8_t scr_trow = 0; +extern uint8_t scr_tcol = 0; +extern uint16_t scr_ptr = 0; + +extern uint8_t byte = 0; +extern uint8_t mask = 0; + +extern uint8_t a = 0; +extern uint8_t b = 0; +extern uint8_t c = 0; +extern uint8_t d = 0; +extern uint8_t e = 0; +extern uint8_t f = 0; + +extern uint8_t bitmask = 0; +extern uint8_t bitabl[16]; + +extern uint8_t scr_str = 0; +extern uint8_t scr_end = 23; +extern uint8_t wrapped = 0; + +extern void print_str(const char *str); +int16_t str_cmp(const char *s0, uint16_t i, const char *s1, uint16_t j) +extern void subasm(); diff --git a/programs/subasm-2.s b/programs/subasm-2.s new file mode 100644 index 0000000..f77116b --- /dev/null +++ b/programs/subasm-2.s @@ -0,0 +1,151 @@ +; SuBAsm +; The Sux Bootstrapped Assembler. +; +; by mr b0nk 500 <b0nk@b0nk.xyz> + + +.org $A000 +; String Constants. +prg_name: + .byte "SuBAsm" +ver_txt: + .byte ", version " +ver_num: + .byte "0.1" + +; Directives. +dir: + .byte "org" + .byte "byte" + .byte "word" + .byte "dword" + .byte "qword" +tok: + .byte '.' + .byte '#' + .byte '$' + .byte '%' + .byte '(' + .byte ')' + .byte ',' + +mne: + .byte "AAB" + .byte "ABA" + .byte "ADC" + .byte "AND" + .byte "ARB" + .byte "ASR" + .byte "BCC" + .byte "BCS" + .byte "BEQ" + .byte "BNE" + .byte "BNG" + .byte "BPO" + .byte "BRK" + .byte "BVC" + .byte "BVS" + .byte "CAB" + .byte "CLC" + .byte "CLI" + .byte "CLV" + .byte "CMP" + .byte "CPB" + .byte "CPS" + .byte "CPX" + .byte "CPY" + .byte "DAB" + .byte "DEB" + .byte "DEC" + .byte "DEX" + .byte "DEY" + .byte "DIV" + .byte "ENT" + .byte "INB" + .byte "INC" + .byte "INX" + .byte "INY" + .byte "JMP" + .byte "JSL" + .byte "JSR" + .byte "LDA" + .byte "LDB" + .byte "LDX" + .byte "LDY" + .byte "LLB" + .byte "LRB" + .byte "LSL" + .byte "LSR" + .byte "MAB" + .byte "MUL" + .byte "NOP" + .byte "OAB" + .byte "ORA" + .byte "PHA" + .byte "PHB" + .byte "PHP" + .byte "PHX" + .byte "PHY" + .byte "PLA" + .byte "PLB" + .byte "PLP" + .byte "PLX" + .byte "PLY" + .byte "RLB" + .byte "ROL" + .byte "ROR" + .byte "RRB" + .byte "RTI" + .byte "RTL" + .byte "RTS" + .byte "SAB" + .byte "SBC" + .byte "SEC" + .byte "SEI" + .byte "STA" + .byte "STB" + .byte "STT" + .byte "STX" + .byte "STY" + .byte "TAB" + .byte "TAX" + .byte "TAY" + .byte "TBA" + .byte "TSX" + .byte "TXA" + .byte "TXS" + .byte "TXY" + .byte "TYA" + .byte "TYX" + .byte "WAI" + .byte "XAB" + .byte "XOR" + +; Start of program code. +.org $8600 +subasm: + ldb #0 + lda.w #tok + sta.q ptr2 + tba + jsl chk_tok + + jsl chk_mne +chk_tok: + phy #2 + txy + lda (ptr6), y + cmp (ptr2), y + ply #2 + cpx #7 + beq tok_false +tok_true: + inb +tok_false: + stb f +tok_end: + ldb #0 + rtl + +chk_mne: + ply #2 diff --git a/programs/subeditor.s b/programs/subeditor.s index 159dc1f..5769936 100644 --- a/programs/subeditor.s +++ b/programs/subeditor.s @@ -3,13 +3,28 @@ ; Writen in Sux assembly by ; mr b0nk 500 <b0nk@b0nk.xyz> -; Instruction mnemonics, -; and opcodes. +; String Literals/Constants. .org $1000 tok: .byte "dab" msg: .byte "oof, you divided a, and b on me.\n" +string: + .byte "Please, type something.\n" +string2: + .byte "You typed, " + +; Linewrap bitmask table. +.org $1100 +bits: + .byte $80 + .byte $40 + .byte $20 + .byte $10 + .byte $08 + .byte $04 + .byte $02 + .byte $01 ; Input buffer. .org $2000 @@ -31,6 +46,7 @@ scr_tcol: .byte $0 scr_ptr: .word $0 +; Registers. a: .byte $0 b: @@ -43,21 +59,12 @@ e: .byte $0 f: .byte $0 -string: - .byte "Please, type something.\n" -string2: - .byte "You typed, " +; This register is always zero. +zero: + .qword $0 +; End of registers. end: .byte $0 -bits: - .byte $80 - .byte $40 - .byte $20 - .byte $10 - .byte $08 - .byte $04 - .byte $02 - .byte $01 bitmask: .byte $0 bitabl: @@ -72,13 +79,17 @@ wrapped: ; Pointers ptr: - .qword buffer -cptr: - .qword cmd_buf -tptr: - .qword tok -mptr: - .qword msg + .qword $0 +ptr2: + .qword $0 +ptr3: + .qword $0 +ptr4: + .qword $0 +ptr5: + .qword $0 +ptr6: + .qword $0 ; Main program .org $8000 @@ -87,44 +98,93 @@ reset: ldx.w #$FFFF txs ldy #0 + tyx lda #23 sta scr_end - lda #0 + lda.w #buffer + sta.q ptr5 + lda.w #cmd_buf + sta.q ptr6 + tya sta scr_str - ldx #8 sta.q bitabl - sta.q bitabl, x - tax + sta.q bitabl+8 jsl clr_buf jmp start clr_buf: - lda #0 + phb #1 + ldb #0 +clr_buf_st: cpy.w #$1FFF - beq clr_buf_end - sta (ptr), y - iny - jmp clr_buf + bcs clr_buf_end + sta.q (ptr5), y + tya + adc #8 + tay + tba + sta.q (ptr5), y + tya + adc #8 + tay + tba + sta.q (ptr5), y + tya + adc #8 + tay + tba + sta.q (ptr5), y + tya + adc #8 + tay + tba + jmp clr_buf_st clr_buf_end: - ldy.w #0 + ldy.w zero + plb #1 rtl start: lda #0 - tax sta $C000 + tax phy #2 - ldy.w #0 + tay jsl clr_cbuf ply #2 - jmp print + lda.w #string + jsl print_str + lda.w zero + jmp rset_a clr_cbuf: + phb #1 + ldb #0 +clr_cbuf_st: cpy.w #$3FF - beq clr_cbuf_end - sta (cptr), y - iny - jmp clr_cbuf + bcs clr_cbuf_end + sta.q (ptr6), y + tya + adc #8 + tay + tba + sta.q (ptr6), y + tya + adc #8 + tay + tba + sta.q (ptr6), y + tya + adc #8 + tay + tba + sta.q (ptr6), y + tya + adc #8 + tay + tba + jmp clr_cbuf_st clr_cbuf_end: + plb #1 rtl pull_y: @@ -140,15 +200,23 @@ read: beq parse ; We got a newline, so start parsing the line. jmp rset_a ; We didn't get a newline, so keep getting more characters. -print: +print_str: + sta.q ptr + ldb #0 + tba +pntstr_st: phy #2 txy - lda string, y ; Get character at offset x. - beq pull_y ; Did we find a null terminator? + lda (ptr), y ; Get character at offset x. + beq pntstr_end ; Did we find a null terminator? ply #2 inx jsl print_char - jmp print + jmp pntstr_st +pntstr_end: + ply #2 + rtl + getbit: clc @@ -167,12 +235,6 @@ getbt1: cmp #1 jmp bitout -;putbit: -; ldx scr_row -;putbt1: -; bcc setbit - - clrbit: jsl bitpos xor #$FF @@ -191,11 +253,19 @@ setbit: jmp bitsav bitpos: + pha #1 + lda.w #bits + sta.q ptr3 + lda.w zero + pla #1 stx bitmask txa and #7 + phy #2 + tay tax - lda bits, x + lda (ptr3), y + ply #2 pha #1 lda bitmask lsr #3 @@ -240,11 +310,11 @@ cmd_cpy: tay ldx.w #$0 cmd_cpy_strt: - lda (ptr), y + lda (ptr5), y beq getchar_pnt phy #2 txy - sta (cptr), y + sta (ptr6), y inx ply #2 iny @@ -294,7 +364,7 @@ print_char: sta a printc: lda a - sta (ptr), y ; Store typed character into the input buffer. + sta (ptr5), y ; Store typed character into the input buffer. inc scr_col ; Increment the cursor's x coordinate. iny printc_2: @@ -344,7 +414,7 @@ printc_end: nl: lda #0 - sta (ptr), y ; Store said terminator into the input buffer. + sta (ptr5), y ; Store said terminator into the input buffer. sta scr_col lda scr_row cmp #23 @@ -365,11 +435,12 @@ clr_scr: sta scr_end lda #0 sta scr_str - ldx #8 sta.q bitabl - sta.q bitabl, x + sta.q bitabl+8 tay jsl clr_buf + tay + jsl clr_cbuf sta scr_col sta scr_row jsl update_pos @@ -397,73 +468,73 @@ stp_end: jmp printc_end back: - lda #$7F - sta $C001 - dey ; Decrement buffer offset. - lda #0 ; Put a null terminator, in place of the backspace. - sta (ptr), y ; Place it into the input buffer. - dec scr_col - jsl update_pos - jmp printc_end ; Get next character. + lda #$7F ; Print a backspace to the screen. + sta $C001 ; + dey ; Decrement the buffer's offset. + lda #0 ; Place a null terminator + sta (ptr5), y ; into the buffer. + dec scr_col ; Move the cursor back by one column, + jsl update_pos ; and update it's position. + jmp printc_end ; We are done. bs: - lda scr_col ; Are we at the start of the buffer? - beq back_wrap - jmp back ; We are not, so add the backspace to the buffer. + lda scr_col ; Are we at the far left of the screen? + beq back_wrap ; Yes, so check for a wrapped line. + jmp back ; No, so add the backspace to the buffer. back_wrap: - jsl getbit - bcs back_wrap1 - jmp printc_end + jsl getbit ; Is this line, a wrapped line? + bcs back_wrap1 ; Yes, so check if the cursor is at the top. + jmp printc_end ; No, so we're done. back_wrap1: - lda scr_row - beq back_wrap2 - jmp backwrp + lda scr_row ; Are we at the top of the screen? + beq back_wrap2 ; Yes, so check if the screen is at the top of the buffer. + jmp backwrp ; No, so start clearing the wrap bit. back_wrap2: - lda scr_str - bne back_scrl - jmp printc_end + lda scr_str ; Are we at the top of the buffer? + bne back_scrl ; Yes, so scroll up. + jmp printc_end ; No, so we're done. back_scrl: - clc - jsl scrl_up - inc scr_row + clc ; Clear the carry flag, so that we don't get odd behaviour. + jsl scrl_up ; Scroll up. + inc scr_row ; Move down by one row. backwrp: - clc - lda scr_row - adc scr_str - tax + clc ; Clear the carry flag. + lda scr_row ; Add the cursor's row position, + adc scr_str ; and the screen's starting row. + tax ; Transfer that into X. backwrp2: - dec scr_row - jsl clrbit - ldb #80 - stb scr_col - jsl update_pos - jmp back + dec scr_row ; Move up by one row. + jsl clrbit ; Clear the wrap bit for this row. + ldb #80 ; Move the cursor to the absolute right of the screen. + stb scr_col ; + jsl update_pos ; Update the cursor's position. + jmp back ; Delete the previous character. esc: - lda $C000 ; Skip the '['. - lda $C002 - cmp #$1B - beq shftesc lda $C000 ; Get the next character. + lda $C002 ; + cmp #$1B ; Is this character an escape character? + beq shftesc ; Yes, so check the other set of escape routines. + lda $C000 ; No, so wait for the next character. beq printc_end ; We have an error, so discard it, and go back to getting user input. lda $C002 ; Get the escape code. sta c ; Store the escape code, until we need it. - lda #0 - sta d + lda #0 ; Set the D pseudo register to zero. + sta d ; jsl isup ; Check if the user pressed up. - lda d - bne esc_end - jsl isdown ; Check if the user pressed down. - lda d - bne esc_end - lda #0 - jsl isleft ; Check if the user pressed left. - lda d - bne esc_end - jsl isright ; Check if the user pressed right. + lda d ; Did the user press up? + bne esc_end ; Yes, so we're done. + jsl isdown ; No, so check if the user pressed down. + lda d ; Did the user press down? + bne esc_end ; Yes, so we're done. + lda #0 ; No, so check if the user pressed left. + jsl isleft ; + lda d ; Did the user press left? + bne esc_end ; Yes, so we're done. + jsl isright ; No, so check if the user pressed right. esc_end: - lda #0 - sta d + lda #0 ; Set the D pseudo register to zero. + sta d ; jmp printc_end ; Go back to getting user input. shftesc: @@ -472,34 +543,32 @@ shftesc: beq printc_end ; We have an error, so discard it, and go back to getting user input. lda $C002 ; Get the escape code. sta c ; Store the escape code, until we need it. - lda #0 - sta d + lda #0 ; + sta d ; jsl isshftup ; Check if the user pressed shift+up. - lda d - bne shftesc_end + lda d ; + bne shftesc_end ; jsl isshftdown ; Check if the user pressed shift+down. shftesc_end: - lda #0 - sta d + lda #0 ; + sta d ; jmp printc_end ; Go back to getting user input. isup: lda c ; No, so load the escape code back into the accumulator. cmp #$41 ; Did the user press the up arrow key? - bne isup_done ; Yes, so return. - lda #1 - sta d - lda scr_row ; Is the cursor at the top of the screen? - beq isup_scrl ; Yes, so return. + bne isup_done ; Yes, so we're done. + lda scr_row ; No, so is the cursor at the top of the screen? + beq isup_scrl ; Yes, so check if we need to scroll. isup_2: lda c ; No, so load the escape code back into the accumulator. cmp #$41 ; Did the user press the up arrow key? beq up ; Yes, so move the cursor up. - jmp isup_done + jmp isup_done ; No, so we're done isup_scrl: - lda scr_str - beq isup_done - jsl scrl_up + lda scr_str ; Are we at the top of the screen buffer? + beq isup_done ; Yes, so we're done. + jsl scrl_up ; No, so scroll up. isup_done: rtl ; End of isup. @@ -515,51 +584,53 @@ isdown: beq down ; Yes, so move the cursor down. jmp isdown_done isdown_scrl: - lda scr_row - sta scr_trow - lda scr_col - sta scr_tcol - jsl scrl_down - lda scr_trow - sta scr_row - lda scr_tcol - sta scr_col + lda scr_row ; Save the cursor's row number. + sta scr_trow ; + lda scr_col ; Save the cursor's column number. + sta scr_tcol ; + jsl scrl_down ; Scroll down. + lda scr_trow ; Load the cursor's row number. + sta scr_row ; + lda scr_tcol ; Load the cursor's column number. + sta scr_col ; isdown_done: rtl ; End of isdown. isright: lda c ; No, so load the escape code back into the accumulator. cmp #$43 ; Did the user press the right arrow key? - bne isright_done - lda scr_col ; Start checking the x coordinate of the cursor. + bne isright_dne ; No, so we're done. + lda scr_col ; Yes, so start checking the x coordinate of the cursor. cmp #79 ; Is the cursor at the far right of the screen? beq isright_wrp ; Yes, so check if this is a wrapped line. jmp right ; No, so move the cursor right, like normal. isright_wrp: - inc scr_row - jsl getbit - bcs wrap_inc - dec scr_row - jmp isright_done -isright_scrl: - lda scr_str - beq isright_end - lda #1 - sta wrapped - jsl scrl_down - dec scr_row - jmp isright_end + inc scr_row ; Move down a row. + jsl getbit ; Is the current line, a wrapped line? + bcs wrap_inc ; Yes, so leave the cursor where it is. + dec scr_row ; No, so move the cursor back up a row. + jmp isright_dne ; We are done. +isright_scr: + lda scr_str ; Are we at the top of the screen buffer? + beq isright_end ; Yes, so we're done. + lda #1 ; No, so scroll down. + sta wrapped ; Set the wrapped flag. + jsl scrl_down ; Scroll down. + jmp isright_end ; We are done. wrap_inc: - lda #0 - sta scr_col - lda scr_row - cmp #23 - bcs isright_scrl + lda #0 ; Set the cursor to the far left of the screen. + sta scr_col ; + lda scr_row ; Get the current row number. + cmp #23 ; Are we at the bottom of the screen? + bcs isright_scr ; Yes, so check if we are scrolling down. + jmp isright_nd2 ; We are done. isright_end: - jsl update_pos -isright_done: - lda #0 - sta wrapped + dec scr_row ; Move back up a row. +isright_nd2: + jsl update_pos ; Update the cursor position. +isright_dne: + lda #0 ; Unset the wrapped flag. + sta wrapped ; rtl ; End of isright. isleft: @@ -571,37 +642,37 @@ isleft: lda c ; No, so load the escape code back into the accumulator. cmp #$44 ; Did the user press the left arrow key? beq left ; Yes, so move the cursor left. - jmp isleft_done + jmp isleft_done ; We are done. isleft_wrp: - jsl getbit - bcs wrap_dec - jmp isleft_done + jsl getbit ; Is the current line, a wrapped line? + bcs wrap_dec ; Yes, so wrap back up a line. + jmp isleft_done ; No, so return. wrap_dec: - lda scr_row - beq wrap_dec1 - lda #1 - sta wrapped - dec scr_row + lda scr_row ; Is the cursor at the top of the screen? + beq wrap_dec1 ; Yes, so don't move up a row. + lda #1 ; No, so move up a row. + sta wrapped ; Set the wrapped flag. + dec scr_row ; Move the cursor up by one row. wrap_dec1: - lda #79 - sta scr_col - lda #1 - sta d - lda scr_row - beq isleft_scrl - jmp isleft_end + lda #79 ; Move the Cursor to the far right of the screen. + sta scr_col ; + lda #1 ; Tell the escape routine to stop after this. + sta d ; + lda scr_row ; Are we at the top of the screen? + beq isleft_scrl ; Yes, so check if we need to scroll. + jmp isleft_end ; No, so we're done. isleft_scrl: - lda wrapped - bne isleft_end - lda scr_str - beq isleft_done - jsl scrl_up - jmp isleft_done + lda wrapped ; Was the wrapped flag set somewhere else? + bne isleft_end ; Yes so we're done. + lda scr_str ; No, but are we actually at the top of the screen buffer? + beq isleft_done ; Yes, so we're done. + jsl scrl_up ; No, so scroll up. + jmp isleft_done ; We are done. isleft_end: - jsl update_pos + jsl update_pos ; Update the cursor position. isleft_done: - lda #0 - sta wrapped + lda #0 ; Unset the wrapped flag. + sta wrapped ; rtl ; End of isleft. up: @@ -619,7 +690,7 @@ down: right: inc scr_col jsl update_pos - jmp isright_done + jmp isright_dne left: dec scr_col jsl update_pos @@ -773,12 +844,12 @@ rdrw_row: sta scr_col jsl update_pos rdrow_st: - lda (ptr), y + lda (ptr5), y beq rdrow_inc sta $C001 rdrow_inc: inc scr_col - lda (ptr), y + lda (ptr5), y beq rdrow_skip iny rdrow_inc1: @@ -819,68 +890,54 @@ rdrow_done: ; rtl result: - phy #2 - txy - lda string2, y - beq rset_y ; Reset y, if we hit the null terminator. - ply #2 - jsl print_char ; Print 'You have typed, ' - inx - jmp result ; Keep printing. - -rset_y: - ply #2 + lda.w #string2 + ldx.w zero + jsl print_str +rset_x: lda #0 ; Reset a. - tax ; Reset y. + tax ; Reset x. jmp print_buf ; Print the input buffer. dabbed: + ldb #0 + lda.w #tok + sta.q ptr2 + tba +dab_st: phy #2 txy - lda (cptr), y ; Get a character from the input buffer. + lda (ptr6), y ; Get a character from the input buffer. beq dab_pend ; Are we done with printing the buffer? - cmp (tptr), y - bcc dab_pend + cmp (ptr2), y beq chk_str - bcs dab_pend + jmp dab_pend chk_str: ply #2 inx cpx #3 - bne dabbed + bne dab_st ldx #0 pnt_msg: - phy #2 - txy - lda (mptr), y ; Get a character from the input buffer. - beq dab_peqnd ; Are we done with printing the buffer? - ply #2 - jsl print_char - inx - jmp pnt_msg ; Keep printing the buffer. + lda.w #msg + ldx #0 + stx.q ptr + jsl print_str + jmp dab_peqnd dab_pend: ply #2 lda #1 jmp dab_end dab_peqnd: - ply #2 lda #0 jmp dab_end dab_end: rtl print_buf: - phy #2 - txy - lda (cptr), y ; Get a character from the input buffer. - beq cmd_clr ; Are we done with printing the buffer? - ply #2 - jsl print_char - inx - jmp print_buf ; Keep printing the buffer. - + lda.w #cmd_buf + jsl print_str + lda.w zero cmd_clr: - ply #2 lda #10 jsl print_char jmp start @@ -896,5 +953,19 @@ cmd_clr: .qword spin .qword spin .qword spin +r +;.org $8000 +;v +;.org $8100 +;v +;.org $8200 +;v +;.org $8300 +;v +;.org $8400 +;v +;.org $8500 +;v +;q done @@ -77,6 +77,7 @@ void *run(void *args) { uint8_t rs; uint8_t regsize; uint8_t tmp; + uint8_t tmp2; char *s = malloc(2048); #if !bench uint8_t lines = (6*thread)+2; @@ -89,6 +90,15 @@ void *run(void *args) { #if bench gettimeofday(&str[thread], 0); #endif +#if debug && !bench + #if keypoll + pthread_mutex_lock(&mutex); + #endif + werase(scr); + #if keypoll + pthread_mutex_unlock(&mutex); + #endif +#endif while (!end) { address = 0; if (wai) { @@ -115,7 +125,7 @@ void *run(void *args) { kbd_rdy &= (uint8_t)~(1 << thread); } prefix = addr[cpu->pc[thread]]; - if ((prefix & 0x07) == 0x07) + if ((prefix & 0x03) == 0x03) cpu->pc[thread]++; else prefix = 0; @@ -142,9 +152,12 @@ void *run(void *args) { #endif #endif - addrsize = (prefix & 8) == 8; + addrsize = (prefix & 0x0C) >> 2; rs = (prefix & 0x30) >> 4; - regsize = (1 << rs); + if (rs) + regsize = (1 << rs); + else + regsize = 1; address = cpu->pc[thread]; cpu->pc[thread]++; iclk++; @@ -186,13 +199,29 @@ void *run(void *args) { case ZMX: case ZMY: address = addr[cpu->pc[thread]]; - if (addrsize) { - address |= addr[cpu->pc[thread]+1] << 8; - address |= addr[cpu->pc[thread]+2] << 16; - address |= addr[cpu->pc[thread]+3] << 24; - cpu->pc[thread]+=4; - } else { - cpu->pc[thread]+=1; + switch (addrsize) { + case 3: + address |= addr[cpu->pc[thread]+1] << 8; + address |= addr[cpu->pc[thread]+2] << 16; + address |= addr[cpu->pc[thread]+3] << 24; + cpu->pc[thread]+=4; + break; + case 2: + address |= addr[cpu->pc[thread]+1] << 8; + address |= addr[cpu->pc[thread]+2] << 16; + address |= addr[cpu->pc[thread]+3] << 24; + address |= (uint64_t)addr[cpu->pc[thread]+4] << 32; + address |= (uint64_t)addr[cpu->pc[thread]+5] << 40; + cpu->pc[thread]+=6; + break; + case 1: + address |= addr[cpu->pc[thread]+1] << 8; + address |= addr[cpu->pc[thread]+2] << 16; + cpu->pc[thread]+=3; + break; + case 0: + cpu->pc[thread]+=1; + break; } tmpaddr = address; switch (optype[opcode]) { @@ -211,13 +240,29 @@ void *run(void *args) { case INDX: case INDY: address = addr[cpu->pc[thread]]; - if (addrsize) { - address |= addr[cpu->pc[thread]+1] << 8; - address |= addr[cpu->pc[thread]+2] << 16; - address |= addr[cpu->pc[thread]+3] << 24; - cpu->pc[thread]+=4; - } else { - cpu->pc[thread]+=1; + switch (addrsize) { + case 3: + address |= addr[cpu->pc[thread]+1] << 8; + address |= addr[cpu->pc[thread]+2] << 16; + address |= addr[cpu->pc[thread]+3] << 24; + cpu->pc[thread]+=4; + break; + case 2: + address |= addr[cpu->pc[thread]+1] << 8; + address |= addr[cpu->pc[thread]+2] << 16; + address |= addr[cpu->pc[thread]+3] << 24; + address |= (uint64_t)addr[cpu->pc[thread]+4] << 32; + address |= (uint64_t)addr[cpu->pc[thread]+5] << 40; + cpu->pc[thread]+=6; + break; + case 1: + address |= addr[cpu->pc[thread]+1] << 8; + address |= addr[cpu->pc[thread]+2] << 16; + cpu->pc[thread]+=3; + break; + case 0: + cpu->pc[thread]+=1; + break; } iclk++; tmpaddr = address; @@ -245,36 +290,51 @@ void *run(void *args) { case ABS: address = addr[cpu->pc[thread]]; address |= addr[cpu->pc[thread]+1] << 8; - if (addrsize) { - address |= addr[cpu->pc[thread]+2] << 16; - address |= addr[cpu->pc[thread]+3] << 24; - address |= (uint64_t)addr[cpu->pc[thread]+4] << 32; - address |= (uint64_t)addr[cpu->pc[thread]+5] << 40; - address |= (uint64_t)addr[cpu->pc[thread]+6] << 48; - address |= (uint64_t)addr[cpu->pc[thread]+7] << 56; - cpu->pc[thread]+=8; - iclk++; - } else { - cpu->pc[thread]+=2; + switch (addrsize) { + case 3: + address |= addr[cpu->pc[thread]+2] << 16; + address |= addr[cpu->pc[thread]+3] << 24; + address |= (uint64_t)addr[cpu->pc[thread]+4] << 32; + address |= (uint64_t)addr[cpu->pc[thread]+5] << 40; + address |= (uint64_t)addr[cpu->pc[thread]+6] << 48; + address |= (uint64_t)addr[cpu->pc[thread]+7] << 56; + cpu->pc[thread]+=8; + iclk++; + break; + case 2: + address |= addr[cpu->pc[thread]+2] << 16; + address |= addr[cpu->pc[thread]+3] << 24; + address |= (uint64_t)addr[cpu->pc[thread]+4] << 32; + address |= (uint64_t)addr[cpu->pc[thread]+5] << 40; + address |= (uint64_t)addr[cpu->pc[thread]+6] << 48; + cpu->pc[thread]+=7; + iclk++; + break; + case 1: + address |= addr[cpu->pc[thread]+2] << 16; + address |= addr[cpu->pc[thread]+3] << 24; + address |= (uint64_t)addr[cpu->pc[thread]+4] << 32; + cpu->pc[thread]+=5; + break; + case 0: + cpu->pc[thread]+=2; + break; } - iclk++; break; } value = addr[address]; - if (regsize >= 2) { - value |= addr[address+1] << 8; - if (regsize >= 4) { - value |= addr[address+2] << 16; + switch (regsize) { + case 8: + value |= (uint64_t)addr[address+7] << 56; + value |= (uint64_t)addr[address+6] << 48; + value |= (uint64_t)addr[address+5] << 40; + value |= (uint64_t)addr[address+4] << 32; + case 4: value |= addr[address+3] << 24; - - if (regsize >= 8) { - value |= (uint64_t)addr[address+4] << 32; - value |= (uint64_t)addr[address+5] << 40; - value |= (uint64_t)addr[address+6] << 48; - value |= (uint64_t)addr[address+7] << 56; - } - } + value |= addr[address+2] << 16; + case 2: + value |= addr[address+1] << 8; } #if debug && !bench int row, col; @@ -324,21 +384,56 @@ void *run(void *args) { tmpaddr = address - cpu->x[thread]; else if (optype[opcode] == ZMY) tmpaddr = address - cpu->y[thread]; - if (addrsize) - mvwprintw(scr, lines, col, "%s%s $%08x%s \r" , op, postfix, tmpaddr, (optype[opcode] == ZM) ? "" : ((optype[opcode] == ZMX) ? ", x" : ", y")); - else - mvwprintw(scr, lines, col, "%s%s $%02x%s \r" , op, postfix, tmpaddr, (optype[opcode] == ZM) ? "" : ((optype[opcode] == ZMX) ? ", x" : ", y")); + switch (addrsize) { + case 3: + mvwprintw(scr, lines, col, "%s%s $%08x%s \r" , op, postfix, tmpaddr, (optype[opcode] == ZM) ? "" : ((optype[opcode] == ZMX) ? ", x" : ", y")); + break; + case 2: + mvwprintw(scr, lines, col, "%s%s $%014llx%s \r" , op, postfix, tmpaddr, (optype[opcode] == ZM) ? "" : ((optype[opcode] == ZMX) ? ", x" : ", y")); + break; + case 1: + mvwprintw(scr, lines, col, "%s%s $%06x%s \r" , op, postfix, tmpaddr, (optype[opcode] == ZM) ? "" : ((optype[opcode] == ZMX) ? ", x" : ", y")); + break; + case 0: + mvwprintw(scr, lines, col, "%s%s $%02x%s \r" , op, postfix, tmpaddr, (optype[opcode] == ZM) ? "" : ((optype[opcode] == ZMX) ? ", x" : ", y")); + break; + } break; case IND: case INDX: case INDY: - if (addrsize) - mvwprintw(scr, lines, col, "%s%s ($%08x%s \r" , op, postfix, tmpaddr, (optype[opcode] == IND) ? ")" : ((optype[opcode] == INDX) ? ", x)" : "), y")); - else - mvwprintw(scr, lines, col, "%s%s ($%02x%s \r" , op, postfix, tmpaddr, (optype[opcode] == IND) ? ")" : ((optype[opcode] == INDX) ? ", x)" : "), y")); + switch (addrsize) { + case 3: + mvwprintw(scr, lines, col, "%s%s ($%08x%s \r" , op, postfix, tmpaddr, (optype[opcode] == IND) ? "" : ((optype[opcode] == INDX) ? ", x" : ", y")); + break; + case 2: + mvwprintw(scr, lines, col, "%s%s ($%012llx%s \r" , op, postfix, tmpaddr, (optype[opcode] == IND) ? "" : ((optype[opcode] == INDX) ? ", x" : ", y")); + break; + case 1: + mvwprintw(scr, lines, col, "%s%s ($%06x%s \r" , op, postfix, tmpaddr, (optype[opcode] == IND) ? "" : ((optype[opcode] == INDX) ? ", x" : ", y")); + break; + case 0: + mvwprintw(scr, lines, col, "%s%s ($%02x%s \r" , op, postfix, tmpaddr, (optype[opcode] == IND) ? "" : ((optype[opcode] == INDX) ? ", x" : ", y")); + break; + } break; case ABS: tmpaddr = address; + switch (addrsize) { + case 3: + mvwprintw(scr, lines, col, "%s%s $%016x\r" , op, postfix, tmpaddr); + break; + case 2: + mvwprintw(scr, lines, col, "%s%s $%014llx \r" , op, postfix, tmpaddr); + break; + case 1: + mvwprintw(scr, lines, col, "%s%s $%010llx \r" , op, postfix, tmpaddr); + break; + case 0: + mvwprintw(scr, lines, col, "%s%s $%04x \r" , op, postfix, tmpaddr); + break; + } + break; if (addrsize) mvwprintw(scr, lines, col, "%s%s $%016llx\r" , op, postfix, value); else @@ -349,8 +444,8 @@ void *run(void *args) { mvwprintw(scr, 29, 0, "address: $%016llx, scr_row: %02u, scr_col: %02u, scr_str: %02u, scr_end: %02u\r", address, addr[0], addr[1], addr[0x4B], addr[0x4C]); mvwprintw(scr, 32, 0, "bitabl: %02x %02x %02x %02x %02x %02x %02x %02x " "%02x %02x %02x %02x %02x %02x %02x %02x\r" - , addr[0x3B], addr[0x3C], addr[0x3D], addr[0x3E], addr[0x3F], addr[0x40], addr[0x41], addr[0x42] - , addr[0x43], addr[0x44], addr[0x45], addr[0x46], addr[0x47], addr[0x48], addr[0x49], addr[0x4A]); + , addr[0x16], addr[0x17], addr[0x18], addr[0x19], addr[0x1A], addr[0x1B], addr[0x1C], addr[0x1D] + , addr[0x1E], addr[0x1F], addr[0x20], addr[0x21], addr[0x22], addr[0x23], addr[0x24], addr[0x25]); mvwprintw(scr, 33, 0, "buffer:\r"); uint8_t ln = 34; uint16_t tmpad = 0x2000; @@ -368,22 +463,34 @@ void *run(void *args) { , i); } - /*tmpad = 0x4000; + tmpad = 0x4000; mvwprintw(scr, ln++, 0, "cmd_buf:\r"); for (uint16_t i = 0; i < 20; i+=2) { mvwprintw(scr, ln++, 0, "%02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x " "%02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x, i: %02x\r" - , addr[tmpad+(0x00)+(i*0x10)], addr[tmpad+(0x01)+(i*0x10)], addr[tmpad+(0x02)+(i*0x10)], addr[tmpad+(0x03)+(i*0x10)] - , addr[tmpad+(0x04)+(i*0x10)], addr[tmpad+(0x05)+(i*0x10)], addr[tmpad+(0x06)+(i*0x10)], addr[tmpad+(0x07)+(i*0x10)] - , addr[tmpad+(0x08)+(i*0x10)], addr[tmpad+(0x09)+(i*0x10)], addr[tmpad+(0x0A)+(i*0x10)], addr[tmpad+(0x0B)+(i*0x10)] - , addr[tmpad+(0x0C)+(i*0x10)], addr[tmpad+(0x0D)+(i*0x10)], addr[tmpad+(0x0E)+(i*0x10)], addr[tmpad+(0x0F)+(i*0x10)] - , addr[tmpad+(0x10)+(i*0x10)], addr[tmpad+(0x11)+(i*0x10)], addr[tmpad+(0x12)+(i*0x10)], addr[tmpad+(0x13)+(i*0x10)] - , addr[tmpad+(0x14)+(i*0x10)], addr[tmpad+(0x15)+(i*0x10)], addr[tmpad+(0x16)+(i*0x10)], addr[tmpad+(0x17)+(i*0x10)] - , addr[tmpad+(0x18)+(i*0x10)], addr[tmpad+(0x19)+(i*0x10)], addr[tmpad+(0x1A)+(i*0x10)], addr[tmpad+(0x1B)+(i*0x10)] - , addr[tmpad+(0x1C)+(i*0x10)], addr[tmpad+(0x1D)+(i*0x10)], addr[tmpad+(0x1E)+(i*0x10)], addr[tmpad+(0x1F)+(i*0x10)] + , addr[0x4000+(0x00)+(i*0x10)], addr[0x4000+(0x01)+(i*0x10)], addr[0x4000+(0x02)+(i*0x10)], addr[0x4000+(0x03)+(i*0x10)] + , addr[0x4000+(0x04)+(i*0x10)], addr[0x4000+(0x05)+(i*0x10)], addr[0x4000+(0x06)+(i*0x10)], addr[0x4000+(0x07)+(i*0x10)] + , addr[0x4000+(0x08)+(i*0x10)], addr[0x4000+(0x09)+(i*0x10)], addr[0x4000+(0x0A)+(i*0x10)], addr[0x4000+(0x0B)+(i*0x10)] + , addr[0x4000+(0x0C)+(i*0x10)], addr[0x4000+(0x0D)+(i*0x10)], addr[0x4000+(0x0E)+(i*0x10)], addr[0x4000+(0x0F)+(i*0x10)] + , addr[0x4000+(0x10)+(i*0x10)], addr[0x4000+(0x11)+(i*0x10)], addr[0x4000+(0x12)+(i*0x10)], addr[0x4000+(0x13)+(i*0x10)] + , addr[0x4000+(0x14)+(i*0x10)], addr[0x4000+(0x15)+(i*0x10)], addr[0x4000+(0x16)+(i*0x10)], addr[0x4000+(0x17)+(i*0x10)] + , addr[0x4000+(0x18)+(i*0x10)], addr[0x4000+(0x19)+(i*0x10)], addr[0x4000+(0x1A)+(i*0x10)], addr[0x4000+(0x1B)+(i*0x10)] + , addr[0x4000+(0x1C)+(i*0x10)], addr[0x4000+(0x1D)+(i*0x10)], addr[0x4000+(0x1E)+(i*0x10)], addr[0x4000+(0x1F)+(i*0x10)] , i); - }*/ + } + mvwprintw(scr, ln++, 0, "ptr: $%02x%02x%02x%02x%02x%02x%02x%02x\r" + , addr[0x30], addr[0x2F], addr[0x2E], addr[0x2D], addr[0x2C], addr[0x2B], addr[0x2A], addr[0x29]); + mvwprintw(scr, ln++, 0, "ptr2: $%02x%02x%02x%02x%02x%02x%02x%02x\r" + , addr[0x38], addr[0x37], addr[0x36], addr[0x35], addr[0x34], addr[0x33], addr[0x32], addr[0x31]); + mvwprintw(scr, ln++, 0, "ptr3: $%02x%02x%02x%02x%02x%02x%02x%02x\r" + , addr[0x40], addr[0x3F], addr[0x3E], addr[0x3D], addr[0x3C], addr[0x3B], addr[0x3A], addr[0x39]); + mvwprintw(scr, ln++, 0, "ptr4: $%02x%02x%02x%02x%02x%02x%02x%02x\r" + , addr[0x48], addr[0x47], addr[0x46], addr[0x45], addr[0x44], addr[0x43], addr[0x42], addr[0x41]); + mvwprintw(scr, ln++, 0, "ptr5: $%02x%02x%02x%02x%02x%02x%02x%02x\r" + , addr[0x50], addr[0x4F], addr[0x4E], addr[0x4D], addr[0x4C], addr[0x4B], addr[0x4A], addr[0x49]); + mvwprintw(scr, ln++, 0, "ptr6: $%02x%02x%02x%02x%02x%02x%02x%02x\r" + , addr[0x58], addr[0x57], addr[0x56], addr[0x55], addr[0x54], addr[0x53], addr[0x52], addr[0x51]); wrefresh(scr); #if keypoll pthread_mutex_unlock(&mutex); @@ -404,8 +511,8 @@ void *run(void *args) { break; case ADC: /* ADC Immediate. */ case AAB: /* Add Accumulator with carry by B register. */ - case 0x03: /* ADC Absolute. */ - case 0x05: /* ADC Zero Matrix. */ + case ADC_AB: /* ADC Absolute. */ + case ADC_Z: /* ADC Zero Matrix. */ if (opcode == AAB) value = cpu->b[thread]; sum = cpu->a[thread]+value+cpu->c[thread]; @@ -440,12 +547,15 @@ void *run(void *args) { if (tmp > 7) tmp = 7; - for (int8_t i = tmp<<3; i >= 0; i-=8) { - if (i) - addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = reg >> i; - else - addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = reg & 0xFF; - cpu->sp[thread]--; + switch (tmp) { + case 7: addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]--] = reg >> (tmp--<<3); + case 6: addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]--] = reg >> (tmp--<<3); + case 5: addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]--] = reg >> (tmp--<<3); + case 4: addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]--] = reg >> (tmp--<<3); + case 3: addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]--] = reg >> (tmp--<<3); + case 2: addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]--] = reg >> (tmp--<<3); + case 1: addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]--] = reg >> (tmp--<<3); + case 0: addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]--] = reg & 0xFF; } break; case TAY: /* Transfer Accumulator to Y. */ @@ -491,7 +601,7 @@ void *run(void *args) { break; case TXS: cpu->sp[thread] = cpu->x[thread]; - if (prefix == 0x17 && (value == thread+1 || value > 8)) { + if (prefix == 0x13 && (value == thread+1 || value > 8)) { cpu->stk_st[thread] = value & 0xFF; cpu->stk_st[thread] += value << 16; cpu->pc[thread]+=2; @@ -520,12 +630,14 @@ void *run(void *args) { setflag(cpu->n[thread], N); break; case JMP: /* JMP Absolute. */ + case JMP_Z: /* JMP Zero Matrix. */ + case JMP_IN: /* JMP Indirect. */ cpu->pc[thread] = address; break; case SBC: /* SBC Immediate. */ case SAB: /* Subtract Accumulator with carry by B register. */ - case 0x13: /* SBC Absolute. */ - case 0x15: /* SBC Zero Matrix. */ + case SBC_AB: /* SBC Absolute. */ + case SBC_Z: /* SBC Zero Matrix. */ if (opcode == SAB) { value = cpu->b[thread]; } @@ -559,12 +671,16 @@ void *run(void *args) { if (tmp > 7) tmp = 7; - for (uint8_t i = 0; i < (tmp+1)<<3; i+=8) { - cpu->sp[thread]++; - if (i) - reg += addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << i; - else - reg = addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] & 0xFF; + tmp2 = 0; + cpu->sp[thread]++;reg = addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] & 0xFF;tmp2+=8;tmp--; + switch (tmp) { + case 6: cpu->sp[thread]++;reg += addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << tmp2;tmp2+=8; + case 5: cpu->sp[thread]++;reg += addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << tmp2;tmp2+=8; + case 4: cpu->sp[thread]++;reg += addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << tmp2;tmp2+=8; + case 3: cpu->sp[thread]++;reg += addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << tmp2;tmp2+=8; + case 2: cpu->sp[thread]++;reg += addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << tmp2;tmp2+=8; + case 1: cpu->sp[thread]++;reg += addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << tmp2;tmp2+=8; + case 0: cpu->sp[thread]++;reg += addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << tmp2;tmp2+=8; } if (opcode == PLB) { cpu->b[thread] = reg; @@ -578,27 +694,37 @@ void *run(void *args) { cpu->x[thread] = reg; } break; - case 0x34: /* JSR Indirect. */ - case 0x44: /* JSR Indexed Indirect. */ - case 0x54: /* JSR Indirect Indexed. */ + case JSR_IN: /* JSR Indirect. */ case JSR: /* Jump to SubRoutine. */ - if (addrsize) + /*if (addrsize) stksize = 24; else - stksize = 0; - for (int8_t i = stksize; i >= 0; i-=8) { + stksize = 0;*/ + switch (addrsize) { + case 2: + addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = (uint64_t)cpu->pc[thread] >> 40;cpu->sp[thread]--; + addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = (uint64_t)cpu->pc[thread] >> 32;cpu->sp[thread]--; + case 3: + addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = (uint64_t)cpu->pc[thread] >> 24;cpu->sp[thread]--; + case 1: + addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = (uint64_t)cpu->pc[thread] >> 16;cpu->sp[thread]--; + addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = (uint64_t)cpu->pc[thread] >> 8;cpu->sp[thread]--; + case 0: + addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = (uint64_t)cpu->pc[thread] & 0xFF;cpu->sp[thread]--; + } + /*for (int8_t i = stksize; i >= 0; i-=8) { if (i) addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = (uint64_t)cpu->pc[thread] >> i; else addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = (uint64_t)cpu->pc[thread] & 0xFF; cpu->sp[thread]--; - } + }*/ cpu->pc[thread] = address; break; case AND: /* AND Immediate. */ case ABA: /* bitwise And with Accumulator, and B register. */ - case 0x23: /* AND Absolute. */ - case 0x25: /* AND Zero Matrix. */ + case AND_AB: /* AND Absolute. */ + case AND_Z: /* AND Zero Matrix. */ if (opcode == ABA) { value = cpu->b[thread]; } @@ -625,14 +751,14 @@ void *run(void *args) { } break; case BPO: /* BPO Absolute. */ - case 0x64: /* BPO Zero Matrix. */ + case BPO_Z: /* BPO Zero Matrix. */ if (!cpu->n[thread]) cpu->pc[thread] = address; break; case ORA: /* ORA Immediate. */ case OAB: /* bitwise Or with Accumulator, and B register. */ - case 0x33: /* ORA Absolute. */ - case 0x35: /* ORA Zero Matrix. */ + case ORA_AB: /* ORA Absolute. */ + case ORA_Z: /* ORA Zero Matrix. */ if (opcode == OAB) { value = cpu->b[thread]; } @@ -647,14 +773,14 @@ void *run(void *args) { setflag(cpu->i[thread], I); break; case BNG: /* BNG Absolute. */ - case 0x74: /* BNG Zero Matrix. */ + case BNG_Z: /* BNG Zero Matrix. */ if (cpu->n[thread]) cpu->pc[thread] = address; break; case XOR: /* XOR Immediate. */ case XAB: /* bitwise Xor with Accumulator, and B register. */ - case 0x43: /* XOR Absolute. */ - case 0x45: /* XOR Zero Matrix. */ + case XOR_AB: /* XOR Absolute. */ + case XOR_Z: /* XOR Zero Matrix. */ if (opcode == XAB) { value = cpu->b[thread]; } @@ -669,14 +795,14 @@ void *run(void *args) { setflag(cpu->i[thread], I); break; case BCS: /* BCS Absolute. */ - case 0x84: /* BCS Zero Matrix. */ + case BCS_Z: /* BCS Zero Matrix. */ if (cpu->c[thread]) cpu->pc[thread] = address; break; case LSL: /* LSL Immediate. */ case LLB: /* Logical shift Left accumulator by B. */ - case 0x53: /* LSL Absolute. */ - case 0x55: /* LSL Zero Matrix. */ + case LSL_AB: /* LSL Absolute. */ + case LSL_Z: /* LSL Zero Matrix. */ if (opcode == LLB) { value = cpu->b[thread]; } @@ -697,58 +823,55 @@ void *run(void *args) { case STY: /* STY Absolute. */ case STX: /* STX Absolute. */ case STB: /* STB Absolute. */ - case 0x49: /* STA Zero Matrix. */ - case 0x4A: /* STY Zero Matrix. */ - case 0x4B: /* STX Zero Matrix. */ - case 0x4E: /* STB Zero Matrix. */ - case 0x69: /* STA Zero Matrix, Indexed with X. */ - case 0x6A: /* STY Zero Matrix, Indexed with X. */ - case 0x6B: /* STX Zero Matrix, Indexed with Y. */ - case 0x6E: /* STB Zero Matrix, Indexed with X. */ - case 0x89: /* STA Zero Matrix, Indexed with Y. */ - case 0x8A: /* STY Indirect. */ - case 0x8B: /* STX Indirect. */ - case 0x8E: /* STB Zero Matrix, Indexed with Y. */ - case 0xA9: /* STA Indirect. */ - case 0xAA: /* STY Indexed Indirect. */ - case 0xAB: /* STX Indirect Indexed. */ - case 0xAE: /* STB Indirect. */ - case 0xC9: /* STA Indexed Indirect. */ - case 0xCE: /* STB Indexed Indirect. */ - case 0xE9: /* STA Indirect Indexed. */ - case 0xEE: /* STB Indirect Indexed. */ + case STA_Z: /* STA Zero Matrix. */ + case STY_Z: /* STY Zero Matrix. */ + case STX_Z: /* STX Zero Matrix. */ + case STB_Z: /* STB Zero Matrix. */ + case STA_ZX: /* STA Zero Matrix, Indexed with X. */ + case STY_ZX: /* STY Zero Matrix, Indexed with X. */ + case STX_ZY: /* STX Zero Matrix, Indexed with Y. */ + case STB_ZX: /* STB Zero Matrix, Indexed with X. */ + case STA_ZY: /* STA Zero Matrix, Indexed with Y. */ + case STB_ZY: /* STB Zero Matrix, Indexed with Y. */ + case STY_IN: /* STY Indirect. */ + case STX_IN: /* STX Indirect. */ + case STA_IN: /* STA Indirect. */ + case STB_IN: /* STB Indirect. */ + case STA_IX: /* STA Indexed Indirect. */ + case STB_IX: /* STB Indexed Indirect. */ + case STA_IY: /* STA Indirect Indexed. */ + case STB_IY: /* STB Indirect Indexed. */ + switch (opcode) { case STB: - case 0x4E: - case 0x6E: - case 0x8E: - case 0xAE: - case 0xCE: - case 0xEE: + case STB_Z: + case STB_ZX: + case STB_ZY: + case STB_IN: + case STB_IX: + case STB_IY: value = cpu->b[thread]; break; case STA: - case 0x49: - case 0x69: - case 0x89: - case 0xA9: - case 0xC9: - case 0xE9: + case STA_Z: + case STA_ZX: + case STA_ZY: + case STA_IN: + case STA_IX: + case STA_IY: value = cpu->a[thread]; break; case STY: - case 0x4A: - case 0x6A: - case 0x8A: - case 0xAA: + case STY_Z: + case STY_ZX: + case STY_IN: value = cpu->y[thread]; break; case STX: - case 0x4B: - case 0x6B: - case 0x8B: - case 0xAB: + case STX_Z: + case STX_ZY: + case STX_IN: value = cpu->x[thread]; break; } @@ -956,14 +1079,14 @@ void *run(void *args) { } break; case BCC: /* BCC Absolute. */ - case 0x94: /* BCC Zero Matrix. */ + case BCC_Z: /* BCC Zero Matrix. */ if (!cpu->c[thread]) cpu->pc[thread] = address; break; case LSR: /* LSR Immediate. */ case LRB: /* Logical shift Right accumulator by B. */ - case 0x63: /* LSR Absolute. */ - case 0x65: /* LSR Zero Matrix. */ + case LSR_AB: /* LSR Absolute. */ + case LSR_Z: /* LSR Zero Matrix. */ if (opcode == LRB) { value = cpu->b[thread]; } @@ -978,8 +1101,8 @@ void *run(void *args) { break; case ASR: /* ASR Immediate. */ case ARB: /* Arithmetic shift Right accumulator by B. */ - case 0xE3: /* ASR Absolute. */ - case 0xE5: /* ASR Zero Matrix. */ + case ASR_AB: /* ASR Absolute. */ + case ASR_Z: /* ASR Zero Matrix. */ if (opcode == ARB) value = cpu->b[thread]; sign = cpu->a[thread] & 0x8000000000000000; @@ -1000,30 +1123,28 @@ void *run(void *args) { case LDA: /* LDA Immediate. */ case LDY: /* LDY Immediate. */ case LDX: /* LDX Immediate. */ - case 0x1E: /* LDB Absolute. */ - case 0x19: /* LDA Absolute. */ - case 0x1A: /* LDY Absolute. */ - case 0x1B: /* LDX Absolute. */ - case 0x3E: /* LDB Zero Matrix. */ - case 0x39: /* LDA Zero Matrix. */ - case 0x3A: /* LDY Zero Matrix. */ - case 0x3B: /* LDX Zero Matrix. */ - case 0x5E: /* LDB Zero Matrix, Indexed with X. */ - case 0x59: /* LDA Zero Matrix, Indexed with X. */ - case 0x5A: /* LDY Zero Matrix, Indexed with X. */ - case 0x5B: /* LDX Zero Matrix, Indexed with Y. */ - case 0x7E: /* LDB Zero Matrix, Indexed with Y. */ - case 0x79: /* LDA Zero Matrix, Indexed with Y. */ - case 0x7A: /* LDY Indirect. */ - case 0x7B: /* LDX Indirect. */ - case 0x9E: /* LDB Indirect. */ - case 0x99: /* LDA Indirect. */ - case 0x9A: /* LDY Indexed Indirect. */ - case 0x9B: /* LDX Indirect Indexed. */ - case 0xBE: /* LDB Indexed Indirect. */ - case 0xB9: /* LDA Indexed Indirect. */ - case 0xDE: /* LDB Indirect Indexed. */ - case 0xD9: /* LDA Indirect Indexed. */ + case LDB_AB: /* LDB Absolute. */ + case LDA_AB: /* LDA Absolute. */ + case LDY_AB: /* LDY Absolute. */ + case LDX_AB: /* LDX Absolute. */ + case LDB_Z: /* LDB Zero Matrix. */ + case LDA_Z: /* LDA Zero Matrix. */ + case LDY_Z: /* LDY Zero Matrix. */ + case LDX_Z: /* LDX Zero Matrix. */ + case LDB_ZX: /* LDB Zero Matrix, Indexed with X. */ + case LDA_ZX: /* LDA Zero Matrix, Indexed with X. */ + case LDY_ZX: /* LDY Zero Matrix, Indexed with X. */ + case LDX_ZY: /* LDX Zero Matrix, Indexed with Y. */ + case LDB_ZY: /* LDB Zero Matrix, Indexed with Y. */ + case LDA_ZY: /* LDA Zero Matrix, Indexed with Y. */ + case LDB_IN: /* LDY Indirect. */ + case LDA_IN: /* LDX Indirect. */ + case LDY_IN: /* LDB Indirect. */ + case LDX_IN: /* LDA Indirect. */ + case LDB_IX: /* LDB Indexed Indirect. */ + case LDA_IX: /* LDA Indexed Indirect. */ + case LDB_IY: /* LDB Indirect Indexed. */ + case LDA_IY: /* LDA Indirect Indexed. */ if (address == CTRL_ADDR) { kbd_rdy = 1; pthread_mutex_lock(&main_mutex); @@ -1037,55 +1158,52 @@ void *run(void *args) { kbd_rdy = 0; } value = addr[address]; - if (regsize >= 2) { - value += addr[address+1] << 8; - if (regsize >= 4) { - value += addr[address+2] << 16; - value += addr[address+3] << 24; - if (regsize >= 8) { - value += (uint64_t)addr[address+4] << 32; - value += (uint64_t)addr[address+5] << 40; - value += (uint64_t)addr[address+6] << 48; - value += (uint64_t)addr[address+7] << 56; - } - } + switch (regsize) { + case 8: + value |= (uint64_t)addr[address+7] << 56; + value |= (uint64_t)addr[address+6] << 48; + value |= (uint64_t)addr[address+5] << 40; + value |= (uint64_t)addr[address+4] << 32; + case 4: + value |= addr[address+3] << 24; + value |= addr[address+2] << 16; + case 2: + value |= addr[address+1] << 8; } switch (opcode) { case LDB: - case 0x1E: - case 0x3E: - case 0x5E: - case 0x7E: - case 0x9E: - case 0xBE: - case 0xDE: + case LDB_AB: + case LDB_Z: + case LDB_ZX: + case LDB_ZY: + case LDB_IN: + case LDB_IX: + case LDB_IY: cpu->b[thread] = value; break; case LDA: - case 0x19: - case 0x39: - case 0x59: - case 0x79: - case 0x99: - case 0xB9: - case 0xD9: + case LDA_AB: + case LDA_Z: + case LDA_ZX: + case LDA_ZY: + case LDA_IN: + case LDA_IX: + case LDA_IY: cpu->a[thread] = value; break; case LDY: - case 0x1A: - case 0x3A: - case 0x5A: - case 0x7A: - case 0x9A: + case LDY_AB: + case LDY_Z: + case LDY_ZX: + case LDY_IN: cpu->y[thread] = value; break; case LDX: - case 0x1B: - case 0x3B: - case 0x5B: - case 0x7B: - case 0x9B: + case LDX_AB: + case LDX_Z: + case LDX_ZY: + case LDX_IN: cpu->x[thread] = value; break; } @@ -1095,14 +1213,14 @@ void *run(void *args) { setflag(cpu->n[thread], N); break; case BEQ: /* BEQ Absolute. */ - case 0xA4: /* BEQ Zero Matrix. */ + case BEQ_Z: /* BEQ Zero Matrix. */ if (cpu->z[thread]) cpu->pc[thread] = address; break; case ROL: /* ROL Immediate. */ case RLB: /* Rotate Left accumulator by B. */ - case 0x73: /* ROL Absolute. */ - case 0x75: /* ROL Zero Matrix. */ + case ROL_AB: /* ROL Absolute. */ + case ROL_Z: /* ROL Zero Matrix. */ if (opcode == RLB) { value = cpu->b[thread]; } @@ -1116,19 +1234,15 @@ void *run(void *args) { setflag(cpu->n[thread], N); setflag(cpu->c[thread], C); break; - case SSP: /* Set Stack Protection flag. */ - cpu->s[thread] = 1; - setflag(cpu->s[thread], S); - break; case BNE: /* BNE Absolute. */ - case 0xB4: /* BNE Zero Matrix. */ + case BNE_Z: /* BNE Zero Matrix. */ if (!cpu->z[thread]) cpu->pc[thread] = address; break; case ROR: /* ROR Immediate. */ case RRB: /* Rotate Right accumulator by B. */ - case 0x83: /* ROR Absolute. */ - case 0x85: /* ROR Zero Matrix. */ + case ROR_AB: /* ROR Absolute. */ + case ROR_Z: /* ROR Zero Matrix. */ if (opcode == RRB) { value = cpu->b[thread]; } @@ -1142,19 +1256,15 @@ void *run(void *args) { setflag(cpu->n[thread], N); setflag(cpu->c[thread], C); break; - case CSP: /* Clear Stack Protection flag. */ - cpu->s[thread] = 0; - setflag(cpu->s[thread], S); - break; case BVS: /* BVS Absolute. */ - case 0xC4: /* BVS Zero Matrix. */ + case BVS_Z: /* BVS Zero Matrix. */ if (cpu->v[thread]) cpu->pc[thread] = address; break; case MUL: /* MUL Immediate. */ case MAB: /* Multiply Accumulator by B. */ - case 0x93: /* MUL Absolute. */ - case 0x95: /* MUL Zero Matrix. */ + case MUL_AB: /* MUL Absolute. */ + case MUL_Z: /* MUL Zero Matrix. */ if (opcode == MAB) { value = cpu->b[thread]; } @@ -1169,19 +1279,15 @@ void *run(void *args) { setflag(cpu->v[thread], V); setflag(cpu->c[thread], C); break; - case SEV: /* SEt oVerflow flag. */ - cpu->v[thread] = 1; - setflag(cpu->v[thread], V); - break; case BVC: /* BVC Absolute. */ - case 0xD4: /* BVC Zero Matrix. */ + case BVC_Z: /* BVC Zero Matrix. */ if (!cpu->v[thread]) cpu->pc[thread] = address; break; case DIV: /* DIV Immediate. */ case DAB: /* Divide Accumulator by B. */ - case 0xA3: /* DIV Absolute. */ - case 0xA5: /* DIV Zero Matrix. */ + case DIV_AB: /* DIV Absolute. */ + case DIV_Z: /* DIV Zero Matrix. */ if (opcode != DAB) { cpu->b[thread] = cpu->a[thread] % value; } else { @@ -1200,16 +1306,20 @@ void *run(void *args) { setflag(cpu->v[thread], V); break; case RTS: /* ReTurn from Subroutine. */ - if (addrsize) + /*if (addrsize) stksize = 32; else - stksize = 8; - for (uint8_t i = 0; i < stksize; i+=8) { - cpu->sp[thread]++; - if (i) - cpu->pc[thread] += addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << i; - else - cpu->pc[thread] = addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]]; + stksize = 8;*/ + cpu->sp[thread]++;cpu->pc[thread] = addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]]; + switch (addrsize) { + case 1: + cpu->sp[thread]++;cpu->pc[thread] += (uint64_t)addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << 8; + cpu->sp[thread]++;cpu->pc[thread] += (uint64_t)addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << 16; + case 3: + cpu->sp[thread]++;cpu->pc[thread] += (uint64_t)addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << 24; + case 2: + cpu->sp[thread]++;cpu->pc[thread] += (uint64_t)addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << 32; + cpu->sp[thread]++;cpu->pc[thread] += (uint64_t)addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << 40; } break; case CPB: /* CPB Immediate. */ @@ -1217,58 +1327,54 @@ void *run(void *args) { case CAB: /* Compare Accumulator, and B. */ case CPY: /* CPY Immediate. */ case CPX: /* CPX Immediate. */ - case 0xCA: /* CPY Absolute. */ - case 0xCB: /* CPX Absolute. */ - case 0xB3: /* CMP Absolute. */ - case 0x36: /* CPB Absolute. */ - case 0xDA: /* CPY Zero Matrix. */ - case 0xDB: /* CPX Zero Matrix. */ - case 0xB5: /* CMP Zero Matrix. */ - case 0x46: /* CPB Zero Matrix. */ - case 0xF1: /* CMP Indirect. */ - case 0xEA: /* CPY Indirect. */ - case 0xEB: /* CPX Indirect. */ - case 0x56: /* CPB Indirect. */ - case 0xF3: /* CMP Indexed Indirect. */ - case 0xFA: /* CPY Indexed Indirect. */ - case 0x66: /* CPB Indexed Indirect. */ - case 0xF5: /* CMP Indirect Indexed. */ - case 0xFB: /* CPX Indirect Indexed. */ - case 0x76: /* CPB Indirect Indexed. */ + case CPY_AB: /* CPY Absolute. */ + case CPX_AB: /* CPX Absolute. */ + case CMP_AB: /* CMP Absolute. */ + case CPB_AB: /* CPB Absolute. */ + case CPY_Z: /* CPY Zero Matrix. */ + case CPX_Z: /* CPX Zero Matrix. */ + case CMP_Z: /* CMP Zero Matrix. */ + case CPB_Z: /* CPB Zero Matrix. */ + case CPY_IN: /* CMP Indirect. */ + case CPX_IN: /* CPY Indirect. */ + case CMP_IN: /* CPX Indirect. */ + case CPB_IN: /* CPB Indirect. */ + case CMP_IX: /* CMP Indexed Indirect. */ + case CPB_IX: /* CPB Indexed Indirect. */ + case CMP_IY: /* CMP Indirect Indexed. */ + case CPB_IY: /* CPB Indirect Indexed. */ if (opcode == CAB) { value = cpu->b[thread]; } switch (opcode) { case CPB: - case 0x36: - case 0x46: - case 0x56: - case 0x66: - case 0x76: + case CPB_AB: + case CPB_Z: + case CPB_IN: + case CPB_IX: + case CPB_IY: reg = cpu->b[thread]; break; case CMP: case CAB: - case 0xB3: - case 0xB5: - case 0xF1: - case 0xF3: - case 0xF5: + case CMP_AB: + case CMP_Z: + case CMP_IN: + case CMP_IX: + case CMP_IY: reg = cpu->a[thread]; break; case CPY: - case 0xCA: - case 0xDA: - case 0xEA: - case 0xFA: + case CPY_AB: + case CPY_Z: + case CPY_IN: reg = cpu->y[thread]; break; - case LDX: - case 0xCB: - case 0xDB: - case 0xEB: - case 0xFB: + case CPX: + case CPX_AB: + case CPX_Z: + case CPX_IN: reg = cpu->x[thread]; break; } @@ -1300,76 +1406,82 @@ void *run(void *args) { } break; case INC: /* INC Accumulator. */ - case IAB: + case INB: case INY: case INX: - if (opcode == INC || opcode == IAB) { - cpu->a[thread]+=1; - if (opcode == IAB) + switch (opcode) { + case INC: + cpu->a[thread]+=1; + cpu->z[thread] = (cpu->a[thread] == 0); + cpu->n[thread] = (cpu->a[thread] >> 63); + break; + case INB: cpu->b[thread]+=1; - cpu->z[thread] = (cpu->a[thread] == 0); - cpu->n[thread] = (cpu->a[thread] >> 63); - } - else if (opcode == INY) { - cpu->y[thread]+=1; - cpu->z[thread] = (cpu->y[thread] == 0); - cpu->n[thread] = (cpu->y[thread] >> 63); - } - else if (opcode == INX) { - cpu->x[thread]+=1; - cpu->z[thread] = (cpu->x[thread] == 0); - cpu->n[thread] = (cpu->x[thread] >> 63); + cpu->z[thread] = (cpu->b[thread] == 0); + cpu->n[thread] = (cpu->b[thread] >> 63); + break; + case INY: + cpu->y[thread]+=1; + cpu->z[thread] = (cpu->y[thread] == 0); + cpu->n[thread] = (cpu->y[thread] >> 63); + break; + case INX: + cpu->x[thread]+=1; + cpu->z[thread] = (cpu->x[thread] == 0); + cpu->n[thread] = (cpu->x[thread] >> 63); + break; } setflag(cpu->z[thread], Z); setflag(cpu->n[thread], N); break; - case 0x04: /* JMP Indirect. */ - case 0x14: /* JMP Indexed Indirect. */ - case 0x24: /* JMP Indirect Indexed. */ - case 0xD0: /* JMP Zero Matrix. */ - cpu->pc[thread] = address; - break; - case DEC: /* DEC Accumulator. */ - case DBA: + case DEB: case DEY: case DEX: - if (opcode == DEC || opcode == DBA) { - cpu->a[thread]-=1; - if (opcode == DBA) + switch (opcode) { + case DEC: + cpu->a[thread]-=1; + cpu->z[thread] = (cpu->a[thread] == 0); + cpu->n[thread] = (cpu->a[thread] >> 63); + break; + case DEB: cpu->b[thread]-=1; - cpu->z[thread] = (cpu->a[thread] == 0); - cpu->n[thread] = (cpu->a[thread] >> 63); - } - else if (opcode == DEY) { - cpu->y[thread]-=1; - cpu->z[thread] = (cpu->y[thread] == 0); - cpu->n[thread] = (cpu->y[thread] >> 63); - } - else if (opcode == DEX) { - cpu->x[thread]-=1; - cpu->z[thread] = (cpu->x[thread] == 0); - cpu->n[thread] = (cpu->x[thread] >> 63); + cpu->z[thread] = (cpu->b[thread] == 0); + cpu->n[thread] = (cpu->b[thread] >> 63); + break; + case DEY: + cpu->y[thread]-=1; + cpu->z[thread] = (cpu->y[thread] == 0); + cpu->n[thread] = (cpu->y[thread] >> 63); + break; + case DEX: + cpu->x[thread]-=1; + cpu->z[thread] = (cpu->x[thread] == 0); + cpu->n[thread] = (cpu->x[thread] >> 63); + break; } setflag(cpu->z[thread], Z); setflag(cpu->n[thread], N); break; case JSL: /* Jump to Subroutine Long. */ - if (addrsize) - stksize = 56; - else - stksize = 8; - for (int8_t i = stksize; i >= 0; i-=8) { - if (i) - addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = (uint64_t)cpu->pc[thread] >> i; - else - addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = (uint64_t)cpu->pc[thread] & 0xFF; - cpu->sp[thread]--; + switch (addrsize) { + case 3: + addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = (uint64_t)cpu->pc[thread] >> 56;cpu->sp[thread]--; + case 2: + addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = (uint64_t)cpu->pc[thread] >> 48;cpu->sp[thread]--; + addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = (uint64_t)cpu->pc[thread] >> 40;cpu->sp[thread]--; + case 1: + addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = (uint64_t)cpu->pc[thread] >> 32;cpu->sp[thread]--; + addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = (uint64_t)cpu->pc[thread] >> 24;cpu->sp[thread]--; + addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = (uint64_t)cpu->pc[thread] >> 16;cpu->sp[thread]--; + case 0: + addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = (uint64_t)cpu->pc[thread] >> 8;cpu->sp[thread]--; + addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] = (uint64_t)cpu->pc[thread] & 0xFF;cpu->sp[thread]--; } cpu->pc[thread] = address; break; - case 0xC3: /* INC Absolute. */ - case 0xC5: /* INC Zero Matrix. */ + case INC_AB: /* INC Absolute. */ + case INC_Z: /* INC Zero Matrix. */ addr[address]++; cpu->z[thread] = (addr[address] == 0); cpu->n[thread] = (addr[address] >> 7); @@ -1379,20 +1491,29 @@ void *run(void *args) { case NOP: /* No OPeration. */ break; case RTL: /* ReTurn from subroutine Long. */ - if (addrsize) - stksize = 64; - else - stksize = 16; - for (uint8_t i = 0; i < stksize; i+=8) { + cpu->sp[thread]++;cpu->pc[thread] = addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]]; + cpu->sp[thread]++;cpu->pc[thread] += addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << 8; + switch (addrsize) { + case 1: + cpu->sp[thread]++;cpu->pc[thread] += (uint64_t)addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << 16; + cpu->sp[thread]++;cpu->pc[thread] += (uint64_t)addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << 24; + cpu->sp[thread]++;cpu->pc[thread] += (uint64_t)addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << 32; + case 2: + cpu->sp[thread]++;cpu->pc[thread] += (uint64_t)addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << 40; + cpu->sp[thread]++;cpu->pc[thread] += (uint64_t)addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << 48; + case 3: + cpu->sp[thread]++;cpu->pc[thread] += (uint64_t)addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << 56; + } + /*for (uint8_t i = 0; i < stksize; i+=8) { cpu->sp[thread]++; if (i) cpu->pc[thread] += addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]] << i; else cpu->pc[thread] = addr[(cpu->stk_st[thread] << 16)+cpu->sp[thread]]; - } + }*/ break; - case 0xD3: /* DEC Absolute. */ - case 0xD5: /* DEC Zero Matrix. */ + case DEC_AB: /* DEC Absolute. */ + case DEC_Z: /* DEC Zero Matrix. */ addr[address]--; cpu->z[thread] = (addr[address] == 0); cpu->n[thread] = (addr[address] >> 7); @@ -1445,6 +1566,7 @@ void *run(void *args) { kbd_ln = 0; else kbd_ln = 1; + /*if (kbd_ln) usleep(16666); usleep(500000);*/ diff --git a/test/subroutine.s b/test/subroutine.s new file mode 100644 index 0000000..03447fd --- /dev/null +++ b/test/subroutine.s @@ -0,0 +1,45 @@ +.org $2000 +buf: + +.org $0 +ptr: +.qword buf + +.org $8000 +reset: + cps + ldx.w #$FFFF + txs +start: + ldy #0 + ldb #0 + inb + stb $C010 + deb + jsl clr_buf + jmp start + +clr_buf: + lda #0 + cpy.w #$1FFF + bcs clr_buf_end + sta.q (ptr), y + tya + adc #8 + tay + tba + sta.q (ptr), y + tya + adc #8 + tay + tba + jmp clr_buf +clr_buf_end: + ldy.w #0 + rtl + + +.org $FFC0 +.qword reset +done + |