Cleaned up Virtal Boy slot code.

vboy.xml updates:
* Set width and endianness for all ROM regions
* Added width and endianness for SRAM, assuming all cartridges have 8k*32 SRAM for now
* Removed mirroring - this is an implementation detail
* Removed "slot" features - there's enough information to work this out anyway

bus/vboy updates:
* Made slot probe software part to determine cartridge type
* Made cartridges responsible for installing themselves
* Added support for arbitrary cartridge sizes, assuming simplistic decoding
* Added support for 8-bit and 16-bit SRAM on LSBs
* Added support for EXP space and INTCRO output
* Fixed SRAM not being loaded

bus/generic: added a helper for mapping non-power-of-two memory with simple decoding

cpu/v810: send I/O accesses to program space if I/O space is unconfigured

vboy.cpp: updated for changed slot and CPU code

bus/wswan: added notes

The Virtual Boy software list is still in pretty poor shape.  It's
assuming all carts with SRAM have 8k*32, there are a bunch of feature
tags for ICs that don't actually give an IC type, making them useless,
3-D Tetris mentions a battery but doesn't have an SRAM data area,
Virtual Fishing refers to a HY6254ALLJ-10 which isn't a real part (I
assume it means HY6264ALLJ-10 which is an 8k*8 50µA standby SRAM).
This commit is contained in:
Vas Crabb 2019-11-03 02:05:07 +11:00
parent 82e6de6f02
commit 295174e4e8
10 changed files with 629 additions and 517 deletions

View File

@ -26,10 +26,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<feature name="u2" value="U2" />
<feature name="u3" value="U3" />
<feature name="battery" value="BT1" />
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="1048576" width="32" endianness="little">
<rom name="vue-vpbe-0.u1" size="1048576" crc="bb71b522" sha1="5177015a91442e56bd76af39447bca365e06c272" offset="000000" />
<rom size="1048576" offset="0x100000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -42,8 +40,7 @@ According to Planet Virtual Boy, the following undumped protos exist
<publisher>Nintendo</publisher>
<info name="serial" value="VUE-VBHE-JPN, VUE-VBHE-USA"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="2097152" width="32" endianness="little">
<rom name="bound high! (ju).bin" size="2097152" crc="e81a3703" sha1="1196ef8b9a96a0ff2f3634f8eb1c4865c0fb6b01" offset="000000" />
</dataarea>
</part>
@ -57,10 +54,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VGPJ-JPN, VUE-VGPJ-USA"/>
<info name="release" value="19950701 (JPN), 19950814 (USA)"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="1048576" width="32" endianness="little">
<rom name="galactic pinball (japan, usa).bin" size="1048576" crc="c9710a36" sha1="93a25abf4f86e71a49c1c3a470140bb40cb693d6" offset="000000" />
<rom size="1048576" offset="0x100000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -73,11 +68,10 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VVGE-USA"/>
<info name="release" value="199511xx"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_eeprom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="2097152" width="32" endianness="little">
<rom name="golf (usa).bin" size="2097152" crc="2199af41" sha1="23ce3c174789cdd306497d86cb2c4e76ba8b06e5" offset="000000" />
</dataarea>
<dataarea name="eeprom" size="0x10000">
<dataarea name="sram" size="0x10000" width="32" endianness="little">
</dataarea>
</part>
</software>
@ -90,10 +84,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VIMJ-JPN"/>
<info name="release" value="19951013"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="1048576" width="32" endianness="little">
<rom name="innsmouth no yakata (japan).bin" size="1048576" crc="83cb6a00" sha1="37e06e53ce2810e870835c48decdd6c72079bfda" offset="000000" />
<rom size="1048576" offset="0x100000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -108,10 +100,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<part name="cart" interface="vboy_cart">
<feature name="pcb" value="VUE-AA-01(K)" />
<feature name="u1" value="U1 PRG" />
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="1048576" width="32" endianness="little">
<rom name="vue-vjbe-0.u1" size="1048576" crc="a44de03c" sha1="0e086d7ef2bd8b97315196943fd0b71da07aa8f1" offset="000000" />
<rom size="1048576" offset="0x100000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -124,10 +114,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VJBJ-JPN"/>
<info name="release" value="19950929"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="1048576" width="32" endianness="little">
<rom name="jack bros. no meiro de hiihoo! (japan).bin" size="1048576" crc="cab61e8b" sha1="a973406590382ee503037271330d68d2834b79db" offset="000000" />
<rom size="1048576" offset="0x100000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -142,10 +130,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<part name="cart" interface="vboy_cart">
<feature name="pcb" value="VUE-AA-01" />
<feature name="u1" value="U1 PRG" />
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="1048576" width="32" endianness="little">
<rom name="vue-vmcj-0.u1" size="1048576" crc="a47de78c" sha1="7556a778b60490bdb81774bcbaa7413fc84cb985" offset="000000" />
<rom size="1048576" offset="0x100000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -158,12 +144,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VMTJ-JPN, VUE-VMTJ-USA"/>
<info name="release" value="19950721 (JPN), 19950814 (USA)"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="524288" width="32" endianness="little">
<rom name="mario's tennis (japan, usa).bin" size="524288" crc="7ce7460d" sha1="5162f7fa9e3eae4338c53ccba641ba080c768754" offset="000000" />
<rom size="524288" offset="0x080000" loadflag="reload" />
<rom size="524288" offset="0x100000" loadflag="reload" />
<rom size="524288" offset="0x180000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -178,8 +160,7 @@ According to Planet Virtual Boy, the following undumped protos exist
<part name="cart" interface="vboy_cart">
<feature name="pcb" value="VUE-AA-01" />
<feature name="u1" value="U1 PRG" />
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="2097152" width="32" endianness="little">
<rom name="vue-vnfe-0.u1" size="2097152" crc="df4d56b4" sha1="f4a4c7928f15102cf14c90c5f044e5f7cc7c32f9" offset="000000" />
</dataarea>
</part>
@ -191,10 +172,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<publisher>Bullet-Proof Software</publisher>
<info name="alt_title" value="ニコちゃんバトル"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="1048576" width="32" endianness="little">
<rom name="nikochan battle (j)(prototype).bin" size="1048576" crc="f3cd40dd" sha1="217ca062f65d4e8b2848085918af5ac4b33b12d4" offset="000000" />
<rom size="1048576" offset="0x100000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -209,12 +188,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<part name="cart" interface="vboy_cart">
<feature name="pcb" value="VUE-AA-01" />
<feature name="u1" value="U1 PRG" />
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="524288" width="32" endianness="little">
<rom name="vue-vh2e-0.u1" size="524288" crc="19bb2dfb" sha1="80216b2874cf162f301d571bb8aebc98d80b4f3e" offset="000000" />
<rom size="524288" offset="0x080000" loadflag="reload" />
<rom size="524288" offset="0x100000" loadflag="reload" />
<rom size="524288" offset="0x180000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -227,10 +202,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VREE-USA"/>
<info name="release" value="19950814"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="1048576" width="32" endianness="little">
<rom name="red alarm (usa).bin" size="1048576" crc="aa10a7b4" sha1="494fa60cb8997880b4e8cd3270b21d6c2768a48a" offset="000000" />
<rom size="1048576" offset="0x100000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -243,10 +216,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VREJ-JPN"/>
<info name="release" value="19950721"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="1048576" width="32" endianness="little">
<rom name="red alarm (japan).bin" size="1048576" crc="7e85c45d" sha1="f5057fa9bfd9d60b9dcfc004cfdd12aa8eb1cb4a" offset="000000" />
<rom size="1048576" offset="0x100000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -259,10 +230,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VSDJ-JPN"/>
<info name="release" value="19951222"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="1048576" width="32" endianness="little">
<rom name="sd gundam - dimension war (japan).bin" size="1048576" crc="44788197" sha1="1a67f6bdb45db46e22b8aadea754a68ad379ae29" offset="000000" />
<rom size="1048576" offset="0x100000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -275,12 +244,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VSPJ-JPN"/>
<info name="release" value="19951201"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="524288" width="32" endianness="little">
<rom name="space invaders - virtual collection (japan).bin" size="524288" crc="fa44402d" sha1="16ad904faafd24642dfd056d10a768e81f0d9bfa" offset="000000" />
<rom size="524288" offset="0x080000" loadflag="reload" />
<rom size="524288" offset="0x100000" loadflag="reload" />
<rom size="524288" offset="0x180000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -290,8 +255,7 @@ According to Planet Virtual Boy, the following undumped protos exist
<year>1995</year>
<publisher>Nintendo</publisher>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="2097152" width="32" endianness="little">
<rom name="space pinball prototype (j).bin" size="2097152" crc="44c2b723" sha1="dc182360c7c8d26323db8921f09db76638e81ced" offset="000000" />
</dataarea>
</part>
@ -305,12 +269,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VSSJ-JPN"/>
<info name="release" value="19950929"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="524288" width="32" endianness="little">
<rom name="space squash (japan).bin" size="524288" crc="60895693" sha1="3f08cae2b6f9e386529949ff954220860db1af64" offset="000000" />
<rom size="524288" offset="0x080000" loadflag="reload" />
<rom size="524288" offset="0x100000" loadflag="reload" />
<rom size="524288" offset="0x180000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -323,12 +283,10 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VTBJ-JPN, VUE-VTBJ-USA"/>
<info name="release" value="19950721 (JPN), 19950814 (USA)"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_eeprom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="1048576" width="32" endianness="little">
<rom name="teleroboxer (japan, usa).bin" size="1048576" crc="36103000" sha1="c59e020f9674774c5cbc022317ebba0eb1d744f7" offset="000000" />
<rom size="1048576" offset="0x100000" loadflag="reload" />
</dataarea>
<dataarea name="eeprom" size="0x10000">
<dataarea name="sram" size="0x10000" width="32" endianness="little">
</dataarea>
</part>
</software>
@ -341,12 +299,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VH2J-JPN"/>
<info name="release" value="19950721"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="524288" width="32" endianness="little">
<rom name="tobidase! panibon (japan).bin" size="524288" crc="40498f5e" sha1="b8a12a9677afa5cbce6ed43eb0effb5a02875534" offset="000000" />
<rom size="524288" offset="0x080000" loadflag="reload" />
<rom size="524288" offset="0x100000" loadflag="reload" />
<rom size="524288" offset="0x180000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -359,10 +313,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VVBJ-JPN"/>
<info name="release" value="19951222"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="1048576" width="32" endianness="little">
<rom name="virtual bowling (japan).bin" size="1048576" crc="20688279" sha1="a5be7654037050f0a781e70efea0191f43d26f06" offset="000000" />
<rom size="1048576" offset="0x100000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -380,12 +332,10 @@ According to Planet Virtual Boy, the following undumped protos exist
<feature name="u2" value="U2 [HY6254ALLJ-10]" />
<feature name="u3" value="U3 [??]" />
<feature name="battery" value="BT1" />
<feature name="slot" value="vb_eeprom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="1048576" width="32" endianness="little">
<rom name="vue-vvfj-0.u1" size="1048576" crc="526cc969" sha1="583b409b7215159219d08e789db46140062095f2" offset="000000" />
<rom size="1048576" offset="0x100000" loadflag="reload" />
</dataarea>
<dataarea name="eeprom" size="0x10000">
<dataarea name="sram" size="0x10000" width="32" endianness="little">
</dataarea>
</part>
</software>
@ -398,10 +348,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VH3E-USA"/>
<info name="release" value="19951201"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="1048576" width="32" endianness="little">
<rom name="vertical force (usa).bin" size="1048576" crc="4c32ba5e" sha1="38f9008f60b09deef1151d46b905b090a0338200" offset="000000" />
<rom size="1048576" offset="0x100000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -414,10 +362,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VH3J-JPN"/>
<info name="release" value="19950812"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="1048576" width="32" endianness="little">
<rom name="vertical force (japan).bin" size="1048576" crc="9e9b8b92" sha1="c7204ba5cfe7d26394b5e22badc580c8ed8c0b37" offset="000000" />
<rom size="1048576" offset="0x100000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -430,11 +376,10 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VVGJ-JPN"/>
<info name="release" value="19950811"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_eeprom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="2097152" width="32" endianness="little">
<rom name="t&amp;e virtual golf (japan).bin" size="2097152" crc="6ba07915" sha1="c595285d42c69f14b2b418c1edfbe4a7f9a624b6" offset="000000" />
</dataarea>
<dataarea name="eeprom" size="0x10000">
<dataarea name="sram" size="0x10000" width="32" endianness="little">
</dataarea>
</part>
</software>
@ -449,10 +394,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<part name="cart" interface="vboy_cart">
<feature name="pcb" value="VUE-AA-01" />
<feature name="u1" value="U1 PRG" />
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="1048576" width="32" endianness="little">
<rom name="vue-vjvj-0.u1" size="1048576" crc="8989fe0a" sha1="d96c9f8aac5b4ea012a8fe659bb68fb1159a9c6d" offset="000000" />
<rom size="1048576" offset="0x100000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -465,10 +408,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VVPE-USA"/>
<info name="release" value="19950911"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="1048576" width="32" endianness="little">
<rom name="virtual league baseball (usa).bin" size="1048576" crc="736b40d6" sha1="266fe615ee3df1160a20b456824699f16810fa28" offset="000000" />
<rom size="1048576" offset="0x100000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -481,10 +422,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VVPJ-JPN"/>
<info name="release" value="19950811"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="1048576" width="32" endianness="little">
<rom name="virtual pro yakyuu '95 (japan).bin" size="1048576" crc="9ba8bb5e" sha1="ab8fa82b79512eefefccdccea6768078a374c4aa" offset="000000" />
<rom size="1048576" offset="0x100000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -497,12 +436,8 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VTRJ-JPN"/>
<info name="release" value="19950825"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="524288" width="32" endianness="little">
<rom name="v-tetris (japan).bin" size="524288" crc="3ccb67ae" sha1="ff7d4dfc467e6e0d3fe8517102132a65a9d17589" offset="000000" />
<rom size="524288" offset="0x080000" loadflag="reload" />
<rom size="524288" offset="0x100000" loadflag="reload" />
<rom size="524288" offset="0x180000" loadflag="reload" />
</dataarea>
</part>
</software>
@ -515,11 +450,10 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VWCJ-JPN, VUE-VWCJ-USA"/>
<info name="release" value="19951201 (JPN), 199511xx (USA)"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_eeprom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="2097152" width="32" endianness="little">
<rom name="virtual boy wario land (japan, usa).bin" size="2097152" crc="133e9372" sha1="274c328fbd904f20e69172ab826bf8f94ced1bdb" offset="000000" />
</dataarea>
<dataarea name="eeprom" size="0x10000">
<dataarea name="sram" size="0x10000" width="32" endianness="little">
</dataarea>
</part>
</software>
@ -532,8 +466,7 @@ According to Planet Virtual Boy, the following undumped protos exist
<info name="serial" value="VUE-VWEE-USA"/>
<info name="release" value="19951221"/>
<part name="cart" interface="vboy_cart">
<feature name="slot" value="vb_rom" />
<dataarea name="rom" size="2097152">
<dataarea name="rom" size="2097152" width="32" endianness="little">
<rom name="waterworld (usa).bin" size="2097152" crc="82a95e51" sha1="dcc46484bd0acab0ac1ea178f425a0f5ccfb8dc2" offset="000000" />
</dataarea>
</part>

View File

@ -7,6 +7,8 @@
#include "softlist_dev.h"
#include <cassert>
/***************************************************************************
TYPE DEFINITIONS
@ -15,6 +17,41 @@
class device_generic_cart_interface : public device_interface
{
public:
// TODO: find a better home for this helper
template <unsigned Shift, typename T>
static void install_non_power_of_two(
offs_t length,
offs_t decode_limit,
offs_t decode_mask,
offs_t decode_offset,
offs_t base,
T &&install)
{
assert(!(decode_limit & base));
for (offs_t remain = length, start = 0U; remain && (decode_limit >= start); )
{
unsigned const msb(31 - count_leading_zeros(u32(remain)));
offs_t const chunk(offs_t(1) << msb);
offs_t range((chunk - 1) & decode_limit);
offs_t mirror(decode_limit & ~decode_mask & ~range);
// TODO: deal with small offsets - probably requires breaking into smaller chunks with mirror set
if (decode_offset & range)
throw emu_fatalerror("Can't deal with offset/size combination\n");
range = (range << Shift) | ((offs_t(1) << Shift) - 1);
mirror <<= Shift;
offs_t const begin(start << Shift);
offs_t const end(begin | range);
offs_t const src(start | ((chunk - 1) & decode_offset));
install(base | begin, base | end, mirror, src);
remain ^= chunk;
start ^= chunk;
}
}
// construction/destruction
virtual ~device_generic_cart_interface();

View File

@ -1,59 +1,207 @@
// license:BSD-3-Clause
// copyright-holders:Fabio Priuli
/***********************************************************************************************************
Nintendo Virtual Boy cart emulation
***********************************************************************************************************/
/***************************************************************************
Virtual Boy cartridges
***************************************************************************/
#include "emu.h"
#include "rom.h"
#include "bus/generic/slot.h"
//-------------------------------------------------
// vboy_rom_device - constructor
//-------------------------------------------------
DEFINE_DEVICE_TYPE(VBOY_ROM_STD, vboy_rom_device, "vboy_rom", "Nintendo Virtual Boy Carts")
DEFINE_DEVICE_TYPE(VBOY_ROM_EEPROM, vboy_eeprom_device, "vboy_eeprom", "Nintendo Virtual Boy Carts + EEPROM")
//#define VERBOSE 1
#include "logmacro.h"
vboy_rom_device::vboy_rom_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock)
: device_t(mconfig, type, tag, owner, clock), device_vboy_cart_interface(mconfig, *this)
{
}
//**************************************************************************
// GLOBAL VARIABLES
//**************************************************************************
vboy_rom_device::vboy_rom_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock)
: vboy_rom_device(mconfig, VBOY_ROM_STD, tag, owner, clock)
{
}
DEFINE_DEVICE_TYPE(VBOY_FLAT_ROM, vboy_flat_rom_device, "vboy_flatrom", "Nintendo Virtual Boy Flat ROM Cartridge")
DEFINE_DEVICE_TYPE(VBOY_FLAT_ROM_SRAM, vboy_flat_rom_sram_device, "vboy_flatrom_sram", "Nintendo Virtual Boy Flat ROM Cartridge with Backup SRAM")
vboy_eeprom_device::vboy_eeprom_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock)
: vboy_rom_device(mconfig, VBOY_ROM_EEPROM, tag, owner, clock)
//**************************************************************************
// vboy_flat_rom_device
//**************************************************************************
vboy_flat_rom_device::vboy_flat_rom_device(machine_config const &mconfig, char const *tag, device_t *owner, u32 clock) :
vboy_flat_rom_device(mconfig, VBOY_FLAT_ROM, tag, owner, clock)
{
}
/*-------------------------------------------------
mapper specific handlers
-------------------------------------------------*/
READ32_MEMBER(vboy_rom_device::read_cart)
vboy_flat_rom_device::vboy_flat_rom_device(machine_config const &mconfig, device_type type, char const *tag, device_t *owner, u32 clock) :
device_t(mconfig, type, tag, owner, clock),
device_vboy_cart_interface(mconfig, *this)
{
return m_rom[offset & m_rom_mask];
}
READ32_MEMBER(vboy_eeprom_device::read_eeprom)
image_init_result vboy_flat_rom_device::load()
{
return m_eeprom[offset];
// if the host has supplied a ROM space, install with appropriate mirroring
memory_region *const romregion(memregion("^rom"));
if (rom_space() && romregion)
{
// the slot should have verified that the ROM is a supported size
assert(!(romregion->bytes() & 0x0000'0003U));
assert(romregion->bytes() <= 0x0100'0000U);
// this should fail a validity check
assert(!(rom_base() & 0x00ff'ffff));
device_generic_cart_interface::install_non_power_of_two<2>(
romregion->bytes() >> 2,
0x00ff'ffff >> 2,
0,
0,
rom_base(),
[this, rom = reinterpret_cast<u32 *>(romregion->base())] (offs_t begin, offs_t end, offs_t mirror, offs_t src)
{
LOG(
"Install ROM 0x%08X-0x%08X at 0x%08X-0x%08X mirror %08X\n",
src << 2,
(src << 2) + (end - begin),
begin,
end,
mirror);
rom_space()->install_rom(begin, end, mirror, &rom[src]);
});
}
return image_init_result::PASS;
}
WRITE32_MEMBER(vboy_eeprom_device::write_eeprom)
void vboy_flat_rom_device::device_start()
{
COMBINE_DATA(&m_eeprom[offset]);
}
//**************************************************************************
// vboy_flat_rom_sram_device
//**************************************************************************
vboy_flat_rom_sram_device::vboy_flat_rom_sram_device(machine_config const &mconfig, char const *tag, device_t *owner, u32 clock) :
vboy_flat_rom_device(mconfig, VBOY_FLAT_ROM_SRAM, tag, owner, clock)
{
}
image_init_result vboy_flat_rom_sram_device::load()
{
image_init_result const result(vboy_flat_rom_device::load());
if (image_init_result::PASS != result)
return result;
memory_region *const sramregion(memregion("^sram"));
if (sramregion)
{
// this should fail a validity check
assert(!(chip_base() & 0x00ff'ffff));
switch (sramregion->bitwidth())
{
case 8:
if (chip_space())
{
device_generic_cart_interface::install_non_power_of_two<2>(
sramregion->bytes(),
0x00ff'ffff >> 2,
0,
0,
chip_base(),
[this, sramregion] (offs_t begin, offs_t end, offs_t mirror, offs_t src)
{
LOG(
"Install SRAM 0x%08X-0x%08X at 0x%08X-0x%08X mirror %08X\n",
src,
src + ((end - begin) >> 2),
begin,
end,
mirror);
u8 *const base(&reinterpret_cast<u8 *>(sramregion->base())[src]);
chip_space()->install_readwrite_handler(
begin,
end,
read8sm_delegate(*this, NAME([base] (offs_t offset) { return base[offset]; })),
write8sm_delegate(*this, NAME([base] (offs_t offset, u8 data) { base[offset] = data; })),
0x0000'00ff);
});
}
save_pointer(NAME(&sramregion->as_u8()), sramregion->bytes());
break;
case 16:
if (chip_space())
{
device_generic_cart_interface::install_non_power_of_two<2>(
sramregion->bytes() >> 1,
0x00ff'ffff >> 2,
0,
0,
chip_base(),
[this, sramregion] (offs_t begin, offs_t end, offs_t mirror, offs_t src)
{
LOG(
"Install SRAM 0x%08X-0x%08X at 0x%08X-0x%08X mirror %08X\n",
src << 1,
(src << 1) + ((end - begin) >> 1),
begin,
end,
mirror);
u16 *const base(&reinterpret_cast<u16 *>(sramregion->base())[src]);
chip_space()->install_readwrite_handler(
begin,
end,
read16s_delegate(*this, NAME([base] (offs_t offset, u16 mem_mask) { return base[offset]; })),
write16s_delegate(*this, NAME([base] (offs_t offset, u16 data, u16 mem_mask) { COMBINE_DATA(base + offset); })),
0x0000'ffff);
});
}
save_pointer(NAME(&sramregion->as_u16()), sramregion->bytes() >> 1);
break;
case 32:
if (chip_space())
{
device_generic_cart_interface::install_non_power_of_two<2>(
sramregion->bytes() >> 2,
0x00ff'ffff >> 2,
0,
0,
chip_base(),
[this, sram = reinterpret_cast<u32 *>(sramregion->base())] (offs_t begin, offs_t end, offs_t mirror, offs_t src)
{
LOG(
"Install SRAM 0x%08X-0x%08X at 0x%08X-0x%08X mirror %08X\n",
src << 2,
(src << 2) + (end - begin),
begin,
end,
mirror);
chip_space()->install_ram(begin, end, mirror, &sram[src]);
});
}
save_pointer(NAME(&sramregion->as_u32()), sramregion->bytes() >> 2);
break;
default:
throw emu_fatalerror("Unsupported Virtual Boy cartridge backup RAM width\n");
}
battery_load(sramregion->base(), sramregion->bytes(), nullptr);
}
return image_init_result::PASS;
}
void vboy_flat_rom_sram_device::unload()
{
memory_region *const sramregion(memregion("^sram"));
if (sramregion)
battery_save(sramregion->base(), sramregion->bytes());
}

View File

@ -1,5 +1,5 @@
// license:BSD-3-Clause
// copyright-holders:Fabio Priuli
// copyright-holders:Vas Crabb
#ifndef MAME_BUS_VBOY_ROM_H
#define MAME_BUS_VBOY_ROM_H
@ -8,41 +8,43 @@
#include "slot.h"
// ======================> vboy_rom_device
//**************************************************************************
// CLASS DECLARATIONS
//**************************************************************************
class vboy_rom_device : public device_t,
public device_vboy_cart_interface
class vboy_flat_rom_device : public device_t, public device_vboy_cart_interface
{
public:
// construction/destruction
vboy_rom_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock);
vboy_flat_rom_device(machine_config const &mconfig, char const *tag, device_t *owner, u32 clock);
// reading and writing
virtual DECLARE_READ32_MEMBER(read_cart) override;
// device_vboy_cart_interface implementation
virtual image_init_result load() override ATTR_COLD;
protected:
vboy_rom_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock);
vboy_flat_rom_device(machine_config const &mconfig, device_type type, char const *tag, device_t *owner, u32 clock);
// device-level overrides
virtual void device_start() override { }
// device_t implementation
virtual void device_start() override ATTR_COLD;
};
// ======================> vboy_eeprom_device
class vboy_eeprom_device : public vboy_rom_device
class vboy_flat_rom_sram_device : public vboy_flat_rom_device
{
public:
// construction/destruction
vboy_eeprom_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock);
vboy_flat_rom_sram_device(machine_config const &mconfig, char const *tag, device_t *owner, u32 clock);
// reading and writing
virtual DECLARE_READ32_MEMBER(read_eeprom) override;
virtual DECLARE_WRITE32_MEMBER(write_eeprom) override;
// device_vboy_cart_interface implementation
virtual image_init_result load() override ATTR_COLD;
virtual void unload() override ATTR_COLD;
};
// device type definition
DECLARE_DEVICE_TYPE(VBOY_ROM_STD, vboy_rom_device)
DECLARE_DEVICE_TYPE(VBOY_ROM_EEPROM, vboy_eeprom_device)
//**************************************************************************
// DEVICE TYPE DECLARATIONS
//**************************************************************************
DECLARE_DEVICE_TYPE(VBOY_FLAT_ROM, vboy_flat_rom_device)
DECLARE_DEVICE_TYPE(VBOY_FLAT_ROM_SRAM, vboy_flat_rom_sram_device)
#endif // MAME_BUS_VBOY_ROM_H

View File

@ -1,250 +1,172 @@
// license:BSD-3-Clause
// copyright-holders:Fabio Priuli
/***********************************************************************************************************
Nintendo Virtual Boy cart emulation
(through slot devices)
***********************************************************************************************************/
// copyright-holders:Vas Crabb
/***************************************************************************
Virtual Boy cartridge slot
***************************************************************************/
#include "emu.h"
#include "slot.h"
#include "emuopts.h"
#include "romload.h"
#include <cstring>
//#define VERBOSE 1
#include "logmacro.h"
//**************************************************************************
// GLOBAL VARIABLES
//**************************************************************************
DEFINE_DEVICE_TYPE(VBOY_CART_SLOT, vboy_cart_slot_device, "vboy_cart_slot", "Nintendo Virtual Boy Cartridge Slot")
//**************************************************************************
// vboy cartridges Interface
//**************************************************************************
//-------------------------------------------------
// device_vboy_cart_interface - constructor
//-------------------------------------------------
device_vboy_cart_interface::device_vboy_cart_interface(const machine_config &mconfig, device_t &device) :
device_interface(device, "vboycart"),
m_rom(nullptr),
m_rom_size(0),
m_rom_mask(0)
{
}
//-------------------------------------------------
// ~device_vboy_cart_interface - destructor
//-------------------------------------------------
device_vboy_cart_interface::~device_vboy_cart_interface()
{
}
//-------------------------------------------------
// rom_alloc - alloc the space for the cart
//-------------------------------------------------
void device_vboy_cart_interface::rom_alloc(uint32_t size, const char *tag)
{
if (m_rom == nullptr)
{
m_rom = (uint32_t *)device().machine().memory().region_alloc(std::string(tag).append(VBOYSLOT_ROM_REGION_TAG).c_str(), size, 4, ENDIANNESS_LITTLE)->base();
m_rom_size = size/4;
m_rom_mask = m_rom_size - 1;
}
}
//-------------------------------------------------
// ram_alloc - alloc the space for the ram
//-------------------------------------------------
void device_vboy_cart_interface::eeprom_alloc(uint32_t size)
{
m_eeprom.resize(size/sizeof(uint32_t));
}
//**************************************************************************
// LIVE DEVICE
// vboy_cart_slot_device
//**************************************************************************
//-------------------------------------------------
// vboy_cart_slot_device - constructor
//-------------------------------------------------
vboy_cart_slot_device::vboy_cart_slot_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) :
vboy_cart_slot_device::vboy_cart_slot_device(machine_config const &mconfig, char const *tag, device_t *owner, u32 clock) :
device_t(mconfig, VBOY_CART_SLOT, tag, owner, clock),
device_image_interface(mconfig, *this),
device_single_card_slot_interface<device_vboy_cart_interface>(mconfig, *this),
m_type(VBOY_STD),
m_intcro(*this),
m_exp_space(*this, finder_base::DUMMY_TAG, -1, 32),
m_chip_space(*this, finder_base::DUMMY_TAG, -1, 32),
m_rom_space(*this, finder_base::DUMMY_TAG, -1, 32),
m_exp_base(0U),
m_chip_base(0U),
m_rom_base(0U),
m_cart(nullptr)
{
}
//-------------------------------------------------
// vboy_cart_slot_device - destructor
//-------------------------------------------------
vboy_cart_slot_device::~vboy_cart_slot_device()
image_init_result vboy_cart_slot_device::call_load()
{
if (!m_cart)
return image_init_result::PASS;
memory_region *romregion(loaded_through_softlist() ? memregion("rom") : nullptr);
if (loaded_through_softlist() && !romregion)
{
seterror(IMAGE_ERROR_INVALIDIMAGE, "Software list item has no 'rom' data area");
return image_init_result::FAIL;
}
u32 const len(loaded_through_softlist() ? romregion->bytes() : length());
if ((0x0000'0003 & len) || (0x0100'0000 < len))
{
seterror(IMAGE_ERROR_UNSUPPORTED, "Unsupported cartridge size (must be a multiple of 4 bytes no larger than 16 MiB)");
return image_init_result::FAIL;
}
if (!loaded_through_softlist())
{
LOG("Allocating %u byte cartridge ROM region\n", len);
romregion = machine().memory().region_alloc(subtag("rom").c_str(), len, 4, ENDIANNESS_LITTLE);
u32 const cnt(fread(romregion->base(), len));
if (cnt != len)
{
seterror(IMAGE_ERROR_UNSPECIFIED, "Error reading cartridge file");
return image_init_result::FAIL;
}
}
return m_cart->load();
}
void vboy_cart_slot_device::call_unload()
{
if (m_cart)
m_cart->unload();
}
void vboy_cart_slot_device::device_validity_check(validity_checker &valid) const
{
if (m_exp_base & 0x00ff'ffff)
osd_printf_error("EXP base address 0x%X is not on a 24-bit boundary\n", m_exp_base);
if (m_chip_base & 0x00ff'ffff)
osd_printf_error("CHIP base address 0x%X is not on a 24-bit boundary\n", m_chip_base);
if (m_rom_base & 0x00ff'ffff)
osd_printf_error("ROM base address 0x%X is not on a 24-bit boundary\n", m_rom_base);
}
void vboy_cart_slot_device::device_resolve_objects()
{
m_intcro.resolve_safe();
}
//-------------------------------------------------
// device_start - device-specific startup
//-------------------------------------------------
void vboy_cart_slot_device::device_start()
{
if (!m_exp_space && ((m_exp_space.finder_tag() != finder_base::DUMMY_TAG) || (m_exp_space.spacenum() >= 0)))
throw emu_fatalerror("%s: Address space %d of device %s not found (EXP)\n", tag(), m_exp_space.spacenum(), m_exp_space.finder_tag());
if (!m_chip_space && ((m_chip_space.finder_tag() != finder_base::DUMMY_TAG) || (m_chip_space.spacenum() >= 0)))
throw emu_fatalerror("%s: Address space %d of device %s not found (CHIP)\n", tag(), m_chip_space.spacenum(), m_chip_space.finder_tag());
if (!m_rom_space && ((m_rom_space.finder_tag() != finder_base::DUMMY_TAG) || (m_rom_space.spacenum() >= 0)))
throw emu_fatalerror("%s: Address space %d of device %s not found (ROM)\n", tag(), m_rom_space.spacenum(), m_rom_space.finder_tag());
m_cart = get_card_device();
}
//-------------------------------------------------
// vboy PCB
//-------------------------------------------------
struct vboy_slot
{
int pcb_id;
const char *slot_option;
};
// Here, we take the feature attribute from .xml (i.e. the PCB name) and we assign a unique ID to it
static const vboy_slot slot_list[] =
{
{ VBOY_STD, "vb_rom" },
{ VBOY_EEPROM, "vb_eeprom" }
};
static int vboy_get_pcb_id(const char *slot)
{
for (auto & elem : slot_list)
{
if (!core_stricmp(elem.slot_option, slot))
return elem.pcb_id;
}
return 0;
}
#if 0
static const char *vboy_get_slot(int type)
{
for (int i = 0; i < ARRAY_LENGTH(slot_list); i++)
{
if (slot_list[i].pcb_id == type)
return slot_list[i].slot_option;
}
return "vb_rom";
}
#endif
/*-------------------------------------------------
call load
-------------------------------------------------*/
image_init_result vboy_cart_slot_device::call_load()
{
if (m_cart)
{
uint8_t *ROM;
uint32_t len = !loaded_through_softlist() ? length() : get_software_region_length("rom");
bool has_eeprom = loaded_through_softlist() && get_software_region("eeprom");
if (len > 0x200000)
{
seterror(IMAGE_ERROR_UNSPECIFIED, "Unsupported cartridge size");
return image_init_result::FAIL;
}
// always alloc 0x200000 so to be able to directly map the region
// to the address map (speeding up emulation a bit)
m_cart->rom_alloc(0x200000, tag());
if (has_eeprom)
m_cart->eeprom_alloc(get_software_region_length("eeprom"));
ROM = (uint8_t *)m_cart->get_rom_base();
if (!loaded_through_softlist())
fread(ROM, len);
else
memcpy(ROM, get_software_region("rom"), len);
if (len < 0x080000) { memcpy(ROM + 0x040000, ROM, 0x040000); }
if (len < 0x100000) { memcpy(ROM + 0x080000, ROM, 0x080000); }
if (len < 0x200000) { memcpy(ROM + 0x100000, ROM, 0x100000); }
if (!loaded_through_softlist())
m_type = vboy_get_pcb_id("vb_rom");
else
{
const char *pcb_name = get_feature("slot");
if (pcb_name)
m_type = vboy_get_pcb_id(pcb_name);
}
//printf("Type: %s\n", vboy_get_slot(m_type));
return image_init_result::PASS;
}
return image_init_result::PASS;
}
/*-------------------------------------------------
call_unload
-------------------------------------------------*/
void vboy_cart_slot_device::call_unload()
{
if (m_cart && m_cart->get_eeprom_base() && m_cart->get_eeprom_size())
battery_save(m_cart->get_eeprom_base(), m_cart->get_eeprom_size() * 4);
}
/*-------------------------------------------------
get default card software
-------------------------------------------------*/
std::string vboy_cart_slot_device::get_default_card_software(get_default_card_software_hook &hook) const
{
return software_get_default_slot("vb_rom");
}
/*-------------------------------------------------
read
-------------------------------------------------*/
READ32_MEMBER(vboy_cart_slot_device::read_cart)
{
if (m_cart)
return m_cart->read_cart(space, offset, mem_mask);
std::string const image_name(mconfig().options().image_option(instance_name()).value());
software_part const *const part(!image_name.empty() ? find_software_item(image_name, true) : nullptr);
if (part)
{
//printf("[%s] Found software part for image name '%s'\n", tag(), image_name.c_str());
for (rom_entry const &entry : part->romdata())
{
if (ROMENTRY_ISREGION(entry) && (entry.name() == "sram"))
{
//printf("[%s] Found 'sram' data area, enabling cartridge backup RAM\n", tag());
return "flatrom_sram";
}
}
}
else
return 0xffffffff;
{
//printf("[%s] No software part found for image name '%s'\n", tag(), image_name.c_str());
}
//printf("[%s] Assuming plain ROM cartridge\n", tag());
return "flatrom";
}
/*-------------------------------------------------
read
-------------------------------------------------*/
READ32_MEMBER(vboy_cart_slot_device::read_eeprom)
//**************************************************************************
// device_vboy_cart_interface
//**************************************************************************
void device_vboy_cart_interface::unload()
{
if (m_cart)
return m_cart->read_eeprom(space, offset, mem_mask);
else
return 0xffffffff;
}
/*-------------------------------------------------
write
-------------------------------------------------*/
WRITE32_MEMBER(vboy_cart_slot_device::write_eeprom)
device_vboy_cart_interface::device_vboy_cart_interface(machine_config const &mconfig, device_t &device) :
device_interface(device, "vboycart"),
m_slot(dynamic_cast<vboy_cart_slot_device *>(device.owner()))
{
if (m_cart)
m_cart->write_eeprom(space, offset, data, mem_mask);
}
#include "rom.h"
void vboy_carts(device_slot_interface &device)
{
device.option_add_internal("flatrom", VBOY_FLAT_ROM);
device.option_add_internal("flatrom_sram", VBOY_FLAT_ROM_SRAM);
}

View File

@ -1,5 +1,62 @@
// license:BSD-3-Clause
// copyright-holders:Fabio Priuli
// copyright-holders:Vas Crabb
/***************************************************************************
Virtual Boy cartridge slot
60-pin two-row connector (2.0 mm pin pitch, 1.6 mm row pitch)
GND 1 2 GND
/WE0 3 4 /ES
/WE1 5 6 /CS
/RESET 7 8 VCC
/INTCRO 9 10 A23
A19 11 12 A22
A18 13 14 A21
A8 15 16 A20
A7 17 18 A9
A6 19 20 A10
A5 21 22 A11
A4 23 24 A12
A3 25 26 A13
A2 27 28 A14
A1 29 30 A15
/RS 31 32 A16
GND 33 34 A17
/OE 35 36 VCC
D0 37 38 D15
D8 39 40 D7
D1 41 42 D14
D9 43 44 D6
D2 45 46 D13
D10 47 48 D5
D3 49 50 D12
D11 51 52 D4
VCC 53 54 VCC
ARO 55 56 ALO
ARI 57 58 ALI
GND 59 60 GND
The cartridge effectively has three 16 bit 8 megaword (16 megabyte) read/
write memory spaces. These are conventionally called EXP, CHIP and ROM.
Only 16 bit word accesses are possible (no lane select signals, and no
address bit A0). No commercial cartridges use the EXP space. The CHIP
space is used for cartridge SRAM (if present) and the ROM space is used
for program ROM.
Space Select Read Enable Write Enable Mapping on Virtual Boy
EXP /ES /OE /WE1 0x0400'0000-0x04ff'ffff
CHIP /CS /OE /WE0 0x0600'0000-0x06ff'ffff
ROM /RS /OE /WE1 0x0700'0000-0x07ff'ffff
Audio is passed through the cartridge, allowing cartridge hardware to
modify it. The output of the Virtual Boy's VSU sound chip is DC-coupled
to ARO (right) and ALO (left) via 4.7 resistors. ARI (right) and ALI
(left) are AC-coupled to the Virtual Boy's audio amplifier.
VCC is +5V
/INTCRO is an interrupt input from the cartridge to the host
/RESET is bidirectional - the system or cartridge can pull it low
***************************************************************************/
#ifndef MAME_BUS_VBOY_SLOT_H
#define MAME_BUS_VBOY_SLOT_H
@ -8,115 +65,121 @@
#include "softlist_dev.h"
/***************************************************************************
TYPE DEFINITIONS
***************************************************************************/
//**************************************************************************
// FORWARD DECLARATIONS
//**************************************************************************
class device_vboy_cart_interface;
/* PCB */
enum
{
VBOY_STD = 0,
VBOY_EEPROM
};
//**************************************************************************
// CLASS DECLARATIONS
//**************************************************************************
// ======================> device_vboy_cart_interface
class device_vboy_cart_interface : public device_interface
class vboy_cart_slot_device :
public device_t,
public device_image_interface,
public device_single_card_slot_interface<device_vboy_cart_interface>
{
public:
// construction/destruction
virtual ~device_vboy_cart_interface();
// reading and writing
virtual DECLARE_READ32_MEMBER(read_cart) { return 0xffffffff; }
virtual DECLARE_READ32_MEMBER(read_eeprom) { return 0xffffffff; }
virtual DECLARE_WRITE32_MEMBER(write_eeprom) { }
void rom_alloc(uint32_t size, const char *tag);
void eeprom_alloc(uint32_t size);
uint32_t* get_rom_base() { return m_rom; }
uint32_t* get_eeprom_base() { return &m_eeprom[0]; }
uint32_t get_rom_size() { return m_rom_size; }
uint32_t get_eeprom_size() { return m_eeprom.size(); }
void save_eeprom() { device().save_item(NAME(m_eeprom)); }
protected:
device_vboy_cart_interface(const machine_config &mconfig, device_t &device);
// internal state
uint32_t *m_rom;
uint32_t m_rom_size;
uint32_t m_rom_mask;
std::vector<uint32_t> m_eeprom;
};
// ======================> vboy_cart_slot_device
class vboy_cart_slot_device : public device_t,
public device_image_interface,
public device_single_card_slot_interface<device_vboy_cart_interface>
{
public:
// construction/destruction
template <typename T>
vboy_cart_slot_device(machine_config const &mconfig, char const *tag, device_t *owner, T &&opts, char const *dflt)
: vboy_cart_slot_device(mconfig, tag, owner, 0)
vboy_cart_slot_device(machine_config const &mconfig, char const *tag, device_t *owner, T &&opts, char const *dflt) :
vboy_cart_slot_device(mconfig, tag, owner, 0U)
{
option_reset();
opts(*this);
set_default_option(dflt);
set_fixed(false);
}
vboy_cart_slot_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock = 0);
virtual ~vboy_cart_slot_device();
vboy_cart_slot_device(machine_config const &mconfig, char const *tag, device_t *owner, u32 clock = 0U);
// image-level overrides
// configuration
auto intcro() { return m_intcro.bind(); }
template <typename T> void set_exp(T &&tag, int no, offs_t base) { m_exp_space.set_tag(std::forward<T>(tag), no); m_exp_base = base; }
template <typename T> void set_chip(T &&tag, int no, offs_t base) { m_chip_space.set_tag(std::forward<T>(tag), no); m_chip_base = base; }
template <typename T> void set_rom(T &&tag, int no, offs_t base) { m_rom_space.set_tag(std::forward<T>(tag), no); m_rom_base = base; }
// device_image_interface implementation
virtual image_init_result call_load() override;
virtual void call_unload() override;
virtual const software_list_loader &get_software_list_loader() const override { return rom_software_list_loader::instance(); }
virtual iodevice_t image_type() const noexcept override { return IO_CARTSLOT; }
virtual bool is_readable() const noexcept override { return true; }
virtual bool is_writeable() const noexcept override { return false; }
virtual bool is_creatable() const noexcept override { return false; }
virtual bool must_be_loaded() const noexcept override { return true; }
virtual bool is_reset_on_load() const noexcept override { return true; }
virtual char const *image_interface() const noexcept override { return "vboy_cart"; }
virtual char const *file_extensions() const noexcept override { return "vb,bin"; }
int get_type() { return m_type; }
void save_eeprom() { if (m_cart && m_cart->get_eeprom_size()) m_cart->save_eeprom(); }
virtual iodevice_t image_type() const override { return IO_CARTSLOT; }
virtual bool is_readable() const override { return 1; }
virtual bool is_writeable() const override { return 0; }
virtual bool is_creatable() const override { return 0; }
virtual bool must_be_loaded() const override { return 1; }
virtual bool is_reset_on_load() const override { return 1; }
virtual const char *image_interface() const override { return "vboy_cart"; }
virtual const char *file_extensions() const override { return "vb,bin"; }
// slot interface overrides
// device_slot_interface implementation
virtual std::string get_default_card_software(get_default_card_software_hook &hook) const override;
// reading and writing
virtual DECLARE_READ32_MEMBER(read_cart);
virtual DECLARE_READ32_MEMBER(read_eeprom);
virtual DECLARE_WRITE32_MEMBER(write_eeprom);
protected:
// device-level overrides
virtual void device_start() override;
// device_t implementation
virtual void device_validity_check(validity_checker &valid) const override ATTR_COLD;
virtual void device_resolve_objects() override ATTR_COLD;
virtual void device_start() override ATTR_COLD;
int m_type;
device_vboy_cart_interface* m_cart;
// device_image_interface implementation
virtual const software_list_loader &get_software_list_loader() const override { return rom_software_list_loader::instance(); }
private:
devcb_write_line m_intcro;
optional_address_space m_exp_space;
optional_address_space m_chip_space;
optional_address_space m_rom_space;
offs_t m_exp_base;
offs_t m_chip_base;
offs_t m_rom_base;
device_vboy_cart_interface *m_cart;
friend class device_vboy_cart_interface;
};
// device type definition
class device_vboy_cart_interface : public device_interface
{
public:
virtual image_init_result load() ATTR_COLD = 0;
virtual void unload() ATTR_COLD;
protected:
device_vboy_cart_interface(machine_config const &mconfig, device_t &device);
bool has_slot() const { return nullptr != m_slot; }
address_space *exp_space() { return m_slot ? m_slot->m_exp_space.target() : nullptr; }
address_space *chip_space() { return m_slot ? m_slot->m_chip_space.target() : nullptr; }
address_space *rom_space() { return m_slot ? m_slot->m_rom_space.target() : nullptr; }
offs_t exp_base() { return m_slot ? m_slot->m_exp_base : 0U; }
offs_t chip_base() { return m_slot ? m_slot->m_chip_base : 0U; }
offs_t rom_base() { return m_slot ? m_slot->m_rom_base : 0U; }
void battery_load(void *buffer, int length, int fill) { assert(m_slot); m_slot->battery_load(buffer, length, fill); }
void battery_load(void *buffer, int length, void *def_buffer) { assert(m_slot); m_slot->battery_load(buffer, length, def_buffer); }
void battery_save(void const *buffer, int length) { assert(m_slot); m_slot->battery_save(buffer, length); }
void intcro(int state) { if (m_slot) m_slot->m_intcro(state); }
private:
vboy_cart_slot_device *const m_slot;
};
//**************************************************************************
// FUNCTION PROTOTYPES
//**************************************************************************
void vboy_carts(device_slot_interface &device);
//**************************************************************************
// DEVICE TYPE DECLARATIONS
//**************************************************************************
DECLARE_DEVICE_TYPE(VBOY_CART_SLOT, vboy_cart_slot_device)
/***************************************************************************
DEVICE CONFIGURATION MACROS
***************************************************************************/
#define VBOYSLOT_ROM_REGION_TAG ":cart:rom"
#endif // MAME_BUS_VBOY_SLOT_H

View File

@ -1,5 +1,66 @@
// license:BSD-3-Clause
// copyright-holders:Wilbert Pol
/***************************************************************************
Bandai WonderSwan cartridge slot
48-pin single-sided PCB edge connector
The SoC maps the following ranges to the cartridge slot:
* Memory 0x10000-0x1ffff 8-bit read/write (typically used for cartridge SRAM)
3-cycle access on WonderSwan, 1-cycle access on WonderSwan Color
* Memory 0x20000-0xfffff 16-bit read-only (writes not emitted)
* I/O 0xc0-0xff
Pin Name Notes
1 GND
2 A15
3 A10
4 A11
5 A9
6 A8
7 A13
8 A14
9 A12
10 A7
11 A6
12 A5
13 A4
14 D15
15 D14
16 D7
17 D6
18 D5
19 D4
20 D3
21 D2
22 D1
23 D0
24 +3.3V
25 +3.3V
26 A0
27 A1
28 A2
29 A3
30 A19
31 A18
32 A17
33 A16
34 D8
35 D9
36 D10
37 D11
38 D12
39 D13
40 /RESET
41 ? input used while authenticating cartridge
42 IO/M low when accessing I/O ports
43 /RD
44 /WR
45 /CART low when accessing cartridge
46 INT usually used for RTC alarm interrupt
47 CLK 384 kHz on WonderSwan
48 GND
***************************************************************************/
#ifndef MAME_BUS_WSWAN_SLOT_H
#define MAME_BUS_WSWAN_SLOT_H

View File

@ -1257,7 +1257,7 @@ void v810_device::device_start()
{
m_program = &space(AS_PROGRAM);
m_cache = m_program->cache<2, 0, ENDIANNESS_LITTLE>();
m_io = &space(AS_IO);
m_io = has_space(AS_IO) ? &space(AS_IO) : m_program;
m_irq_line = 0;
m_irq_state = CLEAR_LINE;

View File

@ -879,16 +879,15 @@ std::string device_t::subtag(std::string _tag) const
{
const char *tag = _tag.c_str();
std::string result;
// if the tag begins with a colon, ignore our path and start from the root
if (*tag == ':')
{
// if the tag begins with a colon, ignore our path and start from the root
tag++;
result.assign(":");
}
// otherwise, start with our path
else
{
// otherwise, start with our path
result.assign(m_tag);
if (result != ":")
result.append(":");

View File

@ -31,8 +31,8 @@
#include "cpu/v810/v810.h"
#include "bus/vboy/slot.h"
#include "bus/vboy/rom.h"
#include "machine/timer.h"
#include "emupal.h"
#include "screen.h"
#include "softlist.h"
@ -85,7 +85,6 @@ public:
void vboy(machine_config &config);
protected:
virtual void machine_start() override;
virtual void machine_reset() override;
virtual void video_start() override;
@ -191,7 +190,6 @@ private:
TIMER_DEVICE_CALLBACK_MEMBER(timer_pad_tick);
TIMER_DEVICE_CALLBACK_MEMBER(vboy_scanlineL);
void vboy_io(address_map &map);
void vboy_mem(address_map &map);
};
@ -1073,40 +1071,10 @@ void vboy_state::vboy_mem(address_map &map)
map(0x01000000, 0x010005ff).rw("vbsnd", FUNC(vboysnd_device::read), FUNC(vboysnd_device::write));
map(0x02000000, 0x0200002b).mirror(0x0ffff00).rw(FUNC(vboy_state::io_r), FUNC(vboy_state::io_w)); // Hardware control registers mask 0xff
//map(0x04000000, 0x04ffffff) // Expansion area
//map(0x04000000, 0x04ffffff) cartslot EXP
map(0x05000000, 0x0500ffff).mirror(0x0ff0000).ram().share("wram");// Main RAM - 64K mask 0xffff
map(0x06000000, 0x06003fff).rw(m_cart, FUNC(vboy_cart_slot_device::read_eeprom), FUNC(vboy_cart_slot_device::write_eeprom)); // Cart RAM - 8K NVRAM
// map(0x07000000, 0x071fffff).mirror(0x0e00000).r("cartslot", FUNC(vboy_cart_slot_device::read_cart)); /* ROM */
}
void vboy_state::vboy_io(address_map &map)
{
map.global_mask(0x07ffffff);
map(0x00000000, 0x00005fff).ram().share("l_frame_0"); // L frame buffer 0
map(0x00006000, 0x00007fff).rw(FUNC(vboy_state::font0_r), FUNC(vboy_state::font0_w)); // Font 0-511
map(0x00008000, 0x0000dfff).ram().share("l_frame_1"); // L frame buffer 1
map(0x0000e000, 0x0000ffff).rw(FUNC(vboy_state::font1_r), FUNC(vboy_state::font1_w)); // Font 512-1023
map(0x00010000, 0x00015fff).ram().share("r_frame_0"); // R frame buffer 0
map(0x00016000, 0x00017fff).rw(FUNC(vboy_state::font2_r), FUNC(vboy_state::font2_w)); // Font 1024-1535
map(0x00018000, 0x0001dfff).ram().share("r_frame_1"); // R frame buffer 1
map(0x0001e000, 0x0001ffff).rw(FUNC(vboy_state::font3_r), FUNC(vboy_state::font3_w)); // Font 1536-2047
map(0x00020000, 0x0003ffff).rw(FUNC(vboy_state::vboy_bgmap_r), FUNC(vboy_state::vboy_bgmap_w)); // VIPC memory
//map(0x00040000, 0x0005ffff).ram(); // VIPC
map(0x0005f800, 0x0005f87f).rw(FUNC(vboy_state::vip_r), FUNC(vboy_state::vip_w));
map(0x00078000, 0x00079fff).rw(FUNC(vboy_state::font0_r), FUNC(vboy_state::font0_w)); // Font 0-511 mirror
map(0x0007a000, 0x0007bfff).rw(FUNC(vboy_state::font1_r), FUNC(vboy_state::font1_w)); // Font 512-1023 mirror
map(0x0007c000, 0x0007dfff).rw(FUNC(vboy_state::font2_r), FUNC(vboy_state::font2_w)); // Font 1024-1535 mirror
map(0x0007e000, 0x0007ffff).rw(FUNC(vboy_state::font3_r), FUNC(vboy_state::font3_w)); // Font 1536-2047 mirror
map(0x01000000, 0x010005ff).rw("vbsnd", FUNC(vboysnd_device::read), FUNC(vboysnd_device::write));
map(0x02000000, 0x0200002b).mirror(0x0ffff00).rw(FUNC(vboy_state::io_r), FUNC(vboy_state::io_w)); // Hardware control registers mask 0xff
// map(0x04000000, 0x04ffffff) // Expansion area
map(0x05000000, 0x0500ffff).mirror(0x0ff0000).ram().share("wram"); // Main RAM - 64K mask 0xffff
map(0x06000000, 0x06003fff).noprw(); // Cart RAM - 8K NVRAM ?
// map(0x07000000, 0x071fffff).mirror(0x0e00000).r("cartslot", FUNC(vboy_cart_slot_device::read_cart)); /* ROM */
//map(0x06000000, 0x06ffffff) cartslot CHIP
//map(0x07000000, 0x07ffffff) cartslot ROM
}
/* Input ports */
@ -1131,25 +1099,6 @@ static INPUT_PORTS_START( vboy )
INPUT_PORTS_END
void vboy_state::machine_start()
{
// install the cart ROM as a bank into the address map.
// this speeds up the rom access, by skipping the m_cart->read_rom
// trampoline (but forces us to alloc always a 0x200000-wide region)
if (m_cart->exists())
{
std::string region_tag;
m_cart_rom = memregion(region_tag.assign(m_cart->tag()).append(VBOYSLOT_ROM_REGION_TAG).c_str());
m_maincpu->space(AS_PROGRAM).install_read_bank(0x07000000, 0x071fffff, 0x0e00000, "prog_cart_bank");
m_maincpu->space(AS_IO).install_read_bank(0x07000000, 0x071fffff, 0x0e00000, "io_cart_bank");
membank("prog_cart_bank")->set_base(m_cart_rom->base());
membank("io_cart_bank")->set_base(m_cart_rom->base());
m_cart->save_eeprom();
}
}
void vboy_state::machine_reset()
{
/* Initial values taken from Reality Boy, to be verified when emulation improves */
@ -1299,18 +1248,12 @@ TIMER_DEVICE_CALLBACK_MEMBER(vboy_state::vboy_scanlineR)
#endif
static void vboy_cart(device_slot_interface &device)
{
device.option_add_internal("vb_rom", VBOY_ROM_STD);
device.option_add_internal("vb_eeprom", VBOY_ROM_EEPROM);
}
void vboy_state::vboy(machine_config &config)
{
/* basic machine hardware */
V810(config, m_maincpu, XTAL(20'000'000));
m_maincpu->set_addrmap(AS_PROGRAM, &vboy_state::vboy_mem);
m_maincpu->set_addrmap(AS_IO, &vboy_state::vboy_io);
TIMER(config, "scantimer_l").configure_scanline(FUNC(vboy_state::vboy_scanlineL), "3dleft", 0, 1);
//TIMER(config, "scantimer_r").configure_scanline(FUNC(vboy_state::vboy_scanlineR), "3dright", 0, 1);
@ -1337,7 +1280,11 @@ void vboy_state::vboy(machine_config &config)
rscreen.set_palette(m_palette);
/* cartridge */
VBOY_CART_SLOT(config, m_cart, vboy_cart, nullptr);
VBOY_CART_SLOT(config, m_cart, vboy_carts, nullptr);
m_cart->intcro().set_inputline(m_maincpu, 2);
m_cart->set_exp(m_maincpu, AS_PROGRAM, 0x0400'0000);
m_cart->set_chip(m_maincpu, AS_PROGRAM, 0x0600'0000);
m_cart->set_rom(m_maincpu, AS_PROGRAM, 0x0700'0000);
/* software lists */
SOFTWARE_LIST(config, "cart_list").set_original("vboy");