cpu/c33: Reconstruct a few more assembler synthetics.

This commit is contained in:
Vas Crabb 2024-01-22 03:25:26 +11:00
parent dd4fded981
commit df57334883

View File

@ -4,7 +4,7 @@
Epson C33 disassembler
TODO:
* Only C33 ADV Core is currently supported - add support for C33 STD Core
* Only C33 ADV Core is currently supported - add support for C33 STD Core, C33 PE Core, etc.
* Reconstruct more assembler synthetics
* Should psrset and psrclr use symbolic names for bits?
* Should 32-bit extended displacements always be displayed as signed?
@ -106,54 +106,54 @@ std::tuple<char const *, bool, bool> const class_0_01_ops[32] = {
{ nullptr, false, false },
{ nullptr, false, false } };
char const *const class_0_jumps[16] = {
nullptr,
nullptr,
nullptr,
nullptr,
"jrgt%1$s 0x%2$x", // 000 0100
"jrge%1$s 0x%2$x", // 000 0101
"jrlt%1$s 0x%2$x", // 000 0110
"jrle%1$s 0x%2$x", // 000 0111
"jrugt%1$s 0x%2$x", // 000 1000
"jruge%1$s 0x%2$x", // 000 1001
"jrult%1$s 0x%2$x", // 000 1010
"jrule%1$s 0x%2$x", // 000 1011
"jreq%1$s 0x%2$x", // 000 1100
"jrne%1$s 0x%2$x", // 000 1101
"call%1$s 0x%2$x", // 000 1110
"jp%1$s 0x%2$x" }; // 000 1111
std::pair<char const *, char const *> const class_0_jumps[16] = {
{ nullptr, nullptr },
{ nullptr, nullptr },
{ nullptr, nullptr },
{ nullptr, nullptr },
{ "jrgt%1$s 0x%2$x", "xjrgt%1$s 0x%2$x" }, // 000 0100
{ "jrge%1$s 0x%2$x", "xjrge%1$s 0x%2$x" }, // 000 0101
{ "jrlt%1$s 0x%2$x", "xjrlt%1$s 0x%2$x" }, // 000 0110
{ "jrle%1$s 0x%2$x", "xjrle%1$s 0x%2$x" }, // 000 0111
{ "jrugt%1$s 0x%2$x", "xjrugt%1$s 0x%2$x" }, // 000 1000
{ "jruge%1$s 0x%2$x", "xjruge%1$s 0x%2$x" }, // 000 1001
{ "jrult%1$s 0x%2$x", "xjrult%1$s 0x%2$x" }, // 000 1010
{ "jrule%1$s 0x%2$x", "xjrule%1$s 0x%2$x" }, // 000 1011
{ "jreq%1$s 0x%2$x", "xjreq%1$s 0x%2$x" }, // 000 1100
{ "jrne%1$s 0x%2$x", "xjrne%1$s 0x%2$x" }, // 000 1101
{ "call%1$s 0x%2$x", "xcall%1$s 0x%2$x" }, // 000 1110
{ "jp%1$s 0x%2$x", "xjp%1$s 0x%2$x" } }; // 000 1111
std::pair<char const *, char const *> const class_1_ops[32] = {
{ "ld.b %%r%1$u,[%%r%2$u]", "ld.b %%r%1$u,[%%r%2$u + 0x%4$x]" }, // 001 000 00
{ "ld.b %%r%1$u,[%%r%2$u]", "xld.b %%r%1$u,[%%r%2$u + 0x%4$x]" }, // 001 000 00
{ "ld.b %%r%1$u,[%%r%2$u]+", nullptr }, // 001 000 01
{ "add %%r%1$u,%%r%2$u", nullptr }, // 001 000 10
{ "add %%r%1$u,%%r%2$u", "xadd %%r%1$u,%%r%2$u,0x%4$x" }, // 001 000 10
{ "srl %%r%1$u,%3$u", nullptr }, // 001 000 11
{ "ld.ub %%r%1$u,[%%r%2$u]", "ld.ub %%r%1$u,[%%r%2$u + 0x%4$x]" }, // 001 001 00
{ "ld.ub %%r%1$u,[%%r%2$u]", "xld.ub %%r%1$u,[%%r%2$u + 0x%4$x]" }, // 001 001 00
{ "ld.ub %%r%1$u,[%%r%2$u]+", nullptr }, // 001 001 01
{ "sub %%r%1$u,%%r%2$u", nullptr }, // 001 001 10
{ "sub %%r%1$u,%%r%2$u", "xsub %%r%1$u,%%r%2$u,0x%4$x" }, // 001 001 10
{ "sll %%r%1$u,%3$u", nullptr }, // 001 001 11
{ "ld.h %%r%1$u,[%%r%2$u]", "ld.h %%r%1$u,[%%r%2$u + 0x%4$x]" }, // 001 010 00
{ "ld.h %%r%1$u,[%%r%2$u]", "xld.h %%r%1$u,[%%r%2$u + 0x%4$x]" }, // 001 010 00
{ "ld.h %%r%1$u,[%%r%2$u]+", nullptr }, // 001 010 01
{ "cmp %%r%1$u,%%r%2$u", nullptr }, // 001 010 10
{ "sra %%r%1$u,%3$u", nullptr }, // 001 010 11
{ "ld.uh %%r%1$u,[%%r%2$u]", "ld.uh %%r%1$u,[%%r%2$u + 0x%4$x]" }, // 001 011 00
{ "ld.uh %%r%1$u,[%%r%2$u]", "xld.uh %%r%1$u,[%%r%2$u + 0x%4$x]" }, // 001 011 00
{ "ld.uh %%r%1$u,[%%r%2$u]+", nullptr }, // 001 011 01
{ "ld.w %%r%1$u,%%r%2$u", nullptr }, // 001 011 10
{ "sla %%r%1$u,%3$u", nullptr }, // 001 011 11
{ "ld.w %%r%1$u,[%%r%2$u]", "ld.w %%r%1$u,[%%r%2$u + 0x%4$x]" }, // 001 100 00
{ "ld.w %%r%1$u,[%%r%2$u]", "xld.w %%r%1$u,[%%r%2$u + 0x%4$x]" }, // 001 100 00
{ "ld.w %%r%1$u,[%%r%2$u]+", nullptr }, // 001 100 01
{ "and %%r%1$u,%%r%2$u", nullptr }, // 001 100 10
{ "and %%r%1$u,%%r%2$u", "xand %%r%1$u,%%r%2$u,0x%4$x" }, // 001 100 10
{ "rr %%r%1$u,%3$u", nullptr }, // 001 100 11
{ "ld.b [%%r%2$u],%%r%1$u", "ld.b [%%r%2$u + 0x%4$x],%%r%1$u" }, // 001 101 00
{ "ld.b [%%r%2$u],%%r%1$u", "xld.b [%%r%2$u + 0x%4$x],%%r%1$u" }, // 001 101 00
{ "ld.b [%%r%2$u]+,%%r%1$u", nullptr }, // 001 101 01
{ "or %%r%1$u,%%r%2$u", nullptr }, // 001 101 10
{ "or %%r%1$u,%%r%2$u", "xoor %%r%1$u,%%r%2$u,0x%4$x" }, // 001 101 10
{ "rl %%r%1$u,%3$u", nullptr }, // 001 101 11
{ "ld.h [%%r%2$u],%%r%1$u", "ld.h [%%r%2$u + 0x%4$x],%%r%1$u" }, // 001 110 00
{ "ld.h [%%r%2$u],%%r%1$u", "xld.h [%%r%2$u + 0x%4$x],%%r%1$u" }, // 001 110 00
{ "ld.h [%%r%2$u]+,%%r%1$u", nullptr }, // 001 110 01
{ "xor %%r%1$u,%%r%2$u", nullptr }, // 001 110 10
{ "xor %%r%1$u,%%r%2$u", "xxor %%r%1$u,%%r%2$u,0x%4$x" }, // 001 110 10
{ nullptr, nullptr },
{ "ld.w [%%r%2$u],%%r%1$u", "ld.w [%%r%2$u + 0x%4$x],%%r%1$u" }, // 001 111 00
{ "ld.w [%%r%2$u],%%r%1$u", "xld.w [%%r%2$u + 0x%4$x],%%r%1$u" }, // 001 111 00
{ "ld.w [%%r%2$u]+,%%r%1$u", nullptr }, // 001 111 01
{ "not %%r%1$u,%%r%2$u", nullptr }, // 001 111 10
{ nullptr, nullptr } };
@ -188,23 +188,23 @@ std::pair<char const *, bool> class_1_ext_3[4] = {
{ "ext %%r%1$u,srl,%2$u", false },
{ "ext %%r%1$u,sll,%2$u", false } };
std::pair<char const *, unsigned> const class_2_3_ops[16] = {
{ "ld.b %%r%1$u,[%%sp + 0x%2$x]", 1 }, // 010 000
{ "ld.ub %%r%1$u,[%%sp + 0x%2$x]", 1 }, // 010 001
{ "ld.h %%r%1$u,[%%sp + 0x%2$x]", 2 }, // 010 010
{ "ld.uh %%r%1$u,[%%sp + 0x%2$x]", 2 }, // 010 011
{ "ld.w %%r%1$u,[%%sp + 0x%2$x]", 4 }, // 010 100
{ "ld.b [%%sp + 0x%2$x],%%r%1$u", 1 }, // 010 101
{ "ld.h [%%sp + 0x%2$x],%%r%1$u", 2 }, // 010 110
{ "ld.w [%%sp + 0x%2$x],%%r%1$u", 4 }, // 010 111
{ "add %%r%1$u,0x%2$x", 1 }, // 011 000
{ "sub %%r%1$u,0x%2$x", 1 }, // 011 001
{ "cmp %%r%1$u,%5$s0x%4$x", 1 }, // 011 010
{ "ld.w %%r%1$u,%5$s0x%4$x", 1 }, // 011 011
{ "and %%r%1$u,0x%3$x", 1 }, // 011 100
{ "or %%r%1$u,0x%3$x", 1 }, // 011 101
{ "xor %%r%1$u,0x%3$x", 1 }, // 011 110
{ "not %%r%1$u,0x%3$x", 1 } }; // 011 111
std::tuple<char const *, char const *, unsigned> const class_2_3_ops[16] = {
{ "ld.b %%r%1$u,[%%sp + 0x%2$x]", "xld.b %%r%1$u,[%%sp + 0x%2$x]",1 }, // 010 000
{ "ld.ub %%r%1$u,[%%sp + 0x%2$x]", "xld.ub %%r%1$u,[%%sp + 0x%2$x]",1 }, // 010 001
{ "ld.h %%r%1$u,[%%sp + 0x%2$x]", "xld.h %%r%1$u,[%%sp + 0x%2$x]",2 }, // 010 010
{ "ld.uh %%r%1$u,[%%sp + 0x%2$x]", "xld.uh %%r%1$u,[%%sp + 0x%2$x]",2 }, // 010 011
{ "ld.w %%r%1$u,[%%sp + 0x%2$x]", "xld.w %%r%1$u,[%%sp + 0x%2$x]",4 }, // 010 100
{ "ld.b [%%sp + 0x%2$x],%%r%1$u", "xld.b [%%sp + 0x%2$x],%%r%1$u",1 }, // 010 101
{ "ld.h [%%sp + 0x%2$x],%%r%1$u", "xld.h [%%sp + 0x%2$x],%%r%1$u",2 }, // 010 110
{ "ld.w [%%sp + 0x%2$x],%%r%1$u", "xld.w [%%sp + 0x%2$x],%%r%1$u",4 }, // 010 111
{ "add %%r%1$u,0x%2$x", "xadd %%r%1$u,0x%2$x", 1 }, // 011 000
{ "sub %%r%1$u,0x%2$x", "xsub %%r%1$u,0x%2$x", 1 }, // 011 001
{ "cmp %%r%1$u,%5$s0x%4$x", "xcmp %%r%1$u,%5$s0x%4$x", 1 }, // 011 010
{ "ld.w %%r%1$u,%5$s0x%4$x", "xld.w %%r%1$u,%5$s0x%4$x", 1 }, // 011 011
{ "and %%r%1$u,0x%3$x", "xand %%r%1$u,0x%3$x", 1 }, // 011 100
{ "or %%r%1$u,0x%3$x", "xoor %%r%1$u,0x%3$x", 1 }, // 011 101
{ "xor %%r%1$u,0x%3$x", "xxor %%r%1$u,0x%3$x", 1 }, // 011 110
{ "not %%r%1$u,0x%3$x", "xnot %%r%1$u,0x%3$x", 1 } }; // 011 111
std::pair<char const *, bool> const class_4_ops[32] = {
{ nullptr, false },
@ -249,19 +249,19 @@ std::tuple<char const *, char const *, unsigned, unsigned> const class_5_ops[32]
{ "ld.ub %%r%1$u,%%r%2$u", nullptr, 4, 0 }, // 101 001 01
{ "mltu.h %%r%1$u,%%r%2$u", nullptr, 4, 0 }, // 101 001 10
{ "mac1.h %%r%1$u,%%r%2$u", nullptr, 4, 0 }, // 101 001 11
{ "btst [%%r%2$u],%1$u", "btst [%%r%2$u + 0x%3$x],%1$u", 3, 0 }, // 101 010 00
{ "btst [%%r%2$u],%1$u", "xbtst [%%r%2$u + 0x%3$x],%1$u", 3, 0 }, // 101 010 00
{ "ld.h %%r%1$u,%%r%2$u", nullptr, 4, 0 }, // 101 010 01
{ "mlt.w %%r%1$u,%%r%2$u", nullptr, 4, 0 }, // 101 010 10
{ "mac1.hw %%r%1$u,%%r%2$u", nullptr, 4, 0 }, // 101 010 11
{ "bclr [%%r%2$u],%1$u", "bclr [%%r%2$u + 0x%3$x],%1$u", 3, 0 }, // 101 011 00
{ "bclr [%%r%2$u],%1$u", "xbclr [%%r%2$u + 0x%3$x],%1$u", 3, 0 }, // 101 011 00
{ "ld.uh %%r%1$u,%%r%2$u", nullptr, 4, 0 }, // 101 011 01
{ "mltu.w %%r%1$u,%%r%2$u", nullptr, 4, 0 }, // 101 011 10
{ nullptr, nullptr, 0, 0 },
{ "bset [%%r%2$u],%1$u", "bset [%%r%2$u + 0x%3$x],%1$u", 3, 0 }, // 101 100 00
{ "bset [%%r%2$u],%1$u", "xbset [%%r%2$u + 0x%3$x],%1$u", 3, 0 }, // 101 100 00
{ "ld.c %%r%1$u,0x%2$x", nullptr, 4, 0 }, // 101 100 01
{ "mac %%r%2$u", nullptr, 0, 0 }, // 101 100 10
{ "mac1.w %%r%1$u,%%r%2$u", nullptr, 4, 0 }, // 101 100 11
{ "bnot [%%r%2$u],%1$u", "bnot [%%r%2$u + 0x%3$x],%1$u", 3, 0 }, // 101 101 00
{ "bnot [%%r%2$u],%1$u", "xbnot [%%r%2$u + 0x%3$x],%1$u", 3, 0 }, // 101 101 00
{ "ld.c 0x%2$x,%%r%1$u", nullptr, 4, 0 }, // 101 101 01
{ "sat.h %%r%1$u,%%r%2$u", nullptr, 4, 0 }, // 101 101 10
{ "sat.uh %%r%1$u,%%r%2$u", nullptr, 4, 0 }, // 101 101 11
@ -274,15 +274,15 @@ std::tuple<char const *, char const *, unsigned, unsigned> const class_5_ops[32]
{ "sat.uw %%r%1$u,%%r%2$u", nullptr, 4, 0 }, // 101 111 10
{ nullptr, nullptr, 0, 0 } };
std::pair<char const *, unsigned> const class_7_ops[8] = {
{ "ld.b %%r%1$u,[%%dp + 0x%2$x]", 1 }, // 111 000
{ "ld.ub %%r%1$u,[%%dp + 0x%2$x]", 1 }, // 111 001
{ "ld.h %%r%1$u,[%%dp + 0x%2$x]", 2 }, // 111 010
{ "ld.uh %%r%1$u,[%%dp + 0x%2$x]", 2 }, // 111 011
{ "ld.w %%r%1$u,[%%dp + 0x%2$x]", 4 }, // 111 100
{ "ld.b [%%dp + 0x%2$x],%%r%1$u", 1 }, // 111 101
{ "ld.h [%%dp + 0x%2$x],%%r%1$u", 2 }, // 111 110
{ "ld.w [%%dp + 0x%2$x],%%r%1$u", 4 } }; // 111 111
std::tuple<char const *, char const *, unsigned> const class_7_ops[8] = {
{ "ld.b %%r%1$u,[%%dp + 0x%2$x]", "xld.b %%r%1$u,[%%dp + 0x%2$x]", 1 }, // 111 000
{ "ld.ub %%r%1$u,[%%dp + 0x%2$x]", "xld.ub %%r%1$u,[%%dp + 0x%2$x]", 1 }, // 111 001
{ "ld.h %%r%1$u,[%%dp + 0x%2$x]", "xld.h %%r%1$u,[%%dp + 0x%2$x]", 2 }, // 111 010
{ "ld.uh %%r%1$u,[%%dp + 0x%2$x]", "xld.uh %%r%1$u,[%%dp + 0x%2$x]", 2 }, // 111 011
{ "ld.w %%r%1$u,[%%dp + 0x%2$x]", "xld.w %%r%1$u,[%%dp + 0x%2$x]", 4 }, // 111 100
{ "ld.b [%%dp + 0x%2$x],%%r%1$u", "xld.b [%%dp + 0x%2$x],%%r%1$u", 1 }, // 111 101
{ "ld.h [%%dp + 0x%2$x],%%r%1$u", "xld.h [%%dp + 0x%2$x],%%r%1$u", 2 }, // 111 110
{ "ld.w [%%dp + 0x%2$x],%%r%1$u", "xld.w [%%dp + 0x%2$x],%%r%1$u", 4 } }; // 111 111
} // anonymous namespace
@ -405,7 +405,8 @@ offs_t c33_disassembler::dasm_class_0(std::ostream &stream, offs_t pc, u16 op, u
else if (1 == ext_count)
imm = util::sext(imm, 22);
util::stream_format(stream, class_0_jumps[BIT(op, 9, 4)], BIT(op, 8) ? ".d" : " ", pc + (ext_count * 2) + imm);
auto const [inst, inst_ext] = class_0_jumps[BIT(op, 9, 5)];
util::stream_format(stream, ext_count ? inst_ext : inst, BIT(op, 8) ? ".d" : " ", pc + (ext_count * 2) + imm);
return 2 + (ext_count * 2);
}
}
@ -475,7 +476,7 @@ offs_t c33_disassembler::dasm_class_1(std::ostream &stream, u16 op, u32 ext_imm,
offs_t c33_disassembler::dasm_class_2_3(std::ostream &stream, u16 op, u32 ext_imm, unsigned ext_count) const
{
auto const [inst, mul] = class_2_3_ops[BIT(op, 10, 4)];
auto const [inst, inst_ext, mul] = class_2_3_ops[BIT(op, 10, 4)];
u8 const reg = BIT(op, 0, 4);
u32 imm = (ext_imm << 6) | BIT(op, 4, 6);
@ -488,7 +489,7 @@ offs_t c33_disassembler::dasm_class_2_3(std::ostream &stream, u16 op, u32 ext_im
simm *= mul;
abs *= mul;
}
util::stream_format(stream, inst, reg, imm, simm, abs, sign);
util::stream_format(stream, ext_count ? inst_ext : inst, reg, imm, simm, abs, sign);
return 2 + (ext_count * 2);
}
@ -576,13 +577,13 @@ offs_t c33_disassembler::dasm_class_6(std::ostream &stream, u16 op, u32 ext_imm,
offs_t c33_disassembler::dasm_class_7(std::ostream &stream, u16 op, u32 ext_imm, unsigned ext_count) const
{
auto const [inst, mul] = class_7_ops[BIT(op, 10, 3)];
auto const [inst, inst_ext, mul] = class_7_ops[BIT(op, 10, 3)];
u8 const reg = BIT(op, 0, 4);
u32 imm = (ext_imm << 6) | BIT(op, 4, 6);
if (!ext_count)
imm *= mul;
util::stream_format(stream, inst, reg, imm);
util::stream_format(stream, ext_count ? inst_ext : inst, reg, imm);
return 2 + (ext_count * 2);
}