summaryrefslogtreecommitdiff
path: root/asmmon.c
diff options
context:
space:
mode:
Diffstat (limited to 'asmmon.c')
-rw-r--r--asmmon.c932
1 files changed, 615 insertions, 317 deletions
diff --git a/asmmon.c b/asmmon.c
index 7af4695..085d7ba 100644
--- a/asmmon.c
+++ b/asmmon.c
@@ -4,7 +4,6 @@
#define debug 1
-#define OPNUM 93
#define SETOP(num, _mne, _IMM, _ZM, _ZMX, _ZMY, _IND, _INX, _INY, _ABS, _IMPL) \
{opcodes[num].mnemonic[3] = '\0'; strncpy(opcodes[num].mnemonic, _mne, 3); \
opcodes[num].imm = _IMM; \
@@ -60,19 +59,6 @@ uint64_t use_label(const char *name, uint64_t adr) {
struct label *l = mklabel(name, 0, 0);
adr++;
if (l->def) {
- addr[adr] = l->adr & 0xFF;
- if (l->adr & 0xFF00)
- addr[adr+1] = l->adr >> 8;
- if (l->adr & 0xFF000000) {
- addr[adr+2] = l->adr >> 16;
- addr[adr+3] = l->adr >> 24;
- }
- if (l->adr & 0xFF00000000000000) {
- addr[adr+4] = l->adr >> 32;
- addr[adr+5] = l->adr >> 40;
- addr[adr+6] = l->adr >> 48;
- addr[adr+7] = l->adr >> 56;
- }
return l->adr;
} else {
printf("oof, label %s, does not exist, yet.\n", name);
@@ -124,102 +110,201 @@ void viewmem(uint64_t address) {
printf("\n");
}
}
+
+void usage() {
+ puts("SuBAsm for CISC-0.2");
+ puts("Commands:");
+ puts("\tviewmem, vm, v\t\tGet the contents of memory\n"
+ "\t\t\t\t(Displays 256 bytes of memory\n"
+ "\t\t\t\t starting from where the program counter\n"
+ "\t\t\t\t currently is).");
+ puts("\trelsv, rf, r\t\tResolve any currently unknown labels.");
+ puts("\tdisasm, dis,\n"
+ "\td [start-][end]\t\tDisassemble from starting address, to\n"
+ "\t\t\t\tending address.");
+ puts("\tinst, i [inst]\t\tGet a descriptions of that instruction.\n"
+ "\t\t\t\tIf no argument is specified, or the\n"
+ "\t\t\t\targument specified is \"all\", list all\n"
+ "\t\t\t\tinstructions, along with a description\n"
+ "\t\t\t\tfor each of them.");
+ puts("\tquit, q\t\t\tQuit the emulator.");
+ puts("\thelp, h\t\t\tDisplays this mesage.");
+}
+
+void instinfo(const char *inst) {
+ for(int i = 0; i < OPNUM; i++) {
+ if (!strcasecmp(inst, mne[i])) {
+ printf("%s\t%s\n", mne[i], instdesc[i]);
+ break;
+ } else if (!strcasecmp(inst, "all")) {
+ printf("%s\t%s\n", mne[i], instdesc[i]);
+ }
+ }
+}
+
+void disasm(uint8_t prefix, uint8_t opcode, uint64_t value) {
+ char postfix[3];
+ char op[4];
+ uint8_t addrsize = (prefix & 8) >> 3;
+ uint8_t rs = (prefix & 0x30) >> 4;
+ uint8_t regsize = (1 << rs);
+ op[0] = opname[opcode][0];
+ op[1] = opname[opcode][1];
+ op[2] = opname[opcode][2];
+ op[3] = '\0';
+ if (regsize == 1) {
+ postfix[0] = '\0';
+ postfix[1] = '\0';
+ postfix[2] = '\0';
+ } else {
+ postfix[0] = '.';
+ if (regsize == 2)
+ postfix[1] = 'W';
+ else if (regsize == 4)
+ postfix[1] = 'D';
+ else if (regsize == 8)
+ postfix[1] = 'Q';
+ else {
+ postfix[0] = '\0';
+ postfix[1] = '\0';
+ }
+ postfix[2] = '\0';
+ }
+ switch (optype[opcode]) {
+ case IMPL:
+ printf("%s\n" , opname[opcode]);
+ break;
+ case IMM:
+ if (regsize == 1)
+ printf("%s #$%02x\n" , op, value);
+ if (regsize == 2)
+ printf("%s%s #$%04x\n" , op, postfix, value);
+ if (regsize == 4)
+ printf("%s%s #$%08x\n" , op, postfix, value);
+ if (regsize == 8)
+ printf("%s%s #$%016llx\n" , op, postfix, value);
+ break;
+ case ZM:
+ case ZMX:
+ case ZMY:
+ if (addrsize)
+ printf("%s%s $%08x%s\n" , op, postfix, value, (optype[opcode] == ZM) ? "" : ((optype[opcode] == ZMX) ? ", x" : ", y"));
+ else
+ printf("%s%s $%02x%s\n" , op, postfix, value, (optype[opcode] == ZM) ? "" : ((optype[opcode] == ZMX) ? ", x" : ", y"));
+ break;
+ case IND:
+ case INDX:
+ case INDY:
+ if (addrsize)
+ printf("%s%s ($%08x%s\n" , op, postfix, value, (optype[opcode] == IND) ? ")" : ((optype[opcode] == INDX) ? ", x)" : "), y"));
+ else
+ printf("%s%s ($%02x%s\n" , op, postfix, value, (optype[opcode] == IND) ? ")" : ((optype[opcode] == INDX) ? ", x)" : "), y"));
+ break;
+ case ABS:
+ if (addrsize)
+ printf("%s%s $%016llx\n" , op, postfix, value);
+ else
+ printf("%s%s $%04x\n" , op, postfix, value);
+ break;
+
+ }
+}
+
int asmmon(const char *fn) {
- opent opcodes[OPNUM];
/* 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( 2, "AAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02);
- SETOP( 3, "PHB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06);
- SETOP( 4, "PHP", 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00);
- SETOP( 5, "PHA", 0x09, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00);
- SETOP( 6, "PHY", 0x0A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00);
- SETOP( 7, "TAY", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0B);
- SETOP( 8, "PHX", 0x0C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00);
- SETOP( 9, "TAX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0D);
- SETOP(10, "TYX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0E);
- SETOP(11, "JMP", 0x00, 0xD0, 0x00, 0x00, 0x04, 0x14, 0x24, 0x10, 0x00);
- SETOP(12, "SBC", 0x11, 0x15, 0x00, 0x00, 0x00, 0x00, 0x00, 0x13, 0x00);
- SETOP(13, "SAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x12);
- SETOP(14, "PLB", 0x16, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00);
- SETOP(15, "PLP", 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00);
- SETOP(16, "PLA", 0x19, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00);
- SETOP(17, "PLY", 0x1A, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00);
- SETOP(18, "TYA", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1B);
- SETOP(19, "PLX", 0x1C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00);
- SETOP(20, "TXA", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1D);
- SETOP(21, "TXY", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1E);
- SETOP(22, "JSR", 0x00, 0x20, 0x00, 0x00, 0x34, 0x44, 0x54, 0x00, 0x00);
- SETOP(23, "AND", 0x21, 0x25, 0x00, 0x00, 0x00, 0x00, 0x00, 0x23, 0x00);
- SETOP(24, "ABA", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x22);
- SETOP(25, "STT", 0x28, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00);
- SETOP(26, "TAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x26);
- SETOP(27, "TSX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x2E);
- SETOP(28, "BPO", 0x00, 0x64, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00);
- SETOP(29, "ORA", 0x31, 0x35, 0x00, 0x00, 0x00, 0x00, 0x00, 0x33, 0x00);
- SETOP(30, "OAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x32);
- SETOP(31, "TBA", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x36);
- SETOP(32, "SEI", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x38);
- SETOP(33, "TXS", 0x3E, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00);
- SETOP(34, "BNG", 0x00, 0x74, 0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x00);
- SETOP(35, "XOR", 0x41, 0x45, 0x00, 0x00, 0x00, 0x00, 0x00, 0x43, 0x00);
- SETOP(36, "XAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x42);
- SETOP(37, "CLI", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x48);
- SETOP(38, "BCS", 0x00, 0x84, 0x00, 0x00, 0x00, 0x00, 0x00, 0x50, 0x00);
- SETOP(39, "LSL", 0x51, 0x55, 0x00, 0x00, 0x00, 0x00, 0x00, 0x53, 0x00);
- SETOP(40, "LLB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x52);
- SETOP(41, "STB", 0x00, 0x7F, 0x8F, 0x9F, 0xAF, 0xBF, 0xCF, 0x5F, 0x00);
- SETOP(42, "SEC", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x58);
- SETOP(43, "STA", 0x00, 0x7B, 0x8B, 0x9B, 0xAB, 0xBB, 0xCB, 0x5B, 0x00);
- SETOP(44, "STY", 0x00, 0x7D, 0x8D, 0x00, 0xAD, 0xBD, 0x00, 0x5D, 0x00);
- SETOP(45, "STX", 0x00, 0x7E, 0x00, 0x9E, 0xAE, 0x00, 0xCE, 0x5E, 0x00);
- SETOP(46, "BCC", 0x00, 0x94, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00);
- SETOP(47, "LSR", 0x61, 0x65, 0x00, 0x00, 0x00, 0x00, 0x00, 0x63, 0x00);
- SETOP(48, "LRB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x62);
- SETOP(49, "LDB", 0x66, 0x76, 0x86, 0x96, 0xA6, 0xB6, 0xC6, 0x56, 0x00);
- SETOP(50, "CLC", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x68);
- SETOP(51, "LDA", 0x69, 0x79, 0x89, 0x99, 0xA9, 0xB9, 0xC9, 0x59, 0x00);
- SETOP(52, "LDY", 0x6A, 0x7A, 0x8A, 0x00, 0xAA, 0xBA, 0x00, 0x5A, 0x00);
- SETOP(53, "LDX", 0x6C, 0x7C, 0x00, 0x9C, 0xAC, 0x00, 0xCC, 0x5C, 0x00);
- SETOP(54, "BEQ", 0x00, 0x46, 0x00, 0x00, 0x00, 0x00, 0x00, 0x70, 0x00);
- SETOP(55, "ROL", 0x71, 0x75, 0x00, 0x00, 0x00, 0x00, 0x00, 0x73, 0x00);
- SETOP(56, "RLB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x72);
- SETOP(57, "SSP", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x78);
- SETOP(58, "BNE", 0x00, 0x0F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x80, 0x00);
- SETOP(59, "ROR", 0x81, 0x85, 0x00, 0x00, 0x00, 0x00, 0x00, 0x83, 0x00);
- SETOP(60, "RRB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x82);
- SETOP(61, "CSP", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x88);
- SETOP(62, "BVS", 0x00, 0x1F, 0x00, 0x00, 0x00, 0x00, 0x00, 0x90, 0x00);
- SETOP(63, "MUL", 0x91, 0x95, 0x00, 0x00, 0x00, 0x00, 0x00, 0x93, 0x00);
- SETOP(64, "MAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x92);
- SETOP(65, "SEV", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x98);
- SETOP(66, "BVC", 0x00, 0x2F, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA0, 0x00);
- SETOP(67, "DIV", 0xA1, 0xA5, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA3, 0x00);
- SETOP(68, "DAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA2);
- SETOP(69, "CLV", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xA8);
- SETOP(70, "RTS", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xB0);
- SETOP(71, "CMP", 0xB1, 0xB5, 0x00, 0x00, 0xE9, 0xEB, 0xED, 0xB3, 0x00);
- SETOP(72, "CAB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xB2);
- SETOP(73, "CPY", 0x2A, 0x3B, 0x00, 0x00, 0xEA, 0xFA, 0x00, 0x2B, 0x00);
- SETOP(74, "CPX", 0xBC, 0x3D, 0x00, 0x00, 0xEC, 0x00, 0xFC, 0x2D, 0x00);
- SETOP(75, "CPB", 0xD6, 0xF6, 0x00, 0x00, 0xDF, 0xEF, 0xFF, 0xE6, 0x00);
- SETOP(76, "ENT", 0xB8, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00);
+ 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, "INY", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3A);
- SETOP(81, "INX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3C);
+ 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, "DEY", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x4A);
- SETOP(85, "DEX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x4C);
- SETOP(86, "WAI", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xD8);
- SETOP(87, "JSL", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE0, 0x00);
- SETOP(88, "ASR", 0xE1, 0xE5, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE3, 0x00);
- SETOP(89, "ARB", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE2);
- SETOP(90, "NOP", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE8);
- SETOP(91, "RTL", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xF0);
- SETOP(92, "BRK", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xF8);
+ 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);
FILE *fp;
if (strcasecmp(fn, "stdin") != 0) {
fp = fopen(fn, "r");
@@ -228,21 +313,25 @@ int asmmon(const char *fn) {
}
uint8_t done = 0;
uint64_t address = 0x0000;
+ uint64_t start, end;
+ uint8_t prefix, opcode;
while (!(done & 1)) {
char *buf = NULL;
char *ins;
char *postfix;
char mode[3];
opent op;
- uint8_t addrmode = 0;
+ uint8_t addrmode = IMPL;
uint64_t value = 0;
char *oprand;
char *cmd;
char ir[2] = ""; /* Index register. */
int a = 0;
+ int b = 0;
char *tmp = malloc(sizeof(char *)*128);
size_t size;
- done &= ~0x1F;
+ prefix = 0;
+ done = 0;
if (!strcasecmp(fn, "stdin")) {
getline(&buf, &size, stdin);
} else {
@@ -260,7 +349,7 @@ int asmmon(const char *fn) {
if (oprand != NULL) {
for (int i = 0; i < strlen(oprand); i++) {
if (oprand[i] == '(')
- addrmode = 6;
+ addrmode = IND;
if (oprand[i] == '"')
break;
if (a && oprand[a] == ',') {
@@ -272,7 +361,13 @@ int asmmon(const char *fn) {
ir[0] = 'y';
ir[1] = '\0';
}
+ if (b && ir[0] == 'y')
+ oprand[b] = '\0';
}
+ if (oprand[i] == ')' && oprand[i+1] == ',')
+ b = i;
+ else if (oprand[i] == ')')
+ oprand[i] = '\0';
if (oprand[i] == ',' || oprand[i] == ';')
a = i;
}
@@ -287,173 +382,327 @@ int asmmon(const char *fn) {
done |= 4;
viewmem(address);
}
+ if (!strcasecmp(cmd, "reslv") || !strcasecmp(cmd, "rf") || !strcasecmp(cmd, "r")) {
+ done |= 4;
+ puts("Resolving unknown labels.");
+ reslv_fixups();
+ puts("Finished resolving unknown labels.");
+ }
+ if (!strcasecmp(cmd, "help") || !strcasecmp(cmd, "h")) {
+ done |= 4;
+ usage();
+ }
if (oprand == NULL && ins == NULL && postfix == NULL) {
done |= 2;
}
- if (ins != NULL) {
- for (int i = 0; i < strlen(ins); i++) {
- if (i && ins[i] == ':') {
- ins[i] = '\0';
- mklabel(ins, address, 1);
- #if debug
- printf("Created label with the name %s, at address: $%llx\n", ins, address);
- #endif
- done |= 6;
- break;
- }
- if (ins[i] == ';') {
- if (i && (ins[i-1] == ' ' || ins[i-1] == '\t'))
- ins[i] = '\0';
- else
- done |=6;
- break;
- }
- }
- if (strcasecmp(ins, ".org") == 0) {
- done |= 6;
- oprand = strtok(oprand, "$");
- address = strtoull(oprand, NULL, 16);
- #if debug
- printf("Origin for program code is now at address $%llx.\n", address);
- #endif
+ cmd = strtok(cmd, " \n");
+ if (!strcasecmp(cmd, "inst") || !strcasecmp(cmd, "i")) {
+ done |= 64;
+ done |= 6;
+ if (oprand != NULL) {
+ instinfo(oprand);
+ } else {
+ instinfo("all");
}
- if (strcasecmp(ins, ".byte") == 0 || strcasecmp(ins, ".word") == 0 || strcasecmp(ins, ".dword") == 0 || strcasecmp(ins, ".qword") == 0) {
- done |= 6;
- uint8_t qstr = 0;
- uint64_t staddr = address;
- uint16_t slen = 0;
- char *tmpstr = tstr;
- char c;
- for (int i = 0; i < strlen(oprand); i++) {
- if (!qstr) {
- if ((isalnum(oprand[i]) || oprand[i] == '_') && oprand[i] != '"') {
- qstr = 0;
- value = use_label(oprand, address);
- sprintf(oprand, "%llx", value);
+
+ }
+ if (!strcasecmp(cmd, "disasm") || !strcasecmp(cmd, "dis") || !strcasecmp(cmd, "d")) {
+ done |= 64;
+ done |= 6;
+ if (oprand != NULL) {
+ cmd = strtok_r(oprand, " -", &tmp);
+ if (cmd != NULL) {
+ for (int i = 0; i < strlen(cmd); i++) {
+ if ((isalnum(cmd[i]) || cmd[i] == '_') && cmd[i] != '"') {
+ value = use_label(tmp, address);
+ sprintf(tmp, "%llx", value);
break;
}
- if (oprand[i] == '"' && !strcasecmp(ins, ".byte")) {
- qstr = 1;
- continue;
+ if (cmd[i] == '$') {
+ cmd = strtok(cmd, "$");
+ value = strtoull(cmd, NULL, 16);
+ break;
}
- if (oprand[i] == '$') {
- qstr = 0;
- oprand = strtok(oprand, "$");
- value = strtoull(oprand, NULL, 16);
+ if (cmd[i] == ';') {
+ done |= 16;
+ break;
+ }
+ }
+ start = value;
+ for (int i = 0; i < strlen(tmp); i++) {
+ if ((isalnum(tmp[i]) || tmp[i] == '_') && tmp[i] != '"') {
+ value = use_label(tmp, address);
+ sprintf(tmp, "%llx", value);
+ break;
+ }
+ if (tmp[i] == '$') {
+ tmp = strtok(tmp, "$");
+ value = strtoull(tmp, NULL, 16);
break;
}
- if (oprand[i] == ';') {
- qstr = 0;
+ if (tmp[i] == ';') {
done |= 16;
break;
}
- } else if (qstr == 1) {
- switch (oprand[i]) {
- case 0:
- puts("oof, unterminated string.");
- qstr = 2;
- break;
- case '"':
- value = '\0';
- 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';
+ }
+ (!strlen(tmp)) ? (end = address) : (end = value);
+ } else {
+ start = value;
+ end = address;
+ }
+ } else {
+ start = 0;
+ end = address;
+ }
+ while (start < end) {
+ uint8_t rs;
+ uint8_t regsize;
+ uint8_t addrsize;
+ if (start < 0xFF)
+ printf("$%02llx: ", start);
+ else if (start < 0xFFFF)
+ printf("$%04llx: ", start);
+ else if (start < 0xFFFFFFFF)
+ printf("$%08llx: ", start);
+ else if (start < 0xFFFFFFFFFFFFFFFF)
+ printf("$%016llx: ", start);
+ prefix = addr[start];
+ if ((prefix & 0x07) == 0x07) {
+ start+=1;
+ addrsize = (prefix & 8) >> 3;
+ rs = (prefix & 0x30) >> 4;
+ regsize = (1 << rs);
+ } else {
+ prefix = 0;
+ regsize = 1;
+ addrsize = 0;
+ }
+ opcode = addr[start];
+ start+=1;
+ switch (optype[opcode]) {
+ case IMPL:
+ 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;
+ }
+ start += regsize;
+ break;
+ case ZM:
+ case ZMX:
+ case ZMY:
+ case IND:
+ 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;
+ }
+ 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;
+ }
+ break;
+ }
+ disasm(prefix, opcode, value);
+ }
+ }
+ if (!(done & 64)) {
+ if (ins != NULL) {
+ for (int i = 0; i < strlen(ins); i++) {
+ if (i && ins[i] == ':') {
+ ins[i] = '\0';
+ mklabel(ins, address, 1);
+ #if debug
+ printf("Created label with the name %s, at address: $%llx\n", ins, address);
+ #endif
+ done |= 6;
+ break;
+ }
+ if (ins[i] == ';') {
+ if (i && (ins[i-1] == ' ' || ins[i-1] == '\t'))
+ ins[i] = '\0';
+ else
+ done |=6;
+ break;
+ }
+ }
+ if (!(done & 6)) {
+ if (oprand != NULL) {
+ if (!strcasecmp(ins, ".org")) {
+ done |= 6;
+ oprand = strtok(oprand, "$");
+ address = strtoull(oprand, NULL, 16);
+ #if debug
+ printf("Origin for program code is now at address $%llx.\n", address);
+ #endif
+ }
+ if (!strcasecmp(ins, ".byte") || !strcasecmp(ins, ".word") || !strcasecmp(ins, ".dword") || !strcasecmp(ins, ".qword")) {
+ done |= 6;
+ uint8_t qstr = 0;
+ uint64_t staddr = address;
+ uint16_t slen = 0;
+ char *tmpstr = tstr;
+ char c;
+ for (int i = 0; i < strlen(oprand); i++) {
+ if (!qstr) {
+ if ((isalnum(oprand[i]) || oprand[i] == '_') && oprand[i] != '"') {
+ qstr = 0;
+ value = use_label(oprand, address);
+ sprintf(oprand, "%llx", value);
break;
- case '0':
+ }
+ if (oprand[i] == '"' && !strcasecmp(ins, ".byte")) {
+ qstr = 1;
+ continue;
+ }
+ if (oprand[i] == '$') {
+ qstr = 0;
+ oprand = strtok(oprand, "$");
+ value = strtoull(oprand, NULL, 16);
break;
- default:
- value = oprand[i];
- tmpstr[slen++] = '\\';
- tmpstr[slen++] = oprand[i];
+ }
+ if (oprand[i] == ';') {
+ qstr = 0;
+ done |= 16;
break;
+ }
+ } else if (qstr == 1) {
+ switch (oprand[i]) {
+ case 0:
+ puts("oof, unterminated string.");
+ qstr = 2;
+ break;
+ case '"':
+ value = '\0';
+ 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;
+ }
+ addr[address++] = (uint8_t)value & 0xFF;
}
- i++;
- break;
- default:
- value = oprand[i];
- c = oprand[i];
- tmpstr[slen++] = c;
- break;
+ }
+ if (!strcasecmp(ins, ".byte") && !qstr)
+ addr[address++] = value & 0xFF;
+ if (!strcasecmp(ins, ".word")) {
+ addr[address] = (uint8_t)value & 0xFF;
+ addr[address+1] = value >> 8;
+ address+=2;
+ }
+ if (!strcasecmp(ins, ".dword")) {
+ addr[address] = (uint8_t)value & 0xFF;
+ addr[address+1] = value >> 8;
+ addr[address+2] = value >> 16;
+ addr[address+3] = value >> 24;
+ address+=4;
+ }
+ if (!strcasecmp(ins, ".qword")) {
+ addr[address] = (uint8_t)value & 0xFF;
+ addr[address+1] = value >> 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;
+ }
+ #if debug
+ if (!qstr) {
+ printf("The value $%llx was placed at address%s ", value, (staddr != address-1) ? "es" : "");
+ if (staddr == address-1)
+ printf("$%llx.\n", staddr);
+ else
+ printf("$%llx-$%llx.\n", staddr, address-1);
+ } else {
+ printf("The string \"%s\", was placed at address%s ", tmpstr, (staddr != address-1) ? "es" : "");
+ if (staddr == address-1)
+ printf("$%llx.\n", staddr);
+ else
+ printf("$%llx-$%llx.\n", staddr, address-1);
+ }
+ #endif
}
- addr[address++] = value & 0xFF;
}
}
- if (strcasecmp(ins, ".byte") == 0 && !qstr)
- addr[address++] = value & 0xFF;
- if (strcasecmp(ins, ".word") == 0) {
- addr[address] = value & 0xFF;
- addr[address+1] = value >> 8;
- address+=2;
- }
- if (strcasecmp(ins, ".dword") == 0) {
- addr[address] = value & 0xFF;
- addr[address+1] = value >> 8;
- addr[address+2] = value >> 16;
- addr[address+3] = value >> 24;
- address+=4;
- }
- if (strcasecmp(ins, ".qword") == 0) {
- addr[address] = value & 0xFF;
- addr[address+1] = value >> 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;
- }
- #if debug
- if (!qstr) {
- printf("The value $%llx was placed at address%s ", value, (staddr != address-1) ? "es" : "");
- if (staddr == address-1)
- printf("$%llx.\n", staddr);
- else
- printf("$%llx-$%llx.\n", staddr, address-1);
- } else {
- printf("The string \"%s\", was placed at address%s ", tmpstr, (staddr != address-1) ? "es" : "");
- if (staddr == address-1)
- printf("$%llx.\n", staddr);
- else
- printf("$%llx-$%llx.\n", staddr, address-1);
- }
- #endif
}
}
if (oprand == NULL && !strcasecmp(ins, "TXS")) {
- addrmode = 1;
+ addrmode = IMM;
done |= 32;
}
else if (oprand != NULL && !strcasecmp(ins, "TXS"))
- addr[address++] = 0x17;
+ prefix = 0x17;
if (!(done & 2) && oprand != NULL) {
mode[0] = oprand[0];
mode[1] = oprand[1];
- if (oprand[0] == '#' || oprand[0] == '$' || oprand[0] == '(') {
+ if (oprand[0] == '#' || oprand[0] == '$' || (oprand[0] == '(' && (oprand[1] == '$' || oprand[1] == '%'))) {
oprand = strtok(oprand, "#($%");
if (mode[0] == '#') {
- addrmode = 1;
+ addrmode = IMM;
done |= 32;
if (mode[1] == '$')
value = strtoull(oprand, NULL, 16);
@@ -468,26 +717,33 @@ 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 & 0xFFFFFFFF || !value) {
- addrmode = 2;
- } else if (value & 0xFFFFFFFF00000000) {
- addrmode = 5;
+ if (value & 0xFFFF0000 || (value <= 0xFF) ||
+ (value & 0xFF00 && address <= 0xFFFF && (ir[0] == 'x' || ir[0] == 'y'))) {
+ addrmode = ZM;
+ if (value & 0xFFFFFF00)
+ prefix |= 0xF;
+ } else if (value & 0xFFFFFFFF00000000 || (value & 0xFF00 && address <= 0xFFFF)) {
+ addrmode = ABS;
+ if (value & 0xFFFFFFFF00000000)
+ prefix |= 0xF;
}
}
if ((addrmode == 2 || addrmode == 6) && ir != NULL) {
switch (ir[0]) {
case 'x':
- if (addrmode == 2)
- addrmode = 3;
- else if (addrmode == 6)
- addrmode = 7;
+ if (addrmode == ZM)
+ addrmode = ZMX;
+ else if (addrmode == IND)
+ addrmode = INDX;
break;
case 'y':
- if (addrmode == 2)
- addrmode = 4;
- else if (addrmode == 6)
- addrmode = 8;
+ if (addrmode == ZM)
+ addrmode = ZMY;
+ else if (addrmode == IND)
+ addrmode = INDY;
break;
default:
done |= 32;
@@ -496,6 +752,8 @@ int asmmon(const char *fn) {
}
}
} else {
+ if (mode[0] == '(')
+ oprand = strtok(oprand, "#($%");
for (int i = 0; i < strlen(oprand); i++) {
if (oprand[i] == ';') {
done |= 16;
@@ -503,26 +761,33 @@ 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 & 0xFFFFFFFF || !value) {
- addrmode = 2;
- } else if (value & 0xFFFFFFFF00000000) {
- addrmode = 5;
+ if (value & 0xFFFF0000 || (value <= 0xFF) ||
+ (value <= 0xFFFF && address <= 0xFFFF && (ir[0] == 'x' || ir[0] == 'y'))) {
+ addrmode = ZM;
+ if (value & 0xFFFFFF00)
+ prefix |= 0xF;
+ } else if (value & 0xFFFFFFFF00000000 || (value & 0xFF00 && address <= 0xFFFF)) {
+ addrmode = ABS;
+ if (value & 0xFFFFFFFF00000000)
+ prefix |= 0xF;
}
}
- if ((addrmode == 2 || addrmode == 6) && ir != NULL && a) {
+ if ((addrmode == ZM || addrmode == IND) && ir != NULL && a) {
switch (ir[0]) {
case 'x':
- if (addrmode == 2)
- addrmode = 3;
- else if (addrmode == 6)
- addrmode = 7;
+ if (addrmode == ZM)
+ addrmode = ZMX;
+ else if (addrmode == IND)
+ addrmode = INDX;
break;
case 'y':
- if (addrmode == 2)
- addrmode = 4;
- else if (addrmode == 6)
- addrmode = 8;
+ if (addrmode == ZM)
+ addrmode = ZMY;
+ else if (addrmode == IND)
+ addrmode = INDY;
break;
default:
done |= 32;
@@ -539,14 +804,16 @@ int asmmon(const char *fn) {
uint8_t i;
for (i = 0; i < OPNUM; i++) {
if (strcasecmp(opcodes[i].mnemonic, ins) == 0) {
- if (addrmode == 0 && (opcodes[i].impl || opcodes[i].impl == CPS)) {
+ if (addrmode == IMPL && (opcodes[i].impl || opcodes[i].impl == CPS)) {
done |= 8;
- } else if (addrmode == 1) {
+ } else if (addrmode == IMM) {
switch (opcodes[i].imm) {
+ case PHB:
case PHP:
case PHA:
case PHY:
case PHX:
+ case PLB:
case PLP:
case PLA:
case PLY:
@@ -594,24 +861,27 @@ int asmmon(const char *fn) {
}
if (postfix != NULL && !(done & 8)) {
if (!strcasecmp(postfix, "w") || !strcasecmp(postfix, "2")) {
- addr[address++] = 0x17;
+ prefix |= 0x17;
} else if (!strcasecmp(postfix, "d") || !strcasecmp(postfix, "4")) {
- addr[address++] = 0x27;
+ prefix |= 0x27;
} else if (!strcasecmp(postfix, "q") || !strcasecmp(postfix, "8")) {
- addr[address++] = 0x37;
- } else {
+ prefix |= 0x37;
+ } else if (!prefix) {
done |=8;
}
- } else if (postfix == NULL && !(done & 8)) {
+ } else if (postfix == NULL && (!(done & 8) && !prefix)) {
done |=8;
}
uint8_t r;
- if (!(done & 8))
- r = addr[address-1];
- else
+ if (!(done & 8)) {
+ r = prefix;
+ addr[address] = prefix;
+ address += 1;
+ } else {
r = 0;
+ }
switch (addrmode) {
- case 0:
+ case IMPL:
if (op.impl || op.impl == CPS) {
addr[address++] = op.impl;
break;
@@ -619,10 +889,10 @@ int asmmon(const char *fn) {
fprintf(stderr, "oof, %s requires an operand.\n", op.mnemonic);
}
break;
- case 1:
+ case IMM:
if (op.imm) {
- if (addr[address-1] == 0x17 && op.imm == TXS)
- r = 0x17;
+ if ((prefix & 0x30) == 0x10 && op.imm == TXS)
+ r = prefix;
addr[address++] = op.imm;
switch (op.imm) {
case PHP:
@@ -643,7 +913,7 @@ int asmmon(const char *fn) {
addr[address++] = value & 0xFF;
break;
case TXS:
- if (r == 0x17) {
+ if ((r & 0x30) == 0x10) {
addr[address] = value & 0xFF;
addr[address+2] = value >> 8;
address+=2;
@@ -670,96 +940,124 @@ int asmmon(const char *fn) {
fprintf(stderr, "oof, %s does not use Immediate data.\n", op.mnemonic);
}
break;
- case 2:
+ case ZM:
if (op.zm) {
addr[address++] = op.zm;
addr[address] = value & 0xFF;
- addr[address+1] = value >> 8;
- addr[address+2] = value >> 16;
- addr[address+3] = value >> 24;
- address+=4;
+ if ((r & 8) == 8) {
+ addr[address+1] = value >> 8;
+ addr[address+2] = value >> 16;
+ addr[address+3] = value >> 24;
+ address+=4;
+ } else {
+ address+=1;
+ }
break;
} else {
fprintf(stderr, "oof, %s does not use Zero Matrix.\n", op.mnemonic);
}
break;
- case 3:
+ case ZMX:
if (op.zmx) {
addr[address++] = op.zmx;
addr[address] = value & 0xFF;
- addr[address+1] = value >> 8;
- addr[address+2] = value >> 16;
- addr[address+3] = value >> 24;
- address+=4;
+ if ((r & 8) == 8) {
+ addr[address+1] = value >> 8;
+ addr[address+2] = value >> 16;
+ addr[address+3] = value >> 24;
+ address+=4;
+ } else {
+ address+=1;
+ }
break;
} else {
fprintf(stderr, "oof, %s does not use Zero Matrix, indexed with x.\n", op.mnemonic);
}
break;
- case 4:
+ case ZMY:
if (op.zmy) {
addr[address++] = op.zmy;
addr[address] = value & 0xFF;
- addr[address+1] = value >> 8;
- addr[address+2] = value >> 16;
- addr[address+3] = value >> 24;
- address+=4;
+ if ((r & 8) == 8) {
+ addr[address+1] = value >> 8;
+ addr[address+2] = value >> 16;
+ addr[address+3] = value >> 24;
+ address+=4;
+ } else {
+ address+=1;
+ }
break;
} else {
fprintf(stderr, "oof, %s does not use Zero Matrix, indexed with y.\n", op.mnemonic);
}
break;
- case 5:
+ case ABS:
if (op.abs) {
addr[address++] = op.abs;
addr[address] = value & 0xFF;
addr[address+1] = value >> 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;
+ 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;
+ }
break;
} else {
fprintf(stderr, "oof, %s cannot be an absolute dictator.\n", op.mnemonic);
}
break;
- case 6:
+ case IND:
if (op.ind) {
addr[address++] = op.ind;
addr[address] = value & 0xFF;
- addr[address+1] = value >> 8;
- addr[address+2] = value >> 16;
- addr[address+3] = value >> 24;
- address+=4;
+ if ((r & 8) == 8) {
+ addr[address+1] = value >> 8;
+ addr[address+2] = value >> 16;
+ addr[address+3] = value >> 24;
+ address+=4;
+ } else {
+ address+=1;
+ }
break;
} else {
fprintf(stderr, "oof, %s cannot use pointers.\n", op.mnemonic);
}
break;
- case 7:
+ case INDX:
if (op.inx) {
addr[address++] = op.inx;
addr[address] = value & 0xFF;
- addr[address+1] = value >> 8;
- addr[address+2] = value >> 16;
- addr[address+3] = value >> 24;
- address+=4;
+ if ((r & 8) == 8) {
+ addr[address+1] = value >> 8;
+ addr[address+2] = value >> 16;
+ addr[address+3] = value >> 24;
+ address+=4;
+ } else {
+ address+=1;
+ }
break;
} else {
fprintf(stderr, "oof, %s does not use Indexed Indirect.\n", op.mnemonic);
}
break;
- case 8:
+ case INDY:
if (op.iny) {
addr[address++] = op.iny;
addr[address] = value & 0xFF;
- addr[address+1] = value >> 8;
- addr[address+2] = value >> 16;
- addr[address+3] = value >> 24;
- address+=4;
+ if ((r & 8) == 8) {
+ addr[address+1] = value >> 8;
+ addr[address+2] = value >> 16;
+ addr[address+3] = value >> 24;
+ address+=4;
+ } else {
+ address+=1;
+ }
break;
} else {
fprintf(stderr, "oof, %s does not use Indirect Indexed.\n", op.mnemonic);