#include "opcode.h" #include #include #define debug 1 #define OPNUM 89 #define SETOP(num, _mne, _IMM, _ZM, _ZMX, _ZMY, _ABS, _IMPL) \ {opcodes[num].mnemonic[3] = '\0'; strncpy(opcodes[num].mnemonic, _mne, 3); \ opcodes[num].imm = _IMM; \ opcodes[num].zm = _ZM; opcodes[num].zmx = _ZMX; opcodes[num].zmy = _ZMY; \ opcodes[num].abs = _ABS; opcodes[num].impl = _IMPL;} struct fixup { struct fixup *nxt; struct label *l; uint64_t adr; }; struct label { struct label* nxt; uint64_t adr; uint8_t def; char name[1]; }; static char tstr[2048]; struct label *labels = 0; struct fixup *fixups = 0; uint8_t defined = 0; struct label *mklabel(const char *name, uint64_t adr, uint8_t def) { struct label *l; for (l = labels; l; l = l->nxt) { if (!strcasecmp(name, l->name)) { if (def) { if (l->def) { printf("oof, you cannot redefine the label: %s\n", name); defined = 1; } else { defined = 0; } l->def = def; l->adr = adr; } return l; } } l = malloc(sizeof(*l) + strlen(name)); l->def = def; l->adr = adr; strcpy(l->name, name); l->nxt = labels; labels = l; defined = 0; return l; } 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); struct fixup *f = malloc(sizeof(*f)); f->nxt = fixups; f->adr = adr; f->l = l; fixups = f; return adr-1; } } void reslv_fixups(void) { struct fixup *f; for (f = fixups; f; f = f->nxt) { if (f->l->def) { addr[f->adr] = f->l->adr & 0xFF; if (f->l->adr & 0xFF00) addr[f->adr+1] = f->l->adr >> 8; if (f->l->adr & 0xFF000000) { addr[f->adr+2] = f->l->adr >> 16; addr[f->adr+3] = f->l->adr >> 24; } if (f->l->adr & 0xFF00000000000000) { addr[f->adr+4] = f->l->adr >> 32; addr[f->adr+5] = f->l->adr >> 40; addr[f->adr+6] = f->l->adr >> 48; addr[f->adr+7] = f->l->adr >> 56; } } else { printf("oof, undefined reference to '%s', at $%016llx.\n", f->l->name, f->adr); } } } void viewmem(uint64_t address) { printf("\t\t\t"); for (int ind = 0; ind < 0x10; ind++) { printf("%02x", ind); if (ind < 0x0F) printf(" "); } printf("\n\n"); for (int hi = 0; hi < 0x10; hi++) { printf("%016llx:\t", (address & ~0xF)+(hi*0x10)); for (int lo = 0; lo < 0x10; lo++) { printf("%02x", addr[(address & ~0xF)+lo+(hi*0x10)]); if (lo < 0x0F) printf(" "); } printf("\n"); } } int asmmon(const char *fn) { opent opcodes[OPNUM]; /* mne IMM ZM ZMX ZMY ABS IMPL*/ SETOP(0, "CPS", 0x00, 0x00, 0x00, 0x00, 0x00, 0x00); SETOP(1, "ADC", 0x01, 0x05, 0x00, 0x00, 0x03, 0x00); SETOP(2, "PHP", 0x08, 0x00, 0x00, 0x00, 0x00, 0x00); SETOP(3, "PHA", 0x09, 0x00, 0x00, 0x00, 0x00, 0x00); SETOP(4, "PHY", 0x0A, 0x00, 0x00, 0x00, 0x00, 0x00); SETOP(5, "TAY", 0x00, 0x00, 0x00, 0x00, 0x00, 0x0B); SETOP(6, "PHX", 0x0C, 0x00, 0x00, 0x00, 0x00, 0x00); SETOP(7, "TAX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x0D); SETOP(8, "TYX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x0E); SETOP(9, "JMP", 0x00, 0xD0, 0x00, 0x00, 0x10, 0x00); SETOP(10, "SBC", 0x11, 0x15, 0x00, 0x00, 0x13, 0x00); SETOP(11, "PLP", 0x18, 0x00, 0x00, 0x00, 0x00, 0x00); SETOP(12, "PLA", 0x19, 0x00, 0x00, 0x00, 0x00, 0x00); SETOP(13, "PLY", 0x1A, 0x00, 0x00, 0x00, 0x00, 0x00); SETOP(14, "TYA", 0x00, 0x00, 0x00, 0x00, 0x00, 0x1B); SETOP(15, "PLX", 0x1C, 0x00, 0x00, 0x00, 0x00, 0x00); SETOP(16, "TXA", 0x00, 0x00, 0x00, 0x00, 0x00, 0x1D); SETOP(17, "TXY", 0x00, 0x00, 0x00, 0x00, 0x00, 0x1E); SETOP(18, "JSR", 0x00, 0x20, 0x00, 0x00, 0x00, 0x00); SETOP(19, "AND", 0x21, 0x2B, 0x00, 0x00, 0x29, 0x00); SETOP(20, "ANY", 0x22, 0x82, 0x00, 0x00, 0x52, 0x00); SETOP(21, "AAY", 0x00, 0x00, 0x00, 0x00, 0x00, 0x23); SETOP(22, "ANX", 0x24, 0x84, 0x00, 0x00, 0x54, 0x00); SETOP(23, "AAX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x25); SETOP(24, "STT", 0x28, 0x00, 0x00, 0x00, 0x00, 0x00); SETOP(25, "TSX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x2E); SETOP(26, "BPO", 0x00, 0x00, 0x00, 0x00, 0x30, 0x00); SETOP(27, "ORA", 0x31, 0x3B, 0x00, 0x00, 0x39, 0x00); SETOP(28, "ORY", 0x32, 0x00, 0x00, 0x00, 0x62, 0x00); SETOP(29, "OAY", 0x00, 0x00, 0x00, 0x00, 0x00, 0x33); SETOP(23, "ORX", 0x34, 0x94, 0x00, 0x00, 0x64, 0x00); SETOP(31, "OAX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x35); SETOP(32, "SEI", 0x00, 0x00, 0x00, 0x00, 0x00, 0x38); SETOP(33, "TXS", 0x3E, 0x00, 0x00, 0x00, 0x00, 0x00); SETOP(34, "BNG", 0x00, 0x00, 0x00, 0x00, 0x40, 0x00); SETOP(35, "XOR", 0x41, 0x4B, 0x00, 0x00, 0x49, 0x00); SETOP(36, "XRY", 0x42, 0xA2, 0x00, 0x00, 0x72, 0x00); SETOP(37, "XAY", 0x00, 0x00, 0x00, 0x00, 0x00, 0x43); SETOP(38, "XRX", 0x44, 0xA4, 0x00, 0x00, 0x74, 0x00); SETOP(39, "XAX", 0x00, 0x00, 0x00, 0x00, 0x00, 0x45); SETOP(40, "CLI", 0x00, 0x00, 0x00, 0x00, 0x00, 0x48); SETOP(41, "BCS", 0x00, 0x00, 0x00, 0x00, 0x50, 0x00); SETOP(42, "LSL", 0x51, 0x55, 0x00, 0x00, 0x53, 0x00); SETOP(43, "SEC", 0x00, 0x00, 0x00, 0x00, 0x00, 0x58); SETOP(44, "STA", 0x00, 0x7B, 0x8B, 0x9B, 0x5B, 0x00); SETOP(45, "STY", 0x00, 0x7D, 0x8D, 0x00, 0x5D, 0x00); SETOP(46, "STX", 0x00, 0x7E, 0x00, 0x9E, 0x5E, 0x00); SETOP(47, "BCC", 0x00, 0x00, 0x00, 0x00, 0x60, 0x00); SETOP(48, "LSR", 0x61, 0x65, 0x00, 0x00, 0x63, 0x00); SETOP(49, "CLC", 0x00, 0x00, 0x00, 0x00, 0x00, 0x68); SETOP(50, "LDA", 0x69, 0x79, 0x89, 0x99, 0x59, 0x00); SETOP(51, "LDY", 0x6A, 0x7A, 0x8A, 0x00, 0x5A, 0x00); SETOP(52, "LDX", 0x6C, 0x7C, 0x00, 0x9C, 0x5C, 0x00); SETOP(53, "BEQ", 0x00, 0x00, 0x00, 0x00, 0x70, 0x00); SETOP(54, "ROL", 0x71, 0x75, 0x00, 0x00, 0x73, 0x00); SETOP(55, "SSP", 0x00, 0x00, 0x00, 0x00, 0x00, 0x78); SETOP(56, "BNE", 0x00, 0x00, 0x00, 0x00, 0x80, 0x00); SETOP(57, "ROR", 0x81, 0x85, 0x00, 0x00, 0x83, 0x00); SETOP(58, "CSP", 0x00, 0x00, 0x00, 0x00, 0x00, 0x88); SETOP(59, "BVS", 0x00, 0x00, 0x00, 0x00, 0x90, 0x00); SETOP(60, "MUL", 0x91, 0x95, 0x00, 0x00, 0x93, 0x00); SETOP(61, "SEV", 0x00, 0x00, 0x00, 0x00, 0x00, 0x98); SETOP(62, "BVC", 0x00, 0x00, 0x00, 0x00, 0xA0, 0x00); SETOP(63, "DIV", 0xA1, 0xA5, 0x00, 0x00, 0xA3, 0x00); SETOP(64, "CLV", 0x00, 0x00, 0x00, 0x00, 0x00, 0xA8); SETOP(65, "ASR", 0xA9, 0xAD, 0x00, 0x00, 0xAB, 0x00); SETOP(66, "RTS", 0x00, 0x00, 0x00, 0x00, 0x00, 0xB0); SETOP(67, "CMP", 0xB1, 0xF5, 0x00, 0x00, 0xE5, 0x00); SETOP(68, "CPY", 0xB2, 0xF2, 0x00, 0x00, 0xE2, 0x00); SETOP(69, "CAY", 0x00, 0x00, 0x00, 0x00, 0x00, 0xB3); SETOP(70, "CPX", 0xB4, 0xF4, 0x00, 0x00, 0xE4, 0x00); SETOP(71, "CAX", 0x00, 0x00, 0x00, 0x00, 0x00, 0xB5); SETOP(72, "ENT", 0xB8, 0x00, 0x00, 0x00, 0x00, 0x00); SETOP(73, "RTI", 0x00, 0x00, 0x00, 0x00, 0x00, 0xC0); SETOP(74, "INC", 0x00, 0xE3, 0x00, 0x00, 0xE1, 0xC1); SETOP(75, "INY", 0x00, 0x00, 0x00, 0x00, 0x00, 0xC2); SETOP(76, "IAY", 0x00, 0x00, 0x00, 0x00, 0x00, 0xC3); SETOP(77, "INX", 0x00, 0x00, 0x00, 0x00, 0x00, 0xC4); SETOP(78, "IAX", 0x00, 0x00, 0x00, 0x00, 0x00, 0xC5); SETOP(79, "DEC", 0x00, 0x00, 0x00, 0x00, 0x00, 0xD1); SETOP(80, "DEY", 0x00, 0x00, 0x00, 0x00, 0x00, 0xD2); SETOP(81, "DAY", 0x00, 0xF3, 0x00, 0x00, 0xF1, 0xD3); SETOP(82, "DEX", 0x00, 0x00, 0x00, 0x00, 0x00, 0xD4); SETOP(83, "DAX", 0x00, 0x00, 0x00, 0x00, 0x00, 0xD5); SETOP(84, "WAI", 0x00, 0x00, 0x00, 0x00, 0x00, 0xD8); SETOP(85, "JSL", 0x00, 0x00, 0x00, 0x00, 0xE0, 0x00); SETOP(86, "NOP", 0x00, 0x00, 0x00, 0x00, 0x00, 0xE8); SETOP(87, "RTL", 0x00, 0x00, 0x00, 0x00, 0x00, 0xF0); SETOP(88, "BRK", 0x00, 0x00, 0x00, 0x00, 0x00, 0xF8); FILE *fp; if (strcasecmp(fn, "stdin") != 0) { fp = fopen(fn, "r"); if (fp == NULL) return 2; } uint8_t done = 0; uint64_t address = 0x0000; while (!(done & 1)) { char *buf = NULL; char *ins; char *postfix; char mode[3]; opent op; uint8_t addrmode = 0; uint64_t value = 0; char *oprand; char *cmd; char ir[2] = ""; /* Index register. */ int a = 0; char *tmp = malloc(sizeof(char *)*128); size_t size; done &= ~0x1F; if (!strcasecmp(fn, "stdin")) { getline(&buf, &size, stdin); } else { getline(&buf, &size, fp); } cmd = strtok_r(buf, "\n", &tmp); if (cmd != NULL) { if (strcasecmp(cmd, "done") == 0) { done |= 1; } else { ins = strtok(buf, "\t\n "); if (ins != NULL) { oprand = strtok(NULL, "\t\n"); strtok_r(ins, ".", &postfix); if (oprand != NULL) { for (int i = 0; i < strlen(oprand); i++) { if (oprand[i] == '"') break; if (oprand[i] == 'x' || oprand[i] == 'X') { ir[0] = 'x'; ir[1] = '\0'; break; } if (oprand[i] == 'y' || oprand[i] == 'Y') { ir[0] = 'y'; ir[1] = '\0'; break; } if (oprand[i] == ',' || oprand[i] == ';') { a = i; } } if (a) oprand[a] = '\0'; } } if (strcasecmp(cmd, "quit") == 0 || strcasecmp(cmd, "q") == 0) { return 2; } if (strcasecmp(cmd, "viewmem") == 0) { done |= 4; viewmem(address); } 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 } 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); break; } if (oprand[i] == '"' && !strcasecmp(ins, ".byte")) { qstr = 1; continue; } if (oprand[i] == '$') { qstr = 0; oprand = strtok(oprand, "$"); value = strtoull(oprand, NULL, 16); break; } 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++] = 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; else if (oprand != NULL && !strcasecmp(ins, "TXS")) addr[address++] = 0x17; if (!(done & 2) && oprand != NULL) { if (oprand[0] == '#' || oprand[0] == '$') { if(oprand[0] == '#' && (oprand[1] == '$' || oprand[1] == '%')) { mode[1] = oprand[1]; mode[2] = '\0'; } else { mode[1] = '\0'; } mode[0] = oprand[0]; oprand = strtok(oprand, "#$%"); if (mode[0] == '#') { addrmode = 1; if (mode[1] == '$') value = strtoull(oprand, NULL, 16); if (mode[1] == '%') value = strtoull(oprand, NULL, 2); } if (mode[0] == '$') { value = strtoull(oprand, NULL, 16); if (value == 0) addrmode = 2; if (value & 0xFFFFFFFF) { char *stf[] = {"BPO", "BNG", "BCS", "BCC", "BEQ", "BNE", "BVS", "BVC"}; for (int i = 0; i < 8; i++) { if (strcasecmp(ins, stf[i]) == 0) { addrmode = 5; break; } else { addrmode = 2; } } } else if (value & 0xFFFFFFFF00000000) { addrmode = 5; } if (addrmode == 2 && ir != NULL) { switch (ir[0]) { case 'x': addrmode = 3; break; case 'y': addrmode = 4; break; } } } } else { for (int i = 0; i < strlen(oprand); i++) { if (oprand[i] == ';') { done |= 16; break; } if ((isalnum(oprand[i]) || oprand[i] == '_') && oprand[i] != '"') { value = use_label(oprand, address); if (value == 0) addrmode = 2; if (value & 0xFFFFFFFF || value == 0) { char *stf[] = {"BPO", "BNG", "BCS", "BCC", "BEQ", "BNE", "BVS", "BVC"}; for (int i = 0; i < 8; i++) { if (!strcasecmp(ins, stf[i])) { addrmode = 5; break; } else { addrmode = 2; } } } else if (value & 0xFFFFFFFF00000000) { addrmode = 5; } if (addrmode == 2 && ir != NULL) { switch (ir[0]) { case 'x': addrmode = 3; break; case 'y': addrmode = 4; break; } } sprintf(oprand, "%llx", value); break; } } } } if (ins != NULL && !(done & 6)) { 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)) { done |= 8; } else if (addrmode == 1) { switch (opcodes[i].imm) { case PHP: case PHA: case PHY: case PHX: case PLP: case PLA: case PLY: case PLX: case STT: case TXS: case LSL: case LSR: case ROL: case ROR: case ASR: case ENT: done |= 8; break; } } else { if (strcasecmp(ins, "JMP") == 0) done |=8; if (strcasecmp(ins, "JSR") == 0) done |=8; if (strcasecmp(ins, "JSL") == 0) done |=8; if (strcasecmp(ins, "INC") == 0) done |=8; if (strcasecmp(ins, "BPO") == 0) done |=8; if (strcasecmp(ins, "BNG") == 0) done |=8; if (strcasecmp(ins, "BCS") == 0) done |=8; if (strcasecmp(ins, "BCC") == 0) done |=8; if (strcasecmp(ins, "BEQ") == 0) done |=8; if (strcasecmp(ins, "BNE") == 0) done |=8; if (strcasecmp(ins, "BVS") == 0) done |=8; if (strcasecmp(ins, "BVC") == 0) done |=8; } op = opcodes[i]; break; } } if (postfix != NULL && !(done & 8)) { if (!strcasecmp(postfix, "w") || !strcasecmp(postfix, "2")) { addr[address++] = 0x17; } else if (!strcasecmp(postfix, "d") || !strcasecmp(postfix, "4")) { addr[address++] = 0x27; } else if (!strcasecmp(postfix, "q") || !strcasecmp(postfix, "8")) { addr[address++] = 0x37; } else { done |=8; } } else if (postfix == NULL && !(done & 8)) { done |=8; } uint8_t r; if (!(done & 8)) r = addr[address-1]; else r = 0; switch (addrmode) { case 0: if (op.impl || op.impl == CPS) { addr[address++] = op.impl; break; } else { fprintf(stderr, "oof, %s requires an operand.\n", op.mnemonic); } break; case 1: if (op.imm) { if (addr[address-1] == 0x17 && op.imm == TXS) r = 0x17; addr[address++] = op.imm; switch (op.imm) { case PHP: case PHA: case PHY: case PHX: case PLP: case PLA: case PLY: case PLX: case STT: case LSL: case LSR: case ROL: case ROR: case ASR: case ENT: addr[address++] = value & 0xFF; break; case TXS: if (r == 0x17) { addr[address] = value & 0xFF; addr[address+2] = value >> 8; address+=2; } break; default: addr[address] = value & 0xFF; if (r & 0x10) addr[address+1] = value >> 8; if (r & 0x20) addr[address+2] = value >> 16; addr[address+3] = value >> 24; 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)); break; } break; } else { fprintf(stderr, "oof, %s does not use Immediate data.\n", op.mnemonic); } break; case 2: 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; break; } else { fprintf(stderr, "oof, %s does not use Zero Matrix.\n", op.mnemonic); } break; case 3: 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; break; } else { fprintf(stderr, "oof, %s does not use Zero Matrix, indexed with x.\n", op.mnemonic); } break; case 4: 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; break; } else { fprintf(stderr, "oof, %s does not use Zero Matrix, indexed with y.\n", op.mnemonic); } break; case 5: 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; break; } else { fprintf(stderr, "oof, %s cannot be an absolute dictator.\n", op.mnemonic); } break; } #if debug if (!(done & 6)) { printf("instruction: %s, ", ins); #if (!__GLIBC__) || (__TINYC__) printf("Postfix: %s, ", (postfix != NULL) ? postfix : "none"); #else printf("Postfix: %s, ", (postfix[0] != '\0') ? postfix : "none"); #endif printf("Operand: %s, ", (oprand != NULL && !(done & 16)) ? oprand : "none"); printf("Index Register: %s, ", (ir != NULL) ? ir : "none"); printf("Address: $%llx\n", address); } #endif } } } } reslv_fixups(); return 0; }