Update to v101r20 release.

byuu says:

Changelog:
- Z80: emulated 272 new instructions
- hiro/GTK: fixed v101r19 Linux regression [thanks, SuperMikeMan!]
This commit is contained in:
Tim Allen 2016-10-29 11:33:30 +11:00
parent f3e67da937
commit 2707c5316d
7 changed files with 1004 additions and 14 deletions

View File

@ -12,7 +12,7 @@ using namespace nall;
namespace Emulator { namespace Emulator {
static const string Name = "higan"; static const string Name = "higan";
static const string Version = "101.19"; static const string Version = "101.20";
static const string Author = "byuu"; static const string Author = "byuu";
static const string License = "GPLv3"; static const string License = "GPLv3";
static const string Website = "http://byuu.org/"; static const string Website = "http://byuu.org/";

View File

@ -309,21 +309,328 @@ auto Z80::disassemble__(uint16 pc, uint8 prefix, uint8 code) -> string {
} }
auto Z80::disassembleCB(uint16 pc, uint8 prefix, uint8 code) -> string { auto Z80::disassembleCB(uint16 pc, uint8 prefix, uint8 code) -> string {
auto read = [&] { return bus->read(pc++); }; auto byte = [&] {
return bus->read(pc++);
};
auto word = [&] {
uint16 data = byte() << 0;
return data | byte() << 8;
};
auto branch = [&] {
auto d = byte();
return pc + (int8)d;
};
auto displace = [&] {
if(!prefix) return string{};
auto d = (int8)byte();
return d >= 0 ? string{"+$", hex(d, 2L)} : string{"-$", hex(-d, 2L)};
};
switch(code) { switch(code) {
op(0x00, "rlc ", B)
op(0x01, "rlc ", C)
op(0x02, "rlc ", D)
op(0x03, "rlc ", E)
op(0x04, "rlc ", H)
op(0x05, "rlc ", L)
op(0x06, "rlc ", IHL)
op(0x07, "rlc ", A)
op(0x08, "rrc ", B)
op(0x09, "rrc ", C)
op(0x0a, "rrc ", D)
op(0x0b, "rrc ", E)
op(0x0c, "rrc ", H)
op(0x0d, "rrc ", L)
op(0x0e, "rrc ", IHL)
op(0x0f, "rrc ", A)
op(0x10, "rl ", B)
op(0x11, "rl ", C)
op(0x12, "rl ", D)
op(0x13, "rl ", E)
op(0x14, "rl ", H)
op(0x15, "rl ", L)
op(0x16, "rl ", IHL)
op(0x17, "rl ", A)
op(0x18, "rr ", B)
op(0x19, "rr ", C)
op(0x1a, "rr ", D)
op(0x1b, "rr ", E)
op(0x1c, "rr ", H)
op(0x1d, "rr ", L)
op(0x1e, "rr ", IHL)
op(0x1f, "rr ", A)
op(0x20, "sla ", B)
op(0x21, "sla ", C)
op(0x22, "sla ", D)
op(0x23, "sla ", E)
op(0x24, "sla ", H)
op(0x25, "sla ", L)
op(0x26, "sla ", IHL)
op(0x27, "sla ", A)
op(0x28, "sra ", B)
op(0x29, "sra ", C)
op(0x2a, "sra ", D)
op(0x2b, "sra ", E)
op(0x2c, "sra ", H)
op(0x2d, "sra ", L)
op(0x2e, "sra ", IHL)
op(0x2f, "sra ", A)
op(0x30, "sll ", B)
op(0x31, "sll ", C)
op(0x32, "sll ", D)
op(0x33, "sll ", E)
op(0x34, "sll ", H)
op(0x35, "sll ", L)
op(0x36, "sll ", IHL)
op(0x37, "sll ", A)
op(0x38, "srl ", B)
op(0x39, "srl ", C)
op(0x3a, "srl ", D)
op(0x3b, "srl ", E)
op(0x3c, "srl ", H)
op(0x3d, "srl ", L)
op(0x3e, "srl ", IHL)
op(0x3f, "srl ", A)
op(0x40, "bit ", "0,", B)
op(0x41, "bit ", "0,", C)
op(0x42, "bit ", "0,", D)
op(0x43, "bit ", "0,", E)
op(0x44, "bit ", "0,", H)
op(0x45, "bit ", "0,", L)
op(0x46, "bit ", "0,", IHL)
op(0x47, "bit ", "0,", A)
op(0x48, "bit ", "1,", B)
op(0x49, "bit ", "1,", C)
op(0x4a, "bit ", "1,", D)
op(0x4b, "bit ", "1,", E)
op(0x4c, "bit ", "1,", H)
op(0x4d, "bit ", "1,", L)
op(0x4e, "bit ", "1,", IHL)
op(0x4f, "bit ", "1,", A)
op(0x50, "bit ", "2,", B)
op(0x51, "bit ", "2,", C)
op(0x52, "bit ", "2,", D)
op(0x53, "bit ", "2,", E)
op(0x54, "bit ", "2,", H)
op(0x55, "bit ", "2,", L)
op(0x56, "bit ", "2,", IHL)
op(0x57, "bit ", "2,", A)
op(0x58, "bit ", "3,", B)
op(0x59, "bit ", "3,", C)
op(0x5a, "bit ", "3,", D)
op(0x5b, "bit ", "3,", E)
op(0x5c, "bit ", "3,", H)
op(0x5d, "bit ", "3,", L)
op(0x5e, "bit ", "3,", IHL)
op(0x5f, "bit ", "3,", A)
op(0x60, "bit ", "4,", B)
op(0x61, "bit ", "4,", C)
op(0x62, "bit ", "4,", D)
op(0x63, "bit ", "4,", E)
op(0x64, "bit ", "4,", H)
op(0x65, "bit ", "4,", L)
op(0x66, "bit ", "4,", IHL)
op(0x67, "bit ", "4,", A)
op(0x68, "bit ", "5,", B)
op(0x69, "bit ", "5,", C)
op(0x6a, "bit ", "5,", D)
op(0x6b, "bit ", "5,", E)
op(0x6c, "bit ", "5,", H)
op(0x6d, "bit ", "5,", L)
op(0x6e, "bit ", "5,", IHL)
op(0x6f, "bit ", "5,", A)
op(0x70, "bit ", "6,", B)
op(0x71, "bit ", "6,", C)
op(0x72, "bit ", "6,", D)
op(0x73, "bit ", "6,", E)
op(0x74, "bit ", "6,", H)
op(0x75, "bit ", "6,", L)
op(0x76, "bit ", "6,", IHL)
op(0x77, "bit ", "6,", A)
op(0x78, "bit ", "7,", B)
op(0x79, "bit ", "7,", C)
op(0x7a, "bit ", "7,", D)
op(0x7b, "bit ", "7,", E)
op(0x7c, "bit ", "7,", H)
op(0x7d, "bit ", "7,", L)
op(0x7e, "bit ", "7,", IHL)
op(0x7f, "bit ", "7,", A)
op(0x80, "res ", "0,", B)
op(0x81, "res ", "0,", C)
op(0x82, "res ", "0,", D)
op(0x83, "res ", "0,", E)
op(0x84, "res ", "0,", H)
op(0x85, "res ", "0,", L)
op(0x86, "res ", "0,", IHL)
op(0x87, "res ", "0,", A)
op(0x88, "res ", "1,", B)
op(0x89, "res ", "1,", C)
op(0x8a, "res ", "1,", D)
op(0x8b, "res ", "1,", E)
op(0x8c, "res ", "1,", H)
op(0x8d, "res ", "1,", L)
op(0x8e, "res ", "1,", IHL)
op(0x8f, "res ", "1,", A)
op(0x90, "res ", "2,", B)
op(0x91, "res ", "2,", C)
op(0x92, "res ", "2,", D)
op(0x93, "res ", "2,", E)
op(0x94, "res ", "2,", H)
op(0x95, "res ", "2,", L)
op(0x96, "res ", "2,", IHL)
op(0x97, "res ", "2,", A)
op(0x98, "res ", "3,", B)
op(0x99, "res ", "3,", C)
op(0x9a, "res ", "3,", D)
op(0x9b, "res ", "3,", E)
op(0x9c, "res ", "3,", H)
op(0x9d, "res ", "3,", L)
op(0x9e, "res ", "3,", IHL)
op(0x9f, "res ", "3,", A)
op(0xa0, "res ", "4,", B)
op(0xa1, "res ", "4,", C)
op(0xa2, "res ", "4,", D)
op(0xa3, "res ", "4,", E)
op(0xa4, "res ", "4,", H)
op(0xa5, "res ", "4,", L)
op(0xa6, "res ", "4,", IHL)
op(0xa7, "res ", "4,", A)
op(0xa8, "res ", "5,", B)
op(0xa9, "res ", "5,", C)
op(0xaa, "res ", "5,", D)
op(0xab, "res ", "5,", E)
op(0xac, "res ", "5,", H)
op(0xad, "res ", "5,", L)
op(0xae, "res ", "5,", IHL)
op(0xaf, "res ", "5,", A)
op(0xb0, "res ", "6,", B)
op(0xb1, "res ", "6,", C)
op(0xb2, "res ", "6,", D)
op(0xb3, "res ", "6,", E)
op(0xb4, "res ", "6,", H)
op(0xb5, "res ", "6,", L)
op(0xb6, "res ", "6,", IHL)
op(0xb7, "res ", "6,", A)
op(0xb8, "res ", "7,", B)
op(0xb9, "res ", "7,", C)
op(0xba, "res ", "7,", D)
op(0xbb, "res ", "7,", E)
op(0xbc, "res ", "7,", H)
op(0xbd, "res ", "7,", L)
op(0xbe, "res ", "7,", IHL)
op(0xbf, "res ", "7,", A)
op(0xc0, "set ", "0,", B)
op(0xc1, "set ", "0,", C)
op(0xc2, "set ", "0,", D)
op(0xc3, "set ", "0,", E)
op(0xc4, "set ", "0,", H)
op(0xc5, "set ", "0,", L)
op(0xc6, "set ", "0,", IHL)
op(0xc7, "set ", "0,", A)
op(0xc8, "set ", "1,", B)
op(0xc9, "set ", "1,", C)
op(0xca, "set ", "1,", D)
op(0xcb, "set ", "1,", E)
op(0xcc, "set ", "1,", H)
op(0xcd, "set ", "1,", L)
op(0xce, "set ", "1,", IHL)
op(0xcf, "set ", "1,", A)
op(0xd0, "set ", "2,", B)
op(0xd1, "set ", "2,", C)
op(0xd2, "set ", "2,", D)
op(0xd3, "set ", "2,", E)
op(0xd4, "set ", "2,", H)
op(0xd5, "set ", "2,", L)
op(0xd6, "set ", "2,", IHL)
op(0xd7, "set ", "2,", A)
op(0xd8, "set ", "3,", B)
op(0xd9, "set ", "3,", C)
op(0xda, "set ", "3,", D)
op(0xdb, "set ", "3,", E)
op(0xdc, "set ", "3,", H)
op(0xdd, "set ", "3,", L)
op(0xde, "set ", "3,", IHL)
op(0xdf, "set ", "3,", A)
op(0xe0, "set ", "4,", B)
op(0xe1, "set ", "4,", C)
op(0xe2, "set ", "4,", D)
op(0xe3, "set ", "4,", E)
op(0xe4, "set ", "4,", H)
op(0xe5, "set ", "4,", L)
op(0xe6, "set ", "4,", IHL)
op(0xe7, "set ", "4,", A)
op(0xe8, "set ", "5,", B)
op(0xe9, "set ", "5,", C)
op(0xea, "set ", "5,", D)
op(0xeb, "set ", "5,", E)
op(0xec, "set ", "5,", H)
op(0xed, "set ", "5,", L)
op(0xee, "set ", "5,", IHL)
op(0xef, "set ", "5,", A)
op(0xf0, "set ", "6,", B)
op(0xf1, "set ", "6,", C)
op(0xf2, "set ", "6,", D)
op(0xf3, "set ", "6,", E)
op(0xf4, "set ", "6,", H)
op(0xf5, "set ", "6,", L)
op(0xf6, "set ", "6,", IHL)
op(0xf7, "set ", "6,", A)
op(0xf8, "set ", "7,", B)
op(0xf9, "set ", "7,", C)
op(0xfa, "set ", "7,", D)
op(0xfb, "set ", "7,", E)
op(0xfc, "set ", "7,", H)
op(0xfd, "set ", "7,", L)
op(0xfe, "set ", "7,", IHL)
op(0xff, "set ", "7,", A)
} }
unreachable;
return {"???: cb ", hex(code, 2L)};
} }
auto Z80::disassembleED(uint16 pc, uint8 prefix, uint8 code) -> string { auto Z80::disassembleED(uint16 pc, uint8 prefix, uint8 code) -> string {
auto read = [&] { return bus->read(pc++); }; auto byte = [&] {
return bus->read(pc++);
};
auto word = [&] {
uint16 data = byte() << 0;
return data | byte() << 8;
};
auto branch = [&] {
auto d = byte();
return pc + (int8)d;
};
auto displace = [&] {
if(!prefix) return string{};
auto d = (int8)byte();
return d >= 0 ? string{"+$", hex(d, 2L)} : string{"-$", hex(-d, 2L)};
};
switch(code) { switch(code) {
op(0x46, "im ", "0") op(0x46, "im ", "0")
op(0x56, "im ", "1") op(0x56, "im ", "1")
op(0x5e, "im ", "2") op(0x5e, "im ", "2")
op(0xa0, "ldi ")
op(0xa1, "cpi ")
op(0xa2, "ini ")
op(0xa3, "outi")
op(0xa8, "ldd ")
op(0xa9, "cpd ")
op(0xaa, "ind ")
op(0xab, "outd")
op(0xb0, "ldir")
op(0xb1, "cpir")
op(0xb2, "inir")
op(0xb3, "otir")
op(0xb8, "lddr")
op(0xb9, "cpdr")
op(0xba, "indr")
op(0xbb, "otdr")
} }
return {"???: ed ", hex(code, 2L)}; return {"???: ed ", hex(code, 2L)};

View File

@ -236,9 +236,263 @@ auto Z80::instruction__(uint8 code) -> void {
auto Z80::instructionCB(uint8 code) -> void { auto Z80::instructionCB(uint8 code) -> void {
switch(code) { switch(code) {
op(0x00, RLC_r, B)
op(0x01, RLC_r, C)
op(0x02, RLC_r, D)
op(0x03, RLC_r, E)
op(0x04, RLC_r, H)
op(0x05, RLC_r, L)
op(0x06, RLC_irr, HL)
op(0x07, RLC_r, A)
op(0x08, RRC_r, B)
op(0x09, RRC_r, C)
op(0x0a, RRC_r, D)
op(0x0b, RRC_r, E)
op(0x0c, RRC_r, H)
op(0x0d, RRC_r, L)
op(0x0e, RRC_irr, HL)
op(0x0f, RRC_r, A)
op(0x10, RL_r, B)
op(0x11, RL_r, C)
op(0x12, RL_r, D)
op(0x13, RL_r, E)
op(0x14, RL_r, H)
op(0x15, RL_r, L)
op(0x16, RL_irr, HL)
op(0x17, RL_r, A)
op(0x18, RR_r, B)
op(0x19, RR_r, C)
op(0x1a, RR_r, D)
op(0x1b, RR_r, E)
op(0x1c, RR_r, H)
op(0x1d, RR_r, L)
op(0x1e, RR_irr, HL)
op(0x1f, RR_r, A)
op(0x20, SLA_r, B)
op(0x21, SLA_r, C)
op(0x22, SLA_r, D)
op(0x23, SLA_r, E)
op(0x24, SLA_r, H)
op(0x25, SLA_r, L)
op(0x26, SLA_irr, HL)
op(0x27, SLA_r, A)
op(0x28, SRA_r, B)
op(0x29, SRA_r, C)
op(0x2a, SRA_r, D)
op(0x2b, SRA_r, E)
op(0x2c, SRA_r, H)
op(0x2d, SRA_r, L)
op(0x2e, SRA_irr, HL)
op(0x2f, SRA_r, A)
op(0x30, SLL_r, B)
op(0x31, SLL_r, C)
op(0x32, SLL_r, D)
op(0x33, SLL_r, E)
op(0x34, SLL_r, H)
op(0x35, SLL_r, L)
op(0x36, SLL_irr, HL)
op(0x37, SLL_r, A)
op(0x38, SRL_r, B)
op(0x39, SRL_r, C)
op(0x3a, SRL_r, D)
op(0x3b, SRL_r, E)
op(0x3c, SRL_r, H)
op(0x3d, SRL_r, L)
op(0x3e, SRL_irr, HL)
op(0x3f, SRL_r, A)
op(0x40, BIT_o_r, 0, B)
op(0x41, BIT_o_r, 0, C)
op(0x42, BIT_o_r, 0, D)
op(0x43, BIT_o_r, 0, E)
op(0x44, BIT_o_r, 0, H)
op(0x45, BIT_o_r, 0, L)
op(0x46, BIT_o_irr, 0, HL)
op(0x47, BIT_o_r, 0, A)
op(0x48, BIT_o_r, 1, B)
op(0x49, BIT_o_r, 1, C)
op(0x4a, BIT_o_r, 1, D)
op(0x4b, BIT_o_r, 1, E)
op(0x4c, BIT_o_r, 1, H)
op(0x4d, BIT_o_r, 1, L)
op(0x4e, BIT_o_irr, 1, HL)
op(0x4f, BIT_o_r, 1, A)
op(0x50, BIT_o_r, 2, B)
op(0x51, BIT_o_r, 2, C)
op(0x52, BIT_o_r, 2, D)
op(0x53, BIT_o_r, 2, E)
op(0x54, BIT_o_r, 2, H)
op(0x55, BIT_o_r, 2, L)
op(0x56, BIT_o_irr, 2, HL)
op(0x57, BIT_o_r, 2, A)
op(0x58, BIT_o_r, 3, B)
op(0x59, BIT_o_r, 3, C)
op(0x5a, BIT_o_r, 3, D)
op(0x5b, BIT_o_r, 3, E)
op(0x5c, BIT_o_r, 3, H)
op(0x5d, BIT_o_r, 3, L)
op(0x5e, BIT_o_irr, 3, HL)
op(0x5f, BIT_o_r, 3, A)
op(0x60, BIT_o_r, 4, B)
op(0x61, BIT_o_r, 4, C)
op(0x62, BIT_o_r, 4, D)
op(0x63, BIT_o_r, 4, E)
op(0x64, BIT_o_r, 4, H)
op(0x65, BIT_o_r, 4, L)
op(0x66, BIT_o_irr, 4, HL)
op(0x67, BIT_o_r, 4, A)
op(0x68, BIT_o_r, 5, B)
op(0x69, BIT_o_r, 5, C)
op(0x6a, BIT_o_r, 5, D)
op(0x6b, BIT_o_r, 5, E)
op(0x6c, BIT_o_r, 5, H)
op(0x6d, BIT_o_r, 5, L)
op(0x6e, BIT_o_irr, 5, HL)
op(0x6f, BIT_o_r, 5, A)
op(0x70, BIT_o_r, 6, B)
op(0x71, BIT_o_r, 6, C)
op(0x72, BIT_o_r, 6, D)
op(0x73, BIT_o_r, 6, E)
op(0x74, BIT_o_r, 6, H)
op(0x75, BIT_o_r, 6, L)
op(0x76, BIT_o_irr, 6, HL)
op(0x77, BIT_o_r, 6, A)
op(0x78, BIT_o_r, 7, B)
op(0x79, BIT_o_r, 7, C)
op(0x7a, BIT_o_r, 7, D)
op(0x7b, BIT_o_r, 7, E)
op(0x7c, BIT_o_r, 7, H)
op(0x7d, BIT_o_r, 7, L)
op(0x7e, BIT_o_irr, 7, HL)
op(0x7f, BIT_o_r, 7, A)
op(0x80, RES_o_r, 0, B)
op(0x81, RES_o_r, 0, C)
op(0x82, RES_o_r, 0, D)
op(0x83, RES_o_r, 0, E)
op(0x84, RES_o_r, 0, H)
op(0x85, RES_o_r, 0, L)
op(0x86, RES_o_irr, 0, HL)
op(0x87, RES_o_r, 0, A)
op(0x88, RES_o_r, 1, B)
op(0x89, RES_o_r, 1, C)
op(0x8a, RES_o_r, 1, D)
op(0x8b, RES_o_r, 1, E)
op(0x8c, RES_o_r, 1, H)
op(0x8d, RES_o_r, 1, L)
op(0x8e, RES_o_irr, 1, HL)
op(0x8f, RES_o_r, 1, A)
op(0x90, RES_o_r, 2, B)
op(0x91, RES_o_r, 2, C)
op(0x92, RES_o_r, 2, D)
op(0x93, RES_o_r, 2, E)
op(0x94, RES_o_r, 2, H)
op(0x95, RES_o_r, 2, L)
op(0x96, RES_o_irr, 2, HL)
op(0x97, RES_o_r, 2, A)
op(0x98, RES_o_r, 3, B)
op(0x99, RES_o_r, 3, C)
op(0x9a, RES_o_r, 3, D)
op(0x9b, RES_o_r, 3, E)
op(0x9c, RES_o_r, 3, H)
op(0x9d, RES_o_r, 3, L)
op(0x9e, RES_o_irr, 3, HL)
op(0x9f, RES_o_r, 3, A)
op(0xa0, RES_o_r, 4, B)
op(0xa1, RES_o_r, 4, C)
op(0xa2, RES_o_r, 4, D)
op(0xa3, RES_o_r, 4, E)
op(0xa4, RES_o_r, 4, H)
op(0xa5, RES_o_r, 4, L)
op(0xa6, RES_o_irr, 4, HL)
op(0xa7, RES_o_r, 4, A)
op(0xa8, RES_o_r, 5, B)
op(0xa9, RES_o_r, 5, C)
op(0xaa, RES_o_r, 5, D)
op(0xab, RES_o_r, 5, E)
op(0xac, RES_o_r, 5, H)
op(0xad, RES_o_r, 5, L)
op(0xae, RES_o_irr, 5, HL)
op(0xaf, RES_o_r, 5, A)
op(0xb0, RES_o_r, 6, B)
op(0xb1, RES_o_r, 6, C)
op(0xb2, RES_o_r, 6, D)
op(0xb3, RES_o_r, 6, E)
op(0xb4, RES_o_r, 6, H)
op(0xb5, RES_o_r, 6, L)
op(0xb6, RES_o_irr, 6, HL)
op(0xb7, RES_o_r, 6, A)
op(0xb8, RES_o_r, 7, B)
op(0xb9, RES_o_r, 7, C)
op(0xba, RES_o_r, 7, D)
op(0xbb, RES_o_r, 7, E)
op(0xbc, RES_o_r, 7, H)
op(0xbd, RES_o_r, 7, L)
op(0xbe, RES_o_irr, 7, HL)
op(0xbf, RES_o_r, 7, A)
op(0xc0, SET_o_r, 0, B)
op(0xc1, SET_o_r, 0, C)
op(0xc2, SET_o_r, 0, D)
op(0xc3, SET_o_r, 0, E)
op(0xc4, SET_o_r, 0, H)
op(0xc5, SET_o_r, 0, L)
op(0xc6, SET_o_irr, 0, HL)
op(0xc7, SET_o_r, 0, A)
op(0xc8, SET_o_r, 1, B)
op(0xc9, SET_o_r, 1, C)
op(0xca, SET_o_r, 1, D)
op(0xcb, SET_o_r, 1, E)
op(0xcc, SET_o_r, 1, H)
op(0xcd, SET_o_r, 1, L)
op(0xce, SET_o_irr, 1, HL)
op(0xcf, SET_o_r, 1, A)
op(0xd0, SET_o_r, 2, B)
op(0xd1, SET_o_r, 2, C)
op(0xd2, SET_o_r, 2, D)
op(0xd3, SET_o_r, 2, E)
op(0xd4, SET_o_r, 2, H)
op(0xd5, SET_o_r, 2, L)
op(0xd6, SET_o_irr, 2, HL)
op(0xd7, SET_o_r, 2, A)
op(0xd8, SET_o_r, 3, B)
op(0xd9, SET_o_r, 3, C)
op(0xda, SET_o_r, 3, D)
op(0xdb, SET_o_r, 3, E)
op(0xdc, SET_o_r, 3, H)
op(0xdd, SET_o_r, 3, L)
op(0xde, SET_o_irr, 3, HL)
op(0xdf, SET_o_r, 3, A)
op(0xe0, SET_o_r, 4, B)
op(0xe1, SET_o_r, 4, C)
op(0xe2, SET_o_r, 4, D)
op(0xe3, SET_o_r, 4, E)
op(0xe4, SET_o_r, 4, H)
op(0xe5, SET_o_r, 4, L)
op(0xe6, SET_o_irr, 4, HL)
op(0xe7, SET_o_r, 4, A)
op(0xe8, SET_o_r, 5, B)
op(0xe9, SET_o_r, 5, C)
op(0xea, SET_o_r, 5, D)
op(0xeb, SET_o_r, 5, E)
op(0xec, SET_o_r, 5, H)
op(0xed, SET_o_r, 5, L)
op(0xee, SET_o_irr, 5, HL)
op(0xef, SET_o_r, 5, A)
op(0xf0, SET_o_r, 6, B)
op(0xf1, SET_o_r, 6, C)
op(0xf2, SET_o_r, 6, D)
op(0xf3, SET_o_r, 6, E)
op(0xf4, SET_o_r, 6, H)
op(0xf5, SET_o_r, 6, L)
op(0xf6, SET_o_irr, 6, HL)
op(0xf7, SET_o_r, 6, A)
op(0xf8, SET_o_r, 7, B)
op(0xf9, SET_o_r, 7, C)
op(0xfa, SET_o_r, 7, D)
op(0xfb, SET_o_r, 7, E)
op(0xfc, SET_o_r, 7, H)
op(0xfd, SET_o_r, 7, L)
op(0xfe, SET_o_irr, 7, HL)
op(0xff, SET_o_r, 7, A)
} }
trap(0xcb, code);
} }
auto Z80::instructionED(uint8 code) -> void { auto Z80::instructionED(uint8 code) -> void {
@ -246,6 +500,22 @@ auto Z80::instructionED(uint8 code) -> void {
op(0x46, IM_o, 0) op(0x46, IM_o, 0)
op(0x56, IM_o, 1) op(0x56, IM_o, 1)
op(0x5e, IM_o, 2) op(0x5e, IM_o, 2)
op(0xa0, LDI)
op(0xa1, CPI)
op(0xa2, INI)
op(0xa3, OUTI)
op(0xa8, LDD)
op(0xa9, CPD)
op(0xaa, IND)
op(0xab, OUTD)
op(0xb0, LDIR)
op(0xb1, CPIR)
op(0xb2, INIR)
op(0xb3, OTIR)
op(0xb8, LDDR)
op(0xb9, CPDR)
op(0xba, INDR)
op(0xbb, OTDR)
} }
trap(0xed, code); trap(0xed, code);

View File

@ -40,6 +40,12 @@ auto Z80::AND(uint8 x, uint8 y) -> uint8 {
return z; return z;
} }
auto Z80::BIT(uint3 bit, uint8 x) -> void {
NF = 0;
HF = 1;
ZF = (x & 1 << bit) == 0;
}
auto Z80::DEC(uint8 x) -> uint8 { auto Z80::DEC(uint8 x) -> uint8 {
uint8 z = x - 1; uint8 z = x - 1;
@ -83,6 +89,142 @@ auto Z80::OR(uint8 x, uint8 y) -> uint8 {
return z; return z;
} }
auto Z80::RES(uint3 bit, uint8 x) -> uint8 {
x &= ~(1 << bit);
return x;
}
auto Z80::RL(uint8 x) -> uint8 {
bool c = x.bit(7);
x = x << 1 | CF;
CF = c;
NF = 0;
PF = parity(x);
XF = x.bit(3);
HF = 0;
YF = x.bit(5);
ZF = x == 0;
SF = x.bit(7);
return x;
}
auto Z80::RLC(uint8 x) -> uint8 {
x = x << 1 | x >> 7;
CF = x.bit(0);
NF = 0;
PF = parity(x);
XF = x.bit(3);
HF = 0;
YF = x.bit(5);
ZF = x == 0;
SF = x.bit(7);
return x;
}
auto Z80::RR(uint8 x) -> uint8 {
bool c = x.bit(0);
x = x >> 1 | CF << 7;
CF = c;
NF = 0;
PF = parity(x);
XF = x.bit(3);
HF = 0;
YF = x.bit(5);
ZF = x == 0;
SF = x.bit(7);
return x;
}
auto Z80::RRC(uint8 x) -> uint8 {
x = x >> 1 | x << 7;
CF = x.bit(7);
NF = 0;
PF = parity(x);
XF = x.bit(3);
HF = 0;
YF = x.bit(5);
ZF = x == 0;
SF = x.bit(7);
return x;
}
auto Z80::SET(uint3 bit, uint8 x) -> uint8 {
x |= (1 << bit);
return x;
}
auto Z80::SLA(uint8 x) -> uint8 {
bool c = x.bit(7);
x = x << 1;
CF = c;
NF = 0;
PF = parity(x);
XF = x.bit(3);
HF = 0;
YF = x.bit(5);
ZF = x == 0;
SF = x.bit(7);
return x;
}
auto Z80::SLL(uint8 x) -> uint8 {
bool c = x.bit(7);
x = x << 1 | 1;
CF = c;
NF = 0;
PF = parity(x);
XF = x.bit(3);
HF = 0;
YF = x.bit(5);
ZF = x == 0;
SF = x.bit(7);
return x;
}
auto Z80::SRA(uint8 x) -> uint8 {
bool c = x.bit(0);
x = (int8)x >> 1;
CF = c;
NF = 0;
PF = parity(x);
XF = x.bit(3);
HF = 0;
YF = x.bit(5);
ZF = x == 0;
SF = x.bit(7);
return x;
}
auto Z80::SRL(uint8 x) -> uint8 {
bool c = x.bit(0);
x = x >> 1;
CF = c;
NF = 0;
PF = parity(x);
XF = x.bit(3);
HF = 0;
YF = x.bit(5);
ZF = x == 0;
SF = x.bit(7);
return x;
}
auto Z80::SUB(uint8 x, uint8 y, bool c) -> uint8 { auto Z80::SUB(uint8 x, uint8 y, bool c) -> uint8 {
uint9 z = x - y - c; uint9 z = x - y - c;
@ -146,6 +288,14 @@ auto Z80::instructionAND_a_r(uint8& x) -> void {
A = AND(A, x); A = AND(A, x);
} }
auto Z80::instructionBIT_o_irr(uint3 bit, uint16& x) -> void {
BIT(bit, read(displace(x)));
}
auto Z80::instructionBIT_o_r(uint3 bit, uint8& x) -> void {
BIT(bit, x);
}
auto Z80::instructionCCF() -> void { auto Z80::instructionCCF() -> void {
CF = !CF; CF = !CF;
NF = 0; NF = 0;
@ -164,6 +314,34 @@ auto Z80::instructionCP_a_r(uint8& x) -> void {
SUB(A, x); SUB(A, x);
} }
auto Z80::instructionCPD() -> void {
auto data = read(_HL--);
SUB(A, data);
VF = --BC > 0;
wait(5);
}
auto Z80::instructionCPDR() -> void {
instructionCPD();
if(!VF || ZF) return;
wait(5);
PC -= 2;
}
auto Z80::instructionCPI() -> void {
auto data = read(_HL++);
SUB(A, data);
VF = --BC > 0;
wait(5);
}
auto Z80::instructionCPIR() -> void {
instructionCPI();
if(!VF || ZF) return;
wait(5);
PC -= 2;
}
auto Z80::instructionCPL() -> void { auto Z80::instructionCPL() -> void {
A = ~A; A = ~A;
@ -234,6 +412,38 @@ auto Z80::instructionINC_rr(uint16& x) -> void {
x++; x++;
} }
//note: should be T(4,5,3,4); is instead T(4,4,4,4)
auto Z80::instructionIND() -> void {
auto data = in(C);
write(_HL--, data);
NF = 0;
ZF = --BC > 0;
wait(4);
}
auto Z80::instructionINDR() -> void {
instructionIND();
if(!ZF) return;
wait(5);
PC -= 2;
}
//note: should be T(4,5,3,4); is instead T(4,4,4,4)
auto Z80::instructionINI() -> void {
auto data = in(C);
write(_HL++, data);
NF = 0;
ZF = --BC > 0;
wait(4);
}
auto Z80::instructionINIR() -> void {
instructionINI();
if(!ZF) return;
wait(5);
PC -= 2;
}
auto Z80::instructionJP_c_nn(bool c) -> void { auto Z80::instructionJP_c_nn(bool c) -> void {
auto pc = operands(); auto pc = operands();
if(c) r.pc = pc; if(c) r.pc = pc;
@ -297,6 +507,38 @@ auto Z80::instructionLD_rr_nn(uint16& x) -> void {
x = operands(); x = operands();
} }
auto Z80::instructionLDD() -> void {
auto data = read(_HL--);
write(DE--, data);
wait(2);
NF = 0;
VF = --BC > 0;
HF = 0;
}
auto Z80::instructionLDDR() -> void {
instructionLDD();
if(!VF) return;
wait(5);
PC -= 2;
}
auto Z80::instructionLDI() -> void {
auto data = read(_HL++);
write(DE++, data);
wait(2);
NF = 0;
VF = --BC > 0;
HF = 0;
}
auto Z80::instructionLDIR() -> void {
instructionLDI();
if(!VF) return;
wait(5);
PC -= 2;
}
auto Z80::instructionNOP() -> void { auto Z80::instructionNOP() -> void {
} }
@ -308,6 +550,54 @@ auto Z80::instructionOR_a_r(uint8& x) -> void {
A = OR(A, x); A = OR(A, x);
} }
auto Z80::instructionOTDR() -> void {
instructionOUTD();
if(!ZF) return;
wait(5);
PC -= 2;
}
auto Z80::instructionOTIR() -> void {
instructionOUTI();
if(!ZF) return;
wait(5);
PC -= 2;
}
//note: should be T(4,5,3,4); instead is T(4,4,4,4)
auto Z80::instructionOUTD() -> void {
auto data = read(_HL--);
out(C, data);
NF = 1;
ZF = --BC > 0;
}
//note: should be T(4,5,3,4); instead is T(4,4,4,4)
auto Z80::instructionOUTI() -> void {
auto data = read(_HL++);
out(C, data);
NF = 1;
ZF = --BC > 0;
}
auto Z80::instructionRES_o_irr(uint3 bit, uint16& x) -> void {
auto addr = displace(x);
write(addr, RES(bit, read(addr)));
}
auto Z80::instructionRES_o_r(uint3 bit, uint8& x) -> void {
x = RES(bit, x);
}
auto Z80::instructionRL_irr(uint16& x) -> void {
auto addr = displace(x);
write(addr, RL(read(addr)));
}
auto Z80::instructionRL_r(uint8& x) -> void {
x = RL(x);
}
auto Z80::instructionRLA() -> void { auto Z80::instructionRLA() -> void {
bool c = A.bit(7); bool c = A.bit(7);
A = A << 1 | CF; A = A << 1 | CF;
@ -319,6 +609,15 @@ auto Z80::instructionRLA() -> void {
YF = A.bit(5); YF = A.bit(5);
} }
auto Z80::instructionRLC_irr(uint16& x) -> void {
auto addr = displace(x);
write(addr, RLC(read(addr)));
}
auto Z80::instructionRLC_r(uint8& x) -> void {
x = RLC(x);
}
auto Z80::instructionRLCA() -> void { auto Z80::instructionRLCA() -> void {
bool c = A.bit(7); bool c = A.bit(7);
A = A << 1 | c; A = A << 1 | c;
@ -330,6 +629,15 @@ auto Z80::instructionRLCA() -> void {
YF = A.bit(5); YF = A.bit(5);
} }
auto Z80::instructionRR_irr(uint16& x) -> void {
auto addr = displace(x);
write(addr, RR(read(addr)));
}
auto Z80::instructionRR_r(uint8& x) -> void {
x = RR(x);
}
auto Z80::instructionRRA() -> void { auto Z80::instructionRRA() -> void {
bool c = A.bit(0); bool c = A.bit(0);
A = CF << 7 | A >> 1; A = CF << 7 | A >> 1;
@ -341,6 +649,15 @@ auto Z80::instructionRRA() -> void {
YF = A.bit(5); YF = A.bit(5);
} }
auto Z80::instructionRRC_irr(uint16& x) -> void {
auto addr = displace(x);
write(addr, RRC(read(addr)));
}
auto Z80::instructionRRC_r(uint8& x) -> void {
x = RRC(x);
}
auto Z80::instructionRRCA() -> void { auto Z80::instructionRRCA() -> void {
bool c = A.bit(0); bool c = A.bit(0);
A = c << 7 | A >> 1; A = c << 7 | A >> 1;
@ -366,6 +683,51 @@ auto Z80::instructionSCF() -> void {
HF = 0; HF = 0;
} }
auto Z80::instructionSET_o_irr(uint3 bit, uint16& x) -> void {
auto addr = displace(x);
write(addr, SET(bit, read(addr)));
}
auto Z80::instructionSET_o_r(uint3 bit, uint8& x) -> void {
x = SET(bit, x);
}
auto Z80::instructionSLA_irr(uint16& x) -> void {
auto addr = displace(x);
write(addr, SLA(read(addr)));
}
auto Z80::instructionSLA_r(uint8& x) -> void {
x = SLA(x);
}
auto Z80::instructionSLL_irr(uint16& x) -> void {
auto addr = displace(x);
write(addr, SLL(read(addr)));
}
auto Z80::instructionSLL_r(uint8& x) -> void {
x = SLL(x);
}
auto Z80::instructionSRA_irr(uint16& x) -> void {
auto addr = displace(x);
write(addr, SRA(read(addr)));
}
auto Z80::instructionSRA_r(uint8& x) -> void {
x = SRA(x);
}
auto Z80::instructionSRL_irr(uint16& x) -> void {
auto addr = displace(x);
write(addr, SRL(read(addr)));
}
auto Z80::instructionSRL_r(uint8& x) -> void {
x = SRL(x);
}
auto Z80::instructionSUB_a_irr(uint16& x) -> void { auto Z80::instructionSUB_a_irr(uint16& x) -> void {
A = SUB(A, read(displace(x))); A = SUB(A, read(displace(x)));
} }

View File

@ -1,7 +1,7 @@
#define AF r.af.word #define AF r.af.word
#define BC r.bc.word #define BC r.bc.word
#define DE r.de.word #define DE r.de.word
#define HL r.hlp->word #define HL r.hlp->word //virtual HL (overridden by IX/IY prefixes)
#define A r.af.byte.hi #define A r.af.byte.hi
#define F r.af.byte.lo #define F r.af.byte.lo
@ -12,11 +12,11 @@
#define H r.hlp->byte.hi #define H r.hlp->byte.hi
#define L r.hlp->byte.lo #define L r.hlp->byte.lo
#define _HL r.hl.word //true HL (ignores IX/IY prefixes)
#define _H r.hl.byte.hi #define _H r.hl.byte.hi
#define _L r.hl.byte.lo #define _L r.hl.byte.lo
#define _HL r.hl.word
#define AF_ r.af_.word #define AF_ r.af_.word //shadow registers
#define BC_ r.bc_.word #define BC_ r.bc_.word
#define DE_ r.de_.word #define DE_ r.de_.word
#define HL_ r.hl_.word #define HL_ r.hl_.word

View File

@ -41,9 +41,20 @@ struct Z80 {
//instructions.cpp //instructions.cpp
auto ADD(uint8, uint8, bool = false) -> uint8; auto ADD(uint8, uint8, bool = false) -> uint8;
auto AND(uint8, uint8) -> uint8; auto AND(uint8, uint8) -> uint8;
auto BIT(uint3, uint8) -> void;
auto DEC(uint8) -> uint8; auto DEC(uint8) -> uint8;
auto INC(uint8) -> uint8; auto INC(uint8) -> uint8;
auto OR (uint8, uint8) -> uint8; auto OR (uint8, uint8) -> uint8;
auto RES(uint3, uint8) -> uint8;
auto RL (uint8) -> uint8;
auto RLC(uint8) -> uint8;
auto RR (uint8) -> uint8;
auto RRC(uint8) -> uint8;
auto SET(uint3, uint8) -> uint8;
auto SLA(uint8) -> uint8;
auto SLL(uint8) -> uint8;
auto SRA(uint8) -> uint8;
auto SRL(uint8) -> uint8;
auto SUB(uint8, uint8, bool = false) -> uint8; auto SUB(uint8, uint8, bool = false) -> uint8;
auto XOR(uint8, uint8) -> uint8; auto XOR(uint8, uint8) -> uint8;
@ -54,10 +65,16 @@ struct Z80 {
auto instructionADD_rr_rr(uint16&, uint16&) -> void; auto instructionADD_rr_rr(uint16&, uint16&) -> void;
auto instructionAND_a_irr(uint16&) -> void; auto instructionAND_a_irr(uint16&) -> void;
auto instructionAND_a_r(uint8&) -> void; auto instructionAND_a_r(uint8&) -> void;
auto instructionBIT_o_irr(uint3, uint16&) -> void;
auto instructionBIT_o_r(uint3, uint8&) -> void;
auto instructionCCF() -> void; auto instructionCCF() -> void;
auto instructionCP_a_irr(uint16& x) -> void; auto instructionCP_a_irr(uint16& x) -> void;
auto instructionCP_a_n() -> void; auto instructionCP_a_n() -> void;
auto instructionCP_a_r(uint8& x) -> void; auto instructionCP_a_r(uint8& x) -> void;
auto instructionCPD() -> void;
auto instructionCPDR() -> void;
auto instructionCPI() -> void;
auto instructionCPIR() -> void;
auto instructionCPL() -> void; auto instructionCPL() -> void;
auto instructionDEC_irr(uint16&) -> void; auto instructionDEC_irr(uint16&) -> void;
auto instructionDEC_r(uint8&) -> void; auto instructionDEC_r(uint8&) -> void;
@ -71,6 +88,10 @@ struct Z80 {
auto instructionINC_irr(uint16&) -> void; auto instructionINC_irr(uint16&) -> void;
auto instructionINC_r(uint8&) -> void; auto instructionINC_r(uint8&) -> void;
auto instructionINC_rr(uint16&) -> void; auto instructionINC_rr(uint16&) -> void;
auto instructionIND() -> void;
auto instructionINDR() -> void;
auto instructionINI() -> void;
auto instructionINIR() -> void;
auto instructionJP_c_nn(bool) -> void; auto instructionJP_c_nn(bool) -> void;
auto instructionJR_c_e(bool) -> void; auto instructionJR_c_e(bool) -> void;
auto instructionLD_a_inn() -> void; auto instructionLD_a_inn() -> void;
@ -85,16 +106,44 @@ struct Z80 {
auto instructionLD_r_r(uint8&, uint8&) -> void; auto instructionLD_r_r(uint8&, uint8&) -> void;
auto instructionLD_rr_inn(uint16&) -> void; auto instructionLD_rr_inn(uint16&) -> void;
auto instructionLD_rr_nn(uint16&) -> void; auto instructionLD_rr_nn(uint16&) -> void;
auto instructionLDD() -> void;
auto instructionLDDR() -> void;
auto instructionLDI() -> void;
auto instructionLDIR() -> void;
auto instructionNOP() -> void; auto instructionNOP() -> void;
auto instructionOR_a_irr(uint16&) -> void; auto instructionOR_a_irr(uint16&) -> void;
auto instructionOR_a_r(uint8&) -> void; auto instructionOR_a_r(uint8&) -> void;
auto instructionOTDR() -> void;
auto instructionOTIR() -> void;
auto instructionOUTD() -> void;
auto instructionOUTI() -> void;
auto instructionRES_o_irr(uint3, uint16&) -> void;
auto instructionRES_o_r(uint3, uint8&) -> void;
auto instructionRL_irr(uint16&) -> void;
auto instructionRL_r(uint8&) -> void;
auto instructionRLA() -> void; auto instructionRLA() -> void;
auto instructionRLC_irr(uint16&) -> void;
auto instructionRLC_r(uint8&) -> void;
auto instructionRLCA() -> void; auto instructionRLCA() -> void;
auto instructionRR_irr(uint16&) -> void;
auto instructionRR_r(uint8&) -> void;
auto instructionRRA() -> void; auto instructionRRA() -> void;
auto instructionRRC_irr(uint16&) -> void;
auto instructionRRC_r(uint8&) -> void;
auto instructionRRCA() -> void; auto instructionRRCA() -> void;
auto instructionSBC_a_irr(uint16&) -> void; auto instructionSBC_a_irr(uint16&) -> void;
auto instructionSBC_a_r(uint8&) -> void; auto instructionSBC_a_r(uint8&) -> void;
auto instructionSCF() -> void; auto instructionSCF() -> void;
auto instructionSET_o_irr(uint3, uint16&) -> void;
auto instructionSET_o_r(uint3, uint8&) -> void;
auto instructionSLA_irr(uint16&) -> void;
auto instructionSLA_r(uint8&) -> void;
auto instructionSLL_irr(uint16&) -> void;
auto instructionSLL_r(uint8&) -> void;
auto instructionSRA_irr(uint16&) -> void;
auto instructionSRA_r(uint8&) -> void;
auto instructionSRL_irr(uint16&) -> void;
auto instructionSRL_r(uint8&) -> void;
auto instructionSUB_a_irr(uint16&) -> void; auto instructionSUB_a_irr(uint16&) -> void;
auto instructionSUB_a_r(uint8&) -> void; auto instructionSUB_a_r(uint8&) -> void;
auto instructionXOR_a_irr(uint16&) -> void; auto instructionXOR_a_irr(uint16&) -> void;

View File

@ -25,18 +25,20 @@ auto pDesktop::workspace() -> Geometry {
unsigned long items, after; unsigned long items, after;
XlibAtom returnAtom; XlibAtom returnAtom;
XlibAtom netWorkarea = XInternAtom(display, "_NET_WORKAREA", XlibTrue);
int result = XGetWindowProperty( int result = XGetWindowProperty(
display, RootWindow(display, screen), XInternAtom(display, "_NET_WORKAREA", XlibTrue), 0, 4, XlibFalse, display, RootWindow(display, screen), netWorkarea, 0, 4, XlibFalse,
XInternAtom(display, "CARDINAL", XlibTrue), &returnAtom, &format, &items, &after, &data XInternAtom(display, "CARDINAL", XlibTrue), &returnAtom, &format, &items, &after, &data
); );
XCloseDisplay(display); XlibAtom cardinal = XInternAtom(display, "CARDINAL", XlibTrue);
if(result == Success && returnAtom == cardinal && format == 32 && items == 4) {
if(result == Success && returnAtom == XInternAtom(display, "CARDINAL", XlibTrue) && format == 32 && items == 4) {
unsigned long* workarea = (unsigned long*)data; unsigned long* workarea = (unsigned long*)data;
XCloseDisplay(display);
return {(int)workarea[0], (int)workarea[1], (int)workarea[2], (int)workarea[3]}; return {(int)workarea[0], (int)workarea[1], (int)workarea[2], (int)workarea[3]};
} }
XCloseDisplay(display);
return { return {
0, 0, 0, 0,
gdk_screen_get_width(gdk_screen_get_default()), gdk_screen_get_width(gdk_screen_get_default()),