More MC6809

This commit is contained in:
alyosha-tas 2019-04-03 19:22:23 -05:00
parent d2131ea947
commit 244b9d2231
4 changed files with 249 additions and 68 deletions

View File

@ -151,35 +151,35 @@ namespace BizHawk.Emulation.Common.Components.MC6809
case 0x7D: EXT_MEM(TST); break; // TST (Extended)
case 0x7E: JMP_EXT_(); break; // JMP (Extended)
case 0x7F: EXT_MEM(CLR); break; // CLR (Extended)
case 0x80: REG_OP(ADD8, A); break; // SUBA (Immediate)
case 0x81: REG_OP(ADD8, A); break; // CMPA (Immediate)
case 0x82: REG_OP(ADD8, A); break; // SBCA (Immediate)
case 0x83: REG_OP(ADD8, A); break; // SUBD (Immediate)
case 0x84: REG_OP(ADD8, A); break; // ANDA (Immediate)
case 0x85: REG_OP(ADD8, A); break; // BITA (Immediate)
case 0x86: REG_OP(ADD8, A); break; // LDA (Immediate)
case 0x80: REG_OP_IMD(SUB8, A); break; // SUBA (Immediate)
case 0x81: REG_OP_IMD(CMP8, A); break; // CMPA (Immediate)
case 0x82: REG_OP_IMD(SBC8, A); break; // SBCA (Immediate)
case 0x83: IMD_OP_D(SUB16, D); break; // SUBD (Immediate)
case 0x84: REG_OP_IMD(AND8, A); break; // ANDA (Immediate)
case 0x85: REG_OP_IMD(BIT, A); break; // BITA (Immediate)
case 0x86: REG_OP_IMD(TR, A); break; // LDA (Immediate)
case 0x87: ILLEGAL(); break; // ILLEGAL
case 0x88: REG_OP(ADC8, A); break; // EORA (Immediate)
case 0x89: REG_OP(ADC8, A); break; // ADCA (Immediate)
case 0x8A: REG_OP(ADC8, A); break; // ORA (Immediate)
case 0x8B: REG_OP(ADC8, A); break; // ADDA (Immediate)
case 0x8C: REG_OP(ADC8, A); break; // CMPX (Immediate)
case 0x8D: REG_OP(ADC8, A); break; // BSR (Relative)
case 0x8E: REG_OP(ADC8, A); break; // LDX (Immediate)
case 0x88: REG_OP_IMD(XOR8, A); break; // EORA (Immediate)
case 0x89: REG_OP_IMD(ADC8, A); break; // ADCA (Immediate)
case 0x8A: REG_OP_IMD(OR8, A); break; // ORA (Immediate)
case 0x8B: REG_OP_IMD(ADD8, A); break; // ADDA (Immediate)
case 0x8C: REG_OP_IMD(ADC8, A); break; // CMPX (Immediate)
case 0x8D: BSR_(); break; // BSR (Relative)
case 0x8E: REG_OP_LD_16(X); break; // LDX (Immediate)
case 0x8F: ILLEGAL(); break; // ILLEGAL
case 0x90: REG_OP(ADD8, A); break; // SUBA (Direct)
case 0x91: REG_OP(ADD8, A); break; // CMPA (Direct)
case 0x92: REG_OP(ADD8, A); break; // SBCA (Direct)
case 0x93: REG_OP(ADD8, A); break; // SUBD (Direct)
case 0x94: REG_OP(ADD8, A); break; // ANDA (Direct)
case 0x95: REG_OP(ADD8, A); break; // BITA (Direct)
case 0x96: REG_OP(ADD8, A); break; // LDA (Direct)
case 0x97: REG_OP(ADD8, A); break; // STA (Direct)
case 0x98: REG_OP(ADC8, A); break; // EORA (Direct)
case 0x99: REG_OP(ADC8, A); break; // ADCA (Direct)
case 0x9A: REG_OP(ADC8, A); break; // ORA (Direct)
case 0x9B: REG_OP(ADC8, A); break; // ADDA (Direct)
case 0x9C: REG_OP(ADC8, A); break; // CMPX (Direct)
case 0x90: DIRECT_MEM_4(SUB8, A); break; // SUBA (Direct)
case 0x91: DIRECT_MEM_4(CMP8, A); break; // CMPA (Direct)
case 0x92: DIRECT_MEM_4(SBC8, A); break; // SBCA (Direct)
case 0x93: DIR_OP_D(SUB16, D); break; // SUBD (Direct)
case 0x94: DIRECT_MEM_4(AND8, A); break; // ANDA (Direct)
case 0x95: DIRECT_MEM_4(BIT, A); break; // BITA (Direct)
case 0x96: DIRECT_MEM_4(TR, A); break; // LDA (Direct)
case 0x97: DIRECT_ST_4(A); break; // STA (Direct)
case 0x98: DIRECT_MEM_4(XOR8, A); break; // EORA (Direct)
case 0x99: DIRECT_MEM_4(ADC8, A); break; // ADCA (Direct)
case 0x9A: DIRECT_MEM_4(OR8, A); break; // ORA (Direct)
case 0x9B: DIRECT_MEM_4(ADD8, A); break; // ADDA (Direct)
case 0x9C: DIR_CMP_16(CMP16, X); break; // CMPX (Direct)
case 0x9D: REG_OP(ADC8, A); break; // JSR (Direct)
case 0x9E: REG_OP(ADC8, A); break; // LDX (Direct)
case 0x9F: REG_OP(ADC8, A); break; // STX (Direct)
@ -215,36 +215,36 @@ namespace BizHawk.Emulation.Common.Components.MC6809
case 0xBD: REG_OP(XOR8, A); break; // JSR (Extended)
case 0xBE: REG_OP(XOR8, A); break; // LDX (Extended)
case 0xBF: REG_OP(XOR8, A); break; // STX (Extended)
case 0xC0: REG_OP(ADD8, A); break; // SUBB (Immediate)
case 0xC1: REG_OP(ADD8, A); break; // CMPB (Immediate)
case 0xC2: REG_OP(ADD8, A); break; // SBCB (Immediate)
case 0xC3: REG_OP(ADD8, A); break; // ADDD (Immediate)
case 0xC4: REG_OP(ADD8, A); break; // ANDB (Immediate)
case 0xC5: REG_OP(ADD8, A); break; // BITB (Immediate)
case 0xC6: REG_OP(ADD8, A); break; // LDB (Immediate)
case 0xC0: REG_OP_IMD(SUB8, B); break; // SUBB (Immediate)
case 0xC1: REG_OP_IMD(CMP8, B); break; // CMPB (Immediate)
case 0xC2: REG_OP_IMD(SBC8, B); break; // SBCB (Immediate)
case 0xC3: IMD_OP_D(ADD16, D); break; // ADDD (Immediate)
case 0xC4: REG_OP_IMD(AND8, B); break; // ANDB (Immediate)
case 0xC5: REG_OP_IMD(BIT, B); break; // BITB (Immediate)
case 0xC6: REG_OP_IMD(TR, B); break; // LDB (Immediate)
case 0xC7: ILLEGAL(); break; // ILLEGAL
case 0xC8: REG_OP(ADC8, A); break; // EORB (Immediate)
case 0xC9: REG_OP(ADC8, A); break; // ADCB (Immediate)
case 0xCA: REG_OP(ADC8, A); break; // ORB (Immediate)
case 0xCB: REG_OP(ADC8, A); break; // ADDB (Immediate)
case 0xCC: REG_OP(ADC8, A); break; // LDD (Immediate)
case 0xC8: REG_OP_IMD(XOR8, B); break; // EORB (Immediate)
case 0xC9: REG_OP_IMD(ADC8, B); break; // ADCB (Immediate)
case 0xCA: REG_OP_IMD(OR8, B); break; // ORB (Immediate)
case 0xCB: REG_OP_IMD(ADD8, B); break; // ADDB (Immediate)
case 0xCC: REG_OP_LD_16D(D); break; // LDD (Immediate)
case 0xCD: ILLEGAL(); break; // ILLEGAL
case 0xCE: REG_OP(ADC8, A); break; // LDU (Immediate)
case 0xCE: REG_OP_LD_16(US); break; // LDU (Immediate)
case 0xCF: ILLEGAL(); break; // ILLEGAL
case 0xD0: REG_OP(ADD8, B); break; // SUBB (Direct)
case 0xD1: REG_OP(ADD8, B); break; // CMPB (Direct)
case 0xD2: REG_OP(ADD8, B); break; // SBCB (Direct)
case 0xD3: REG_OP(ADD8, B); break; // ADDD (Direct)
case 0xD4: REG_OP(ADD8, B); break; // ANDB (Direct)
case 0xD5: REG_OP(ADD8, B); break; // BITB (Direct)
case 0xD6: REG_OP(ADD8, B); break; // LDB (Direct)
case 0xD7: REG_OP(ADD8, B); break; // STB (Direct)
case 0xD8: REG_OP(ADC8, B); break; // EORB (Direct)
case 0xD9: REG_OP(ADC8, B); break; // ADCB (Direct)
case 0xDA: REG_OP(ADC8, B); break; // ORB (Direct)
case 0xDB: REG_OP(ADC8, B); break; // ADDB (Direct)
case 0xDC: REG_OP(ADC8, B); break; // LDD (Direct)
case 0xDD: REG_OP(ADC8, B); break; // STD (Direct)
case 0xD0: DIRECT_MEM_4(SUB8, B); break; // SUBB (Direct)
case 0xD1: DIRECT_MEM_4(CMP8, B); break; // CMPB (Direct)
case 0xD2: DIRECT_MEM_4(SBC8, B); break; // SBCB (Direct)
case 0xD3: DIR_OP_D(ADD16, D); break; // ADDD (Direct)
case 0xD4: DIRECT_MEM_4(AND8, B); break; // ANDB (Direct)
case 0xD5: DIRECT_MEM_4(BIT, B); break; // BITB (Direct)
case 0xD6: DIRECT_MEM_4(TR, B); break; // LDB (Direct)
case 0xD7: DIRECT_ST_4(B); break; // STB (Direct)
case 0xD8: DIRECT_MEM_4(XOR8, B); break; // EORB (Direct)
case 0xD9: DIRECT_MEM_4(ADC8, B); break; // ADCB (Direct)
case 0xDA: DIRECT_MEM_4(OR8, B); break; // ORB (Direct)
case 0xDB: DIRECT_MEM_4(ADD8, B); break; // ADDB (Direct)
case 0xDC: DIRECT_MEM_4(ADC8, B); break; // LDD (Direct)
case 0xDD: DIRECT_MEM_4(ADC8, B); break; // STD (Direct)
case 0xDE: REG_OP(ADC8, B); break; // LDU (Direct)
case 0xDF: REG_OP(ADC8, B); break; // STU (Direct)
case 0xE0: REG_OP(AND8, B); break; // SUBB (Indexed)

View File

@ -87,6 +87,10 @@ namespace BizHawk.Emulation.Common.Components.MC6809
public const ushort SET_F_I = 73;
public const ushort SET_E = 74;
public const ushort ANDCC = 75;
public const ushort CMP8 = 76;
public const ushort SUB16 = 77;
public const ushort ADD16 = 78;
public const ushort CMP16 = 79;
public MC6809()
{
@ -216,12 +220,33 @@ namespace BizHawk.Emulation.Common.Components.MC6809
case AND8:
AND8_Func(cur_instr[instr_pntr++], cur_instr[instr_pntr++]);
break;
case ADD8:
ADD8_Func(cur_instr[instr_pntr++], cur_instr[instr_pntr++]);
break;
case ADC8:
ADC8_Func(cur_instr[instr_pntr++], cur_instr[instr_pntr++]);
break;
case OR8:
OR8_Func(cur_instr[instr_pntr++], cur_instr[instr_pntr++]);
break;
case XOR8:
XOR8_Func(cur_instr[instr_pntr++], cur_instr[instr_pntr++]);
break;
case BIT:
BIT_Func(cur_instr[instr_pntr++], cur_instr[instr_pntr++]);
break;
case SUB8:
SUB8_Func(cur_instr[instr_pntr++], cur_instr[instr_pntr++]);
break;
case SBC8:
SUB8_Func(cur_instr[instr_pntr++], cur_instr[instr_pntr++]);
break;
case CMP8:
CMP8_Func(cur_instr[instr_pntr++], cur_instr[instr_pntr++]);
break;
case TR:
TR_Func(cur_instr[instr_pntr++], cur_instr[instr_pntr++]);
break;
case SET_ADDR:
Regs[cur_instr[instr_pntr++]] = (ushort)((Regs[cur_instr[instr_pntr++]] << 8) | Regs[cur_instr[instr_pntr++]]);
break;
@ -347,6 +372,9 @@ namespace BizHawk.Emulation.Common.Components.MC6809
case SBC8:
SBC8_Func(cur_instr[instr_pntr++], cur_instr[instr_pntr++]);
break;
case CMP8:
CMP8_Func(cur_instr[instr_pntr++], cur_instr[instr_pntr++]);
break;
case INC16:
INC16_Func(cur_instr[instr_pntr++], cur_instr[instr_pntr++]);
break;
@ -356,6 +384,15 @@ namespace BizHawk.Emulation.Common.Components.MC6809
case DEC16:
DEC16_Func(cur_instr[instr_pntr++]);
break;
case SUB16:
SUB16_Func(cur_instr[instr_pntr++]);
break;
case ADD16:
ADD16_Func(cur_instr[instr_pntr++]);
break;
case CMP16:
CMP16_Func(cur_instr[instr_pntr++], cur_instr[instr_pntr++]);
break;
case DEC8:
DEC8_Func(cur_instr[instr_pntr++]);
break;

View File

@ -117,7 +117,7 @@ namespace BizHawk.Emulation.Common.Components.MC6809
{
Regs[ALU] = (ushort)(Regs[A] * Regs[B]);
D = Regs[ALU];
FlagC = Regs[B] > 127;
FlagC = Regs[A] > 127;
FlagZ = D == 0;
}
@ -136,7 +136,7 @@ namespace BizHawk.Emulation.Common.Components.MC6809
Reg16_d += (Regs[src] & 0xF);
FlagH = Reg16_d.Bit(4);
FlagV = (Regs[dest].Bit(7) != Regs[src].Bit(7)) && (Regs[dest].Bit(7) != ans.Bit(7));
FlagN = false;
Regs[dest] = ans;
@ -157,16 +157,39 @@ namespace BizHawk.Emulation.Common.Components.MC6809
Reg16_d -= (Regs[src] & 0xF);
FlagH = Reg16_d.Bit(4);
FlagN = true;
FlagN = ans > 127;
FlagV = (Regs[dest].Bit(7) != Regs[src].Bit(7)) && (Regs[dest].Bit(7) != ans.Bit(7));
Regs[dest] = ans;
}
public void BIT_Func(ushort bit, ushort src)
// same as SUB8 but result not stored
public void CMP8_Func(ushort dest, ushort src)
{
FlagZ = !Regs[src].Bit(bit);
FlagH = true;
FlagN = false;
int Reg16_d = Regs[dest];
Reg16_d -= Regs[src];
FlagC = Reg16_d.Bit(8);
FlagZ = (Reg16_d & 0xFF) == 0;
ushort ans = (ushort)(Reg16_d & 0xFF);
// redo for half carry flag
Reg16_d = Regs[dest] & 0xF;
Reg16_d -= (Regs[src] & 0xF);
FlagH = Reg16_d.Bit(4);
FlagN = ans > 127;
FlagV = (Regs[dest].Bit(7) != Regs[src].Bit(7)) && (Regs[dest].Bit(7) != ans.Bit(7));
}
public void BIT_Func(ushort dest, ushort src)
{
ushort ans = (ushort)(Regs[dest] & Regs[src]);
FlagZ = ans == 0;
FlagV = false;
FlagN = ans > 127;
}
public void SET_Func(ushort bit, ushort src)
@ -253,7 +276,7 @@ namespace BizHawk.Emulation.Common.Components.MC6809
}
FlagZ = D == 0;
FlagN = Regs[B] > 127;
FlagN = Regs[A] > 127;
}
public void CCF_Func(ushort src)
@ -276,7 +299,7 @@ namespace BizHawk.Emulation.Common.Components.MC6809
FlagZ = Regs[dest] == 0;
FlagV = false;
FlagN = Regs[B] > 127;
FlagN = Regs[dest] > 127;
}
public void OR8_Func(ushort dest, ushort src)
@ -285,7 +308,7 @@ namespace BizHawk.Emulation.Common.Components.MC6809
FlagZ = Regs[dest] == 0;
FlagV = false;
FlagN = Regs[B] > 127;
FlagN = Regs[dest] > 127;
}
public void XOR8_Func(ushort dest, ushort src)
@ -293,9 +316,8 @@ namespace BizHawk.Emulation.Common.Components.MC6809
Regs[dest] = (ushort)(Regs[dest] ^ Regs[src]);
FlagZ = Regs[dest] == 0;
FlagC = false;
FlagH = false;
FlagN = false;
FlagV = false;
FlagN = Regs[dest] > 127;
}
public void CP8_Func(ushort dest, ushort src)
@ -418,6 +440,7 @@ namespace BizHawk.Emulation.Common.Components.MC6809
Reg16_d += ((Regs[src] & 0xF) + c);
FlagH = Reg16_d.Bit(4);
FlagV = (Regs[dest].Bit(7) != Regs[src].Bit(7)) && (Regs[dest].Bit(7) != ans.Bit(7));
FlagN = false;
Regs[dest] = ans;
@ -440,7 +463,8 @@ namespace BizHawk.Emulation.Common.Components.MC6809
Reg16_d -= ((Regs[src] & 0xF) + c);
FlagH = Reg16_d.Bit(4);
FlagN = true;
FlagN = ans > 127;
FlagV = (Regs[dest].Bit(7) != Regs[src].Bit(7)) && (Regs[dest].Bit(7) != ans.Bit(7));
Regs[dest] = ans;
}
@ -518,6 +542,60 @@ namespace BizHawk.Emulation.Common.Components.MC6809
}
// D register implied
public void SUB16_Func(ushort src)
{
int Reg16_d = D;
int Reg16_s = Regs[src];
Reg16_d -= Reg16_s;
FlagC = Reg16_d.Bit(16);
FlagZ = (Reg16_d & 0xFFFF) == 0;
ushort ans = (ushort)(Reg16_d & 0xFFFF);
FlagN = ans > 0x7FFF;
FlagV = (D.Bit(15) != Regs[src].Bit(15)) && (D.Bit(15) != ans.Bit(15));
D = ans;
}
// D register implied
public void ADD16_Func(ushort src)
{
int Reg16_d = D;
int Reg16_s = Regs[src];
Reg16_d += Reg16_s;
FlagC = Reg16_d.Bit(16);
FlagZ = (Reg16_d & 0xFFFF) == 0;
ushort ans = (ushort)(Reg16_d & 0xFFFF);
FlagN = ans > 0x7FFF;
FlagV = (D.Bit(15) != Regs[src].Bit(15)) && (D.Bit(15) != ans.Bit(15));
D = ans;
}
public void CMP16_Func(ushort dest, ushort src)
{
int Reg16_d = Regs[dest];
int Reg16_s = Regs[src];
Reg16_d += Reg16_s;
FlagC = Reg16_d.Bit(16);
FlagZ = (Reg16_d & 0xFFFF) == 0;
ushort ans = (ushort)(Reg16_d & 0xFFFF);
FlagN = ans > 0x7FFF;
FlagV = (Regs[dest].Bit(15) != Regs[src].Bit(15)) && (Regs[dest].Bit(15) != ans.Bit(15));
}
public void EXG_Func(ushort sel)
{
ushort src = 0;

View File

@ -32,6 +32,20 @@ namespace BizHawk.Emulation.Common.Components.MC6809
WR, ADDR, ALU);
}
private void DIRECT_ST_4(ushort dest)
{
PopulateCURINSTR(RD_INC_OP, ALU, PC, SET_ADDR, ADDR, DP, ALU,
RD, ALU, ADDR,
WR, ADDR, dest);
}
private void DIRECT_MEM_4(ushort oper, ushort dest)
{
PopulateCURINSTR(RD_INC_OP, ALU, PC, SET_ADDR, ADDR, DP, ALU,
RD, ALU, ADDR,
oper, dest, ALU);
}
private void EXT_MEM(ushort oper)
{
PopulateCURINSTR(RD_INC, ALU, PC,
@ -49,6 +63,48 @@ namespace BizHawk.Emulation.Common.Components.MC6809
TR, CC, ALU2);
}
private void REG_OP_IMD(ushort oper, ushort dest)
{
PopulateCURINSTR(RD_INC_OP, ALU, PC, oper, dest, ALU);
}
private void IMD_OP_D(ushort oper, ushort dest)
{
PopulateCURINSTR(RD_INC, ALU, PC,
RD_INC_OP, ALU2, PC, SET_ADDR, ADDR, ALU, ALU2,
oper, ADDR);
}
private void DIR_OP_D(ushort oper, ushort dest)
{
PopulateCURINSTR(RD_INC_OP, ALU, PC, SET_ADDR, ADDR, DP, ALU,
RD_INC, ALU, ADDR,
RD, ALU2, ADDR,
SET_ADDR, ADDR, ALU, ALU2,
oper, ADDR);
}
private void DIR_CMP_16(ushort oper, ushort dest)
{
PopulateCURINSTR(RD_INC_OP, ALU, PC, SET_ADDR, ADDR, DP, ALU,
RD_INC, ALU, ADDR,
RD, ALU2, ADDR,
SET_ADDR, ADDR, ALU, ALU2,
oper, dest, ADDR);
}
private void REG_OP_LD_16(ushort dest)
{
PopulateCURINSTR(RD_INC, ALU, PC,
RD_INC_OP, ALU2, PC, SET_ADDR, dest, ALU, ALU2);
}
private void REG_OP_LD_16D(ushort dest)
{
PopulateCURINSTR(RD_INC, A, PC,
RD_INC, B, PC);
}
private void EXG_()
{
PopulateCURINSTR(RD_INC, ALU,
@ -118,6 +174,16 @@ namespace BizHawk.Emulation.Common.Components.MC6809
}
}
private void BSR_()
{
PopulateCURINSTR(RD_INC, ALU, PC,
ADD8BR, PC, ALU,
TR, ADDR, PC,
DEC16, SP,
WR_DEC_LO, SP, ADDR,
WR_HI, SP, ADDR);
}
private void LBSR_()
{
PopulateCURINSTR(RD_INC, ALU, PC,