commodore64: add cartridge mapper 0012 (Zaxxon, Super Zaxxon), fix mapper 0000 to support 4k roms
This commit is contained in:
parent
d05bd47ed0
commit
1eca7805cf
|
@ -84,6 +84,7 @@
|
||||||
<Compile Include="Computers\Commodore64\Cartridges\Mapper0000.cs" />
|
<Compile Include="Computers\Commodore64\Cartridges\Mapper0000.cs" />
|
||||||
<Compile Include="Computers\Commodore64\C64.Input.cs" />
|
<Compile Include="Computers\Commodore64\C64.Input.cs" />
|
||||||
<Compile Include="Computers\Commodore64\Cartridges\Mapper0005.cs" />
|
<Compile Include="Computers\Commodore64\Cartridges\Mapper0005.cs" />
|
||||||
|
<Compile Include="Computers\Commodore64\Cartridges\Mapper0012.cs" />
|
||||||
<Compile Include="Computers\Commodore64\Media\PRG.cs" />
|
<Compile Include="Computers\Commodore64\Media\PRG.cs" />
|
||||||
<Compile Include="Computers\Commodore64\Memory.cs" />
|
<Compile Include="Computers\Commodore64\Memory.cs" />
|
||||||
<Compile Include="Computers\Commodore64\Cartridges\Cartridge.cs" />
|
<Compile Include="Computers\Commodore64\Cartridges\Cartridge.cs" />
|
||||||
|
|
|
@ -70,6 +70,9 @@ namespace BizHawk.Emulation.Computers.Commodore64.Cartridges
|
||||||
case 0x0005:
|
case 0x0005:
|
||||||
result = new Mapper0005(chipAddress, chipBank, chipData);
|
result = new Mapper0005(chipAddress, chipBank, chipData);
|
||||||
break;
|
break;
|
||||||
|
case 0x0012:
|
||||||
|
result = new Mapper0012(chipAddress, chipBank, chipData);
|
||||||
|
break;
|
||||||
default:
|
default:
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
|
@ -10,6 +10,8 @@ namespace BizHawk.Emulation.Computers.Commodore64.Cartridges
|
||||||
private byte[] romA;
|
private byte[] romA;
|
||||||
private byte[] romB;
|
private byte[] romB;
|
||||||
|
|
||||||
|
// standard cartridge mapper (Commodore)
|
||||||
|
|
||||||
public Mapper0000(byte[] data, bool exrom, bool game)
|
public Mapper0000(byte[] data, bool exrom, bool game)
|
||||||
{
|
{
|
||||||
pinGame = game;
|
pinGame = game;
|
||||||
|
@ -17,17 +19,32 @@ namespace BizHawk.Emulation.Computers.Commodore64.Cartridges
|
||||||
|
|
||||||
romA = new byte[0x2000];
|
romA = new byte[0x2000];
|
||||||
romB = new byte[0x2000];
|
romB = new byte[0x2000];
|
||||||
|
validCartridge = true;
|
||||||
|
|
||||||
Array.Copy(data, 0x0000, romA, 0x0000, 0x2000);
|
// we can expect three different configurations:
|
||||||
|
// bank of 4k, bank of 8k, or two banks of 8k
|
||||||
|
|
||||||
if (data.Length == 0x2000)
|
if (data.Length == 0x1000)
|
||||||
{
|
{
|
||||||
|
Array.Copy(data, 0x0000, romA, 0x0000, 0x1000);
|
||||||
|
Array.Copy(data, 0x0000, romA, 0x1000, 0x1000);
|
||||||
for (int i = 0; i < 0x2000; i++)
|
for (int i = 0; i < 0x2000; i++)
|
||||||
romB[i] = 0xFF;
|
romB[i] = 0xFF;
|
||||||
}
|
}
|
||||||
|
else if (data.Length == 0x2000)
|
||||||
|
{
|
||||||
|
Array.Copy(data, 0x0000, romA, 0x0000, 0x2000);
|
||||||
|
for (int i = 0; i < 0x2000; i++)
|
||||||
|
romB[i] = 0xFF;
|
||||||
|
}
|
||||||
|
else if (data.Length == 0x4000)
|
||||||
|
{
|
||||||
|
Array.Copy(data, 0x0000, romA, 0x0000, 0x2000);
|
||||||
|
Array.Copy(data, 0x2000, romB, 0x0000, 0x2000);
|
||||||
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
Array.Copy(data, 0x2000, romB, 0x0000, 0x2000);
|
validCartridge = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
HardReset();
|
HardReset();
|
||||||
|
|
|
@ -0,0 +1,72 @@
|
||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Text;
|
||||||
|
|
||||||
|
namespace BizHawk.Emulation.Computers.Commodore64.Cartridges
|
||||||
|
{
|
||||||
|
public class Mapper0012 : Cartridge
|
||||||
|
{
|
||||||
|
private byte[] bankMain;
|
||||||
|
private byte[][] bankHigh;
|
||||||
|
private byte[] bankHighSelected;
|
||||||
|
private byte[] dummyBank;
|
||||||
|
|
||||||
|
// Zaxxon and Super Zaxxon cartridges
|
||||||
|
// - read to 8xxx selects bank 0 in A000-BFFF
|
||||||
|
// - read to 9xxx selects bank 1 in A000-BFFF
|
||||||
|
|
||||||
|
public Mapper0012(List<uint> newAddresses, List<uint> newBanks, List<byte[]> newData)
|
||||||
|
{
|
||||||
|
bankMain = new byte[0x2000];
|
||||||
|
bankHigh = new byte[2][];
|
||||||
|
dummyBank = new byte[0x2000];
|
||||||
|
|
||||||
|
// create dummy bank just in case
|
||||||
|
for (uint i = 0; i < 0x2000; i++)
|
||||||
|
dummyBank[i] = 0xFF;
|
||||||
|
|
||||||
|
bankHigh[0] = dummyBank;
|
||||||
|
bankHigh[1] = dummyBank;
|
||||||
|
|
||||||
|
// load in the banks
|
||||||
|
for (int i = 0; i < newAddresses.Count; i++)
|
||||||
|
{
|
||||||
|
if (newAddresses[i] == 0x8000)
|
||||||
|
Array.Copy(newData[i], bankMain, 0x1000);
|
||||||
|
else if (newAddresses[i] == 0xA000 && newBanks[i] < 2)
|
||||||
|
bankHigh[newBanks[i]] = newData[i];
|
||||||
|
}
|
||||||
|
|
||||||
|
// mirror the main rom from 8000 to 9000
|
||||||
|
Array.Copy(bankMain, 0x0000, bankMain, 0x1000, 0x1000);
|
||||||
|
|
||||||
|
// set both pins low for 16k rom config
|
||||||
|
pinExRom = false;
|
||||||
|
pinGame = false;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
public override byte Peek8000(int addr)
|
||||||
|
{
|
||||||
|
return bankMain[addr];
|
||||||
|
}
|
||||||
|
|
||||||
|
public override byte PeekA000(int addr)
|
||||||
|
{
|
||||||
|
return bankHighSelected[addr];
|
||||||
|
}
|
||||||
|
|
||||||
|
public override byte Read8000(ushort addr)
|
||||||
|
{
|
||||||
|
uint bank = (addr & (uint)0x1000) >> 12;
|
||||||
|
bankHighSelected = bankHigh[bank];
|
||||||
|
return bankMain[addr];
|
||||||
|
}
|
||||||
|
|
||||||
|
public override byte ReadA000(ushort addr)
|
||||||
|
{
|
||||||
|
return bankHighSelected[addr];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -168,20 +168,20 @@ namespace BizHawk.Emulation.Computers.Commodore64.MOS
|
||||||
},
|
},
|
||||||
new uint[] // BA
|
new uint[] // BA
|
||||||
{
|
{
|
||||||
0x0834, 0x0834,
|
0x0843, 0x0843,
|
||||||
0x0345, 0x0345,
|
0x0543, 0x0543,
|
||||||
0x0845, 0x0845,
|
0x0548, 0x0548,
|
||||||
0x0456, 0x0456,
|
0x0546, 0x0546,
|
||||||
0x0856, 0x0856,
|
0x0586, 0x0586,
|
||||||
|
|
||||||
0x0567, 0x0567,
|
0x0576, 0x0576,
|
||||||
0x0867, 0x0867,
|
0x0876, 0x0876,
|
||||||
0x0887, 0x0887,
|
0x0876, 0x0876,
|
||||||
0x0887, 0x0887,
|
0x0878, 0x0878,
|
||||||
0x0000, 0x0000,
|
0x0878, 0x0878,
|
||||||
|
|
||||||
0x0000, 0x0000,
|
0x0000, 0x0000,
|
||||||
0x1000, 0x1000,
|
0x1000, 0x1000, // 12: badline
|
||||||
0x1000, 0x1000,
|
0x1000, 0x1000,
|
||||||
0x1000, 0x1000,
|
0x1000, 0x1000,
|
||||||
0x1000, 0x1000,
|
0x1000, 0x1000,
|
||||||
|
@ -232,17 +232,17 @@ namespace BizHawk.Emulation.Computers.Commodore64.MOS
|
||||||
0x1000, 0x1000,
|
0x1000, 0x1000,
|
||||||
0x1000, 0x1000,
|
0x1000, 0x1000,
|
||||||
0x1000, 0x1000,
|
0x1000, 0x1000,
|
||||||
0x1000, 0x1000,
|
0x0880, 0x0880, // 55: sprites
|
||||||
|
|
||||||
0x0880, 0x0880,
|
0x0880, 0x0880,
|
||||||
0x0880, 0x0880,
|
0x0810, 0x0810,
|
||||||
0x0801, 0x0801,
|
0x0810, 0x0810,
|
||||||
0x0012, 0x0012,
|
0x0210, 0x0210,
|
||||||
0x0812, 0x0812,
|
0x0218, 0x0218,
|
||||||
|
|
||||||
0x0123, 0x0123,
|
0x0213, 0x0213,
|
||||||
0x0823, 0x0823,
|
0x0283, 0x0283,
|
||||||
0x0234, 0x0234
|
0x0243, 0x0243
|
||||||
},
|
},
|
||||||
new uint[] // actions
|
new uint[] // actions
|
||||||
{
|
{
|
||||||
|
|
|
@ -171,7 +171,7 @@ namespace BizHawk.Emulation.Computers.Commodore64.MOS
|
||||||
backgroundColor1 = 0;
|
backgroundColor1 = 0;
|
||||||
backgroundColor2 = 0;
|
backgroundColor2 = 0;
|
||||||
backgroundColor3 = 0;
|
backgroundColor3 = 0;
|
||||||
baCount = 4;
|
baCount = baResetCounter;
|
||||||
badline = false;
|
badline = false;
|
||||||
badlineEnable = false;
|
badlineEnable = false;
|
||||||
bitmapMode = false;
|
bitmapMode = false;
|
||||||
|
@ -243,9 +243,10 @@ namespace BizHawk.Emulation.Computers.Commodore64.MOS
|
||||||
private void UpdateBA()
|
private void UpdateBA()
|
||||||
{
|
{
|
||||||
if (pinBA)
|
if (pinBA)
|
||||||
baCount = 4;
|
baCount = baResetCounter;
|
||||||
else if (baCount > 0)
|
else if (baCount > 0)
|
||||||
baCount--;
|
baCount--;
|
||||||
|
pinAEC = (baCount > 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void UpdateBorder()
|
private void UpdateBorder()
|
||||||
|
@ -279,12 +280,17 @@ namespace BizHawk.Emulation.Computers.Commodore64.MOS
|
||||||
protected const uint pipelineChkSprDisp = 512;
|
protected const uint pipelineChkSprDisp = 512;
|
||||||
protected const uint pipelineUpdateRc = 1024;
|
protected const uint pipelineUpdateRc = 1024;
|
||||||
|
|
||||||
|
protected const uint rasterIrqLine0Cycle = 1;
|
||||||
|
protected const uint rasterIrqLineXCycle = 0;
|
||||||
|
|
||||||
|
protected const uint baResetCounter = 4;
|
||||||
|
|
||||||
// ------------------------------------
|
// ------------------------------------
|
||||||
|
|
||||||
public void ExecutePhase1()
|
public void ExecutePhase1()
|
||||||
{
|
{
|
||||||
// raster IRQ compare
|
// raster IRQ compare
|
||||||
if ((cycle == 0 && rasterLine > 0) || (cycle == 1 && rasterLine == 0))
|
if ((cycle == rasterIrqLineXCycle && rasterLine > 0) || (cycle == rasterIrqLine0Cycle && rasterLine == 0))
|
||||||
{
|
{
|
||||||
if (rasterLine != lastRasterLine)
|
if (rasterLine != lastRasterLine)
|
||||||
if (rasterLine == rasterInterruptLine)
|
if (rasterLine == rasterInterruptLine)
|
||||||
|
@ -327,6 +333,9 @@ namespace BizHawk.Emulation.Computers.Commodore64.MOS
|
||||||
xOffset = 0;
|
xOffset = 0;
|
||||||
Render();
|
Render();
|
||||||
|
|
||||||
|
// if the BA counter is nonzero, allow CPU bus access
|
||||||
|
UpdateBA();
|
||||||
|
|
||||||
// must always come last
|
// must always come last
|
||||||
UpdatePins();
|
UpdatePins();
|
||||||
}
|
}
|
||||||
|
@ -355,10 +364,6 @@ namespace BizHawk.Emulation.Computers.Commodore64.MOS
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// if the BA counter is nonzero, allow CPU bus access
|
|
||||||
UpdateBA();
|
|
||||||
pinAEC = (baCount > 0);
|
|
||||||
|
|
||||||
Render();
|
Render();
|
||||||
|
|
||||||
// must always come last
|
// must always come last
|
||||||
|
@ -367,7 +372,6 @@ namespace BizHawk.Emulation.Computers.Commodore64.MOS
|
||||||
|
|
||||||
private void ParseCycle()
|
private void ParseCycle()
|
||||||
{
|
{
|
||||||
bool baPinThisCycle = true;
|
|
||||||
ushort addr = 0x3FFF;
|
ushort addr = 0x3FFF;
|
||||||
uint cycleBAsprite0;
|
uint cycleBAsprite0;
|
||||||
uint cycleBAsprite1;
|
uint cycleBAsprite1;
|
||||||
|
@ -477,10 +481,10 @@ namespace BizHawk.Emulation.Computers.Commodore64.MOS
|
||||||
switch (ba)
|
switch (ba)
|
||||||
{
|
{
|
||||||
case 0x0000:
|
case 0x0000:
|
||||||
baPinThisCycle = true;
|
pinBA = true;
|
||||||
break;
|
break;
|
||||||
case 0x1000:
|
case 0x1000:
|
||||||
baPinThisCycle = !badline;
|
pinBA = !badline;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
cycleBAsprite0 = ba & 0x000F;
|
cycleBAsprite0 = ba & 0x000F;
|
||||||
|
@ -489,10 +493,11 @@ namespace BizHawk.Emulation.Computers.Commodore64.MOS
|
||||||
if ((cycleBAsprite0 < 8 && sprites[cycleBAsprite0].dma) ||
|
if ((cycleBAsprite0 < 8 && sprites[cycleBAsprite0].dma) ||
|
||||||
(cycleBAsprite1 < 8 && sprites[cycleBAsprite1].dma) ||
|
(cycleBAsprite1 < 8 && sprites[cycleBAsprite1].dma) ||
|
||||||
(cycleBAsprite2 < 8 && sprites[cycleBAsprite2].dma))
|
(cycleBAsprite2 < 8 && sprites[cycleBAsprite2].dma))
|
||||||
baPinThisCycle = false;
|
pinBA = false;
|
||||||
|
else
|
||||||
|
pinBA = true;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
pinBA = baPinThisCycle;
|
|
||||||
|
|
||||||
// perform actions
|
// perform actions
|
||||||
borderCheckLEnable = true;
|
borderCheckLEnable = true;
|
||||||
|
|
Loading…
Reference in New Issue