#include <u.h>
#include <libc.h>
#include "6502.h"
void asprintf(char** targ, char* msg, ...) {
*targ = malloc(512);
va_list va;
va_start(va, msg);
vsnprint(*targ, 511, msg, va);
va_end(va);
}
char* disasm(byte* x) {
switch(*x) {
case 0x00: return strdup("BRK"); break;
case 0x08: return strdup("PHP"); break;
case 0x18: return strdup("CLC"); break;
case 0x20: {
char* buf;
asprintf(&buf, "JSR $%.2x", x[1] | (x[2] << 8));
return buf;
}
case 0x28: return strdup("PLP"); break;
case 0x38: return strdup("SEC"); break;
case 0x40: return strdup("RTI"); break;
case 0x48: return strdup("PHA"); break;
case 0x4C: {
char* buf;
asprintf(&buf, "JMP $%.2x", x[1] | (x[2] << 8));
return buf;
}
case 0x58: return strdup("CLI"); break;
case 0x60: return strdup("RTS"); break;
case 0x6C: {
char* buf;
asprintf(&buf, "JMP ($%.2x)", x[1] | (x[2] << 8));
return buf;
}
case 0x68: return strdup("PLA"); break;
case 0x78: return strdup("SEI"); break;
case 0x88: return strdup("DEY"); break;
case 0x8A: return strdup("TXA"); break;
case 0x98: return strdup("TYA"); break;
case 0x9A: return strdup("TXS"); break;
case 0xA8: return strdup("TAY"); break;
case 0xAA: return strdup("TAX"); break;
case 0xB8: return strdup("CLV"); break;
case 0xBA: return strdup("TSX"); break;
case 0xC8: return strdup("INY"); break;
case 0xCA: return strdup("DEX"); break;
case 0xD8: return strdup("CLD"); break;
case 0xE8: return strdup("INX"); break;
case 0xEA: return strdup("NOP"); break;
case 0xF8: return strdup("SED"); break;
}
byte a = *x >> 5;
byte b = (*x >> 2) & 7;
byte c = *x & 3;
if(c == 0) {
if(b != 4) {
char * os[] = {"", "BIT", "JMP", "JMP", "STY", "LDY", "CPY", "CPX"};
char* buf;
switch(b) {
case 0: asprintf(&buf, "%s #$%x", os[a], x[1]); break;
case 1: asprintf(&buf, "%s $%x", os[a], x[1]); break;
case 3: asprintf(&buf, "%s $%x", os[a], x[1] | (x[2] << 8)); break;
case 5: asprintf(&buf, "%s $%x, X", os[a], x[1]); break;
case 7: asprintf(&buf, "%s $%x, X", os[a], x[1] | (x[2] << 8)); break;
}
return buf;
}
char * os[] = {"BPL", "BMI", "BVC", "BVS", "BCC", "BCS", "BNE", "BEQ"};
char* buf;
asprintf(&buf, "%s $%x", os[a], x[1]);
return buf;
}
if(c == 1) {
char * os[] = {"ORA", "AND", "EOR", "ADC", "STA", "LDA", "CMP", "SBC"};
char* buf;
switch(b) {
case 0: asprintf(&buf, "%s ($%x, X)", os[a], x[1]); break;
case 1: asprintf(&buf, "%s $%x", os[a], x[1]); break;
case 2: asprintf(&buf, "%s #$%x", os[a], x[1]); break;
case 3: asprintf(&buf, "%s $%x", os[a], x[1] | (x[2] << 8)); break;
case 4: asprintf(&buf, "%s ($%x, Y)", os[a], x[1]); break;
case 5: asprintf(&buf, "%s $%x, X", os[a], x[1]); break;
case 6: asprintf(&buf, "%s ($%x, Y)", os[a], x[1] | (x[2] << 8)); break;
case 7: asprintf(&buf, "%s ($%x, X)", os[a], x[1] | (x[2] << 8)); break;
}
return buf;
}
if(c == 2) {
char * os[] = {"ASL", "ROL", "LSR", "ROR", "STX", "LDX", "DEC", "INC"};
char* buf;
switch(b) {
case 0: asprintf(&buf, "%s #$%x", os[a], x[1]); break;
case 1: asprintf(&buf, "%s $%x", os[a], x[1]); break;
case 2: asprintf(&buf, "%s A", os[a]); break;
case 3: asprintf(&buf, "%s $%x", os[a], x[1] | (x[2] << 8)); break;
case 5: asprintf(&buf, "%s $%x, X", os[a], x[1]); break;
case 7: asprintf(&buf, "%s $%x, X", os[a], x[1] | (x[2] << 8)); break;
}
return buf;
}
return strdup("???");
}
|